@tarojs/runtime 3.7.0-canary.6 → 3.8.0-canary.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +14 -0
- package/dist/bom/URL.d.ts +54 -0
- package/dist/bom/URL.js +221 -0
- package/dist/bom/URL.js.map +1 -0
- package/dist/bom/URLSearchParams.d.ts +2 -0
- package/dist/bom/URLSearchParams.js +131 -0
- package/dist/bom/URLSearchParams.js.map +1 -0
- package/dist/bom/document.d.ts +3 -0
- package/dist/bom/document.js +39 -0
- package/dist/bom/document.js.map +1 -0
- package/dist/bom/getComputedStyle.d.ts +5 -0
- package/dist/bom/getComputedStyle.js +8 -0
- package/dist/bom/getComputedStyle.js.map +1 -0
- package/dist/bom/history.d.ts +32 -0
- package/dist/bom/history.js +121 -0
- package/dist/bom/history.js.map +1 -0
- package/dist/bom/location.d.ts +39 -0
- package/dist/bom/location.js +240 -0
- package/dist/bom/location.js.map +1 -0
- package/dist/bom/navigator.d.ts +2 -0
- package/dist/bom/navigator.js +24 -0
- package/dist/bom/navigator.js.map +1 -0
- package/dist/bom/raf.d.ts +4 -0
- package/dist/bom/raf.js +33 -0
- package/dist/bom/raf.js.map +1 -0
- package/dist/bom/window.d.ts +25 -0
- package/dist/bom/window.js +92 -0
- package/dist/bom/window.js.map +1 -0
- package/dist/constants/index.d.ts +60 -0
- package/dist/constants/index.js +63 -0
- package/dist/constants/index.js.map +1 -0
- package/dist/current.d.ts +19 -0
- package/dist/current.js +9 -0
- package/dist/current.js.map +1 -0
- package/dist/dom/anchor-element.d.ts +14 -0
- package/dist/dom/anchor-element.js +54 -0
- package/dist/dom/anchor-element.js.map +1 -0
- package/dist/dom/class-list.d.ts +17 -0
- package/dist/dom/class-list.js +92 -0
- package/dist/dom/class-list.js.map +1 -0
- package/dist/dom/document.d.ts +25 -0
- package/dist/dom/document.js +80 -0
- package/dist/dom/document.js.map +1 -0
- package/dist/dom/element.d.ts +40 -0
- package/dist/dom/element.js +318 -0
- package/dist/dom/element.js.map +1 -0
- package/dist/dom/event-source.d.ts +7 -0
- package/dist/dom/event-source.js +17 -0
- package/dist/dom/event-source.js.map +1 -0
- package/dist/dom/event-target.d.ts +8 -0
- package/dist/dom/event-target.js +78 -0
- package/dist/dom/event-target.js.map +1 -0
- package/dist/dom/event.d.ts +24 -0
- package/dist/dom/event.js +152 -0
- package/dist/dom/event.js.map +1 -0
- package/dist/dom/form.d.ts +10 -0
- package/dist/dom/form.js +38 -0
- package/dist/dom/form.js.map +1 -0
- package/dist/dom/node.d.ts +107 -0
- package/dist/dom/node.js +292 -0
- package/dist/dom/node.js.map +1 -0
- package/dist/dom/root.d.ts +16 -0
- package/dist/dom/root.js +169 -0
- package/dist/dom/root.js.map +1 -0
- package/dist/dom/style.d.ts +15 -0
- package/dist/dom/style.js +168 -0
- package/dist/dom/style.js.map +1 -0
- package/dist/dom/style_properties.d.ts +3 -0
- package/dist/dom/style_properties.js +186 -0
- package/dist/dom/style_properties.js.map +1 -0
- package/dist/dom/svg.d.ts +4 -0
- package/dist/dom/svg.js +8 -0
- package/dist/dom/svg.js.map +1 -0
- package/dist/dom/text.d.ts +15 -0
- package/dist/dom/text.js +41 -0
- package/dist/dom/text.js.map +1 -0
- package/dist/dom/transfer.d.ts +8 -0
- package/dist/dom/transfer.js +15 -0
- package/dist/dom/transfer.js.map +1 -0
- package/dist/dom/tree.d.ts +4 -0
- package/dist/dom/tree.js +38 -0
- package/dist/dom/tree.js.map +1 -0
- package/dist/dom-external/element.d.ts +4 -0
- package/dist/dom-external/element.js +29 -0
- package/dist/dom-external/element.js.map +1 -0
- package/dist/dom-external/index.d.ts +1 -0
- package/dist/dom-external/index.js +38 -0
- package/dist/dom-external/index.js.map +1 -0
- package/dist/dom-external/inner-html/html.d.ts +3 -0
- package/dist/dom-external/inner-html/html.js +28 -0
- package/dist/dom-external/inner-html/html.js.map +1 -0
- package/dist/dom-external/inner-html/parser.d.ts +25 -0
- package/dist/dom-external/inner-html/parser.js +257 -0
- package/dist/dom-external/inner-html/parser.js.map +1 -0
- package/dist/dom-external/inner-html/scaner.d.ts +30 -0
- package/dist/dom-external/inner-html/scaner.js +304 -0
- package/dist/dom-external/inner-html/scaner.js.map +1 -0
- package/dist/dom-external/inner-html/style.d.ts +27 -0
- package/dist/dom-external/inner-html/style.js +235 -0
- package/dist/dom-external/inner-html/style.js.map +1 -0
- package/dist/dom-external/inner-html/tags.d.ts +14 -0
- package/dist/dom-external/inner-html/tags.js +41 -0
- package/dist/dom-external/inner-html/tags.js.map +1 -0
- package/dist/dom-external/inner-html/utils.d.ts +2 -0
- package/dist/dom-external/inner-html/utils.js +12 -0
- package/dist/dom-external/inner-html/utils.js.map +1 -0
- package/dist/dom-external/mutation-observer/implements.d.ts +71 -0
- package/dist/dom-external/mutation-observer/implements.js +108 -0
- package/dist/dom-external/mutation-observer/implements.js.map +1 -0
- package/dist/dom-external/mutation-observer/index.d.ts +12 -0
- package/dist/dom-external/mutation-observer/index.js +35 -0
- package/dist/dom-external/mutation-observer/index.js.map +1 -0
- package/dist/dom-external/node.d.ts +12 -0
- package/dist/dom-external/node.js +75 -0
- package/dist/dom-external/node.js.map +1 -0
- package/dist/dsl/common.d.ts +15 -0
- package/dist/dsl/common.js +337 -0
- package/dist/dsl/common.js.map +1 -0
- package/dist/emitter/emitter.d.ts +4 -0
- package/dist/emitter/emitter.js +7 -0
- package/dist/emitter/emitter.js.map +1 -0
- package/dist/env.d.ts +7 -0
- package/dist/env.js +9 -0
- package/dist/env.js.map +1 -0
- package/dist/hydrate.d.ts +11 -0
- package/dist/hydrate.js +91 -0
- package/dist/hydrate.js.map +1 -0
- package/dist/index-26658829.d.ts +23 -0
- package/dist/{runtime.cjs.d.ts → index.cjs.d.ts} +95 -88
- package/dist/{runtime.h5.js → index.cjs.js} +2276 -438
- package/dist/index.cjs.js.map +1 -0
- package/dist/index.d.ts +34 -0
- package/dist/index.js +33 -0
- package/dist/index.js.map +1 -0
- package/dist/instance-0f017c6e.d.ts +95 -0
- package/dist/next-tick.d.ts +3 -0
- package/dist/next-tick.js +47 -0
- package/dist/next-tick.js.map +1 -0
- package/dist/node_types-9ac5b4dd.d.ts +11 -0
- package/dist/options-0f017c6e.d.ts +17 -0
- package/dist/options.d.ts +3 -0
- package/dist/options.js +7 -0
- package/dist/options.js.map +1 -0
- package/dist/perf.d.ts +7 -0
- package/dist/perf.js +28 -0
- package/dist/perf.js.map +1 -0
- package/dist/polyfill/array.d.ts +3 -0
- package/dist/polyfill/array.js +56 -0
- package/dist/polyfill/array.js.map +1 -0
- package/dist/polyfill/index.d.ts +2 -0
- package/dist/polyfill/index.js +34 -0
- package/dist/polyfill/index.js.map +1 -0
- package/dist/polyfill/intersection-observer.d.ts +2 -0
- package/dist/polyfill/intersection-observer.js +599 -0
- package/dist/polyfill/intersection-observer.js.map +1 -0
- package/dist/polyfill/object.d.ts +4 -0
- package/dist/polyfill/object.js +102 -0
- package/dist/polyfill/object.js.map +1 -0
- package/dist/record-32b054d8.d.ts +25 -0
- package/dist/runtime.esm.d.ts +95 -88
- package/dist/runtime.esm.js +1267 -427
- package/dist/runtime.esm.js.map +1 -1
- package/dist/utils/cache.d.ts +13 -0
- package/dist/utils/cache.js +27 -0
- package/dist/utils/cache.js.map +1 -0
- package/dist/utils/index.d.ts +24 -0
- package/dist/utils/index.js +95 -0
- package/dist/utils/index.js.map +1 -0
- package/dist/utils/lodash.d.ts +2 -0
- package/dist/utils/lodash.js +22 -0
- package/dist/utils/lodash.js.map +1 -0
- package/dist/utils/router.d.ts +8 -0
- package/dist/utils/router.js +24 -0
- package/dist/utils/router.js.map +1 -0
- package/package.json +16 -11
- package/dist/runtime.cjs.js +0 -4614
- package/dist/runtime.h5.d.ts +0 -781
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"parser.js","sources":["../../../src/dom-external/inner-html/parser.ts"],"sourcesContent":["import { isFunction } from '@tarojs/shared'\n\nimport { options } from '../../options'\nimport { Scaner, Token } from './scaner'\nimport StyleTagParser from './style'\nimport { getSpecialElementMapping, isBlockElements, isInlineElements, isMiniElements, isSpecialElements, specialMiniElements } from './tags'\nimport { unquote } from './utils'\n\nimport type { TaroDocument } from '../../dom/document'\nimport type { TaroElement } from '../../dom/element'\n\ninterface State {\n tokens: Token[]\n cursor: number\n stack: Element[]\n}\n\nconst closingTagAncestorBreakers = {\n li: ['ul', 'ol', 'menu'],\n dt: ['dl'],\n dd: ['dl'],\n tbody: ['table'],\n thead: ['table'],\n tfoot: ['table'],\n tr: ['table'],\n td: ['table']\n}\n\ninterface Node {\n type: string\n}\n\ninterface Comment extends Node {\n type: 'comment'\n content: string\n}\n\nexport interface Text extends Node {\n type: 'text'\n content: string\n}\n\nexport interface Element extends Node {\n type: 'element'\n tagName: string\n children: ChildNode[]\n attributes: string[]\n}\n\nexport interface ParsedTaroElement extends TaroElement {\n h5tagName?: string\n}\n\ntype ChildNode = Comment | Text | Element\n\nfunction hasTerminalParent (tagName: string, stack: Element[]) {\n const tagParents: undefined | string[] = closingTagAncestorBreakers[tagName]\n if (tagParents) {\n let currentIndex = stack.length - 1\n while (currentIndex >= 0) {\n const parentTagName = stack[currentIndex].tagName\n if (parentTagName === tagName) {\n break\n }\n if (tagParents && tagParents.includes(parentTagName!)) {\n return true\n }\n currentIndex--\n }\n }\n return false\n}\n\n/**\n * 将属性数组转换为属性对象\n * @param attributes 字符串数组,包含属性信息\n * @returns 属性对象,键为属性名,值为属性值或true\n */\nfunction attributesArray2Props (attributes: string[]): Record<string, string | true> {\n const props: Record<string, string | true> = {}\n for (let i = 0; i < attributes.length; i++) {\n const attr = attributes[i]\n const [key, value] = splitEqual(attr)\n props[key] = value == null ? true : unquote(value)\n }\n\n return props\n}\n\nfunction getTagName (tag: string, attributes: string[]) {\n if (options.html!.renderHTMLTag) {\n return tag\n }\n\n if (specialMiniElements[tag]) {\n return specialMiniElements[tag]\n } else if (isMiniElements(tag)) {\n return tag\n } else if (isBlockElements(tag)) {\n return 'view'\n } else if (isInlineElements(tag)) {\n return 'text'\n } else if (isSpecialElements(tag)) {\n // if it's special tag, the real tag is determined by the config mapping\n const mapping = getSpecialElementMapping(tag)\n const props = attributesArray2Props(attributes)\n\n if (mapping) {\n return mapping.mapName(props)\n }\n }\n\n return 'view'\n}\n\nfunction splitEqual (str: string) {\n const sep = '='\n const idx = str.indexOf(sep)\n if (idx === -1) return [str]\n const key = str.slice(0, idx).trim()\n const value = str.slice(idx + sep.length).trim()\n return [key, value]\n}\n\nfunction format (\n children: ChildNode[],\n document: TaroDocument,\n styleOptions: {\n styleTagParser: StyleTagParser\n descendantList: number[]\n },\n parent?: TaroElement\n) {\n return children\n .filter(child => {\n // 过滤注释和空文本节点\n if (child.type === 'comment') {\n return false\n } else if (child.type === 'text') {\n return child.content !== ''\n }\n return true\n })\n .map((child: Text | Element) => {\n // 文本节点\n if (child.type === 'text') {\n let text = document.createTextNode(child.content)\n if (isFunction(options.html!.transformText)) {\n text = options.html!.transformText(text, child)\n }\n parent?.appendChild(text)\n return text\n }\n // img标签,把width和height写入style,删除原有的width、height和style属性\n if (child.tagName === 'img') {\n let styleText = ''\n const toBeRemovedIndexs: number[] = []\n for (let i = 0; i < child.attributes.length; i++) {\n const attr = child.attributes[i]\n const [key, value] = splitEqual(attr)\n if (key === 'width' || key === 'height') {\n styleText += `${key}:${value};`\n toBeRemovedIndexs.push(i)\n } else if (key === 'style') {\n styleText = `${styleText}${value};`\n toBeRemovedIndexs.push(i)\n }\n }\n child.attributes = child.attributes.filter((_, index) => !toBeRemovedIndexs.includes(index))\n child.attributes.push(`style=${styleText.replace(/['\"]/g, '')}`)\n }\n\n const el: ParsedTaroElement = document.createElement(getTagName(child.tagName, child.attributes))\n el.h5tagName = child.tagName\n\n parent?.appendChild(el)\n\n if (!options.html!.renderHTMLTag) {\n el.className = `h5-${child.tagName}`\n }\n\n for (let i = 0; i < child.attributes.length; i++) {\n const attr = child.attributes[i]\n const [key, value] = splitEqual(attr)\n if (key === 'class') {\n el.className += ' ' + unquote(value)\n } else if (key[0] === 'o' && key[1] === 'n') {\n continue\n } else {\n el.setAttribute(key, value == null ? true : unquote(value))\n }\n }\n\n const { styleTagParser, descendantList } = styleOptions\n const list = descendantList.slice()\n const style = styleTagParser.matchStyle(child.tagName, el, list)\n\n el.setAttribute('style', style + el.style.cssText)\n // console.log('style, ', style)\n\n format(child.children, document, {\n styleTagParser,\n descendantList: list\n }, el)\n\n if (isFunction(options.html!.transformElement)) {\n return options.html!.transformElement(el, child)\n }\n\n return el\n })\n}\n\nexport function parser (html: string, document: TaroDocument) {\n const styleTagParser = new StyleTagParser()\n html = styleTagParser.extractStyle(html)\n\n const tokens = new Scaner(html).scan()\n\n const root: Element = { tagName: '', children: [], type: 'element', attributes: [] }\n\n const state = { tokens, options, cursor: 0, stack: [root] }\n parse(state)\n\n return format(root.children, document, {\n styleTagParser,\n descendantList: Array(styleTagParser.styles.length).fill(0)\n })\n}\n\nfunction parse (state: State) {\n const { tokens, stack } = state\n let { cursor } = state\n\n const len = tokens.length\n\n let nodes = stack[stack.length - 1].children\n\n while (cursor < len) {\n const token = tokens[cursor]\n if (token.type !== 'tag-start') {\n // comment or text\n nodes.push(token as ChildNode)\n cursor++\n continue\n }\n\n const tagToken = tokens[++cursor]\n cursor++\n const tagName = tagToken.content!.toLowerCase()\n if (token.close) {\n let index = stack.length\n let shouldRewind = false\n while (--index > -1) {\n if (stack[index].tagName === tagName) {\n shouldRewind = true\n break\n }\n }\n while (cursor < len) {\n const endToken = tokens[cursor]\n if (endToken.type !== 'tag-end') break\n cursor++\n }\n if (shouldRewind) {\n stack.splice(index)\n break\n } else {\n continue\n }\n }\n\n const isClosingTag = options.html!.closingElements.has(tagName)\n let shouldRewindToAutoClose = isClosingTag\n if (shouldRewindToAutoClose) {\n shouldRewindToAutoClose = !hasTerminalParent(tagName, stack)\n }\n\n if (shouldRewindToAutoClose) {\n let currentIndex = stack.length - 1\n while (currentIndex > 0) {\n if (tagName === stack[currentIndex].tagName) {\n stack.splice(currentIndex)\n const previousIndex = currentIndex - 1\n nodes = stack[previousIndex].children\n break\n }\n currentIndex = currentIndex - 1\n }\n }\n\n const attributes: string[] = []\n let attrToken: Token\n while (cursor < len) {\n attrToken = tokens[cursor]\n if (attrToken.type === 'tag-end') break\n attributes.push(attrToken.content!)\n cursor++\n }\n\n cursor++\n const children: Element[] = []\n const element: Element = {\n type: 'element',\n tagName: tagToken.content!,\n attributes,\n children\n }\n nodes.push(element)\n\n const hasChildren = !(attrToken!.close || options.html!.voidElements.has(tagName))\n if (hasChildren) {\n stack.push({ tagName, children } as any)\n const innerState: State = { tokens, cursor, stack }\n parse(innerState)\n cursor = innerState.cursor\n }\n }\n\n state.cursor = cursor\n}\n"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
interface Position {
|
|
2
|
+
index: number;
|
|
3
|
+
column: number;
|
|
4
|
+
line: number;
|
|
5
|
+
}
|
|
6
|
+
interface Token {
|
|
7
|
+
type: string;
|
|
8
|
+
content?: string;
|
|
9
|
+
position?: {
|
|
10
|
+
start?: Position;
|
|
11
|
+
end?: Position;
|
|
12
|
+
};
|
|
13
|
+
close?: boolean;
|
|
14
|
+
}
|
|
15
|
+
declare class Scaner {
|
|
16
|
+
private tokens;
|
|
17
|
+
private position;
|
|
18
|
+
private html;
|
|
19
|
+
constructor(html: string);
|
|
20
|
+
scan(): Token[];
|
|
21
|
+
private scanText;
|
|
22
|
+
private scanComment;
|
|
23
|
+
private scanTag;
|
|
24
|
+
private scanTagStart;
|
|
25
|
+
private scanTagEnd;
|
|
26
|
+
private scanTagName;
|
|
27
|
+
private scanAttrs;
|
|
28
|
+
private scanSkipTag;
|
|
29
|
+
}
|
|
30
|
+
export { Token, Scaner };
|
|
@@ -0,0 +1,304 @@
|
|
|
1
|
+
import { options } from '../../options.js';
|
|
2
|
+
|
|
3
|
+
function initPosition() {
|
|
4
|
+
return {
|
|
5
|
+
index: 0,
|
|
6
|
+
column: 0,
|
|
7
|
+
line: 0
|
|
8
|
+
};
|
|
9
|
+
}
|
|
10
|
+
function feedPosition(position, str, len) {
|
|
11
|
+
const start = position.index;
|
|
12
|
+
const end = position.index = start + len;
|
|
13
|
+
for (let i = start; i < end; i++) {
|
|
14
|
+
const char = str.charAt(i);
|
|
15
|
+
if (char === '\n') {
|
|
16
|
+
position.line++;
|
|
17
|
+
position.column = 0;
|
|
18
|
+
}
|
|
19
|
+
else {
|
|
20
|
+
position.column++;
|
|
21
|
+
}
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
function jumpPosition(position, str, end) {
|
|
25
|
+
const len = end - position.index;
|
|
26
|
+
return feedPosition(position, str, len);
|
|
27
|
+
}
|
|
28
|
+
function copyPosition(position) {
|
|
29
|
+
return {
|
|
30
|
+
index: position.index,
|
|
31
|
+
line: position.line,
|
|
32
|
+
column: position.column
|
|
33
|
+
};
|
|
34
|
+
}
|
|
35
|
+
const whitespace = /\s/;
|
|
36
|
+
function isWhitespaceChar(char) {
|
|
37
|
+
return whitespace.test(char);
|
|
38
|
+
}
|
|
39
|
+
const equalSign = /=/;
|
|
40
|
+
function isEqualSignChar(char) {
|
|
41
|
+
return equalSign.test(char);
|
|
42
|
+
}
|
|
43
|
+
function shouldBeIgnore(tagName) {
|
|
44
|
+
const name = tagName.toLowerCase();
|
|
45
|
+
if (options.html.skipElements.has(name)) {
|
|
46
|
+
return true;
|
|
47
|
+
}
|
|
48
|
+
return false;
|
|
49
|
+
}
|
|
50
|
+
const alphanumeric = /[A-Za-z0-9]/;
|
|
51
|
+
function findTextEnd(str, index) {
|
|
52
|
+
while (true) {
|
|
53
|
+
const textEnd = str.indexOf('<', index);
|
|
54
|
+
if (textEnd === -1) {
|
|
55
|
+
return textEnd;
|
|
56
|
+
}
|
|
57
|
+
const char = str.charAt(textEnd + 1);
|
|
58
|
+
if (char === '/' || char === '!' || alphanumeric.test(char)) {
|
|
59
|
+
return textEnd;
|
|
60
|
+
}
|
|
61
|
+
index = textEnd + 1;
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
function isWordEnd(cursor, wordBegin, html) {
|
|
65
|
+
if (!isWhitespaceChar(html.charAt(cursor)))
|
|
66
|
+
return false;
|
|
67
|
+
const len = html.length;
|
|
68
|
+
// backwrad
|
|
69
|
+
for (let i = cursor - 1; i > wordBegin; i--) {
|
|
70
|
+
const char = html.charAt(i);
|
|
71
|
+
if (!isWhitespaceChar(char)) {
|
|
72
|
+
if (isEqualSignChar(char))
|
|
73
|
+
return false;
|
|
74
|
+
break;
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
// forward
|
|
78
|
+
for (let i = cursor + 1; i < len; i++) {
|
|
79
|
+
const char = html.charAt(i);
|
|
80
|
+
if (!isWhitespaceChar(char)) {
|
|
81
|
+
if (isEqualSignChar(char))
|
|
82
|
+
return false;
|
|
83
|
+
return true;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
class Scaner {
|
|
88
|
+
constructor(html) {
|
|
89
|
+
this.tokens = [];
|
|
90
|
+
this.position = initPosition();
|
|
91
|
+
this.html = html;
|
|
92
|
+
}
|
|
93
|
+
scan() {
|
|
94
|
+
const { html, position } = this;
|
|
95
|
+
const len = html.length;
|
|
96
|
+
while (position.index < len) {
|
|
97
|
+
const start = position.index;
|
|
98
|
+
this.scanText();
|
|
99
|
+
if (position.index === start) {
|
|
100
|
+
const isComment = html.startsWith('!--', start + 1);
|
|
101
|
+
if (isComment) {
|
|
102
|
+
this.scanComment();
|
|
103
|
+
}
|
|
104
|
+
else {
|
|
105
|
+
const tagName = this.scanTag();
|
|
106
|
+
if (shouldBeIgnore(tagName)) {
|
|
107
|
+
this.scanSkipTag(tagName);
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
return this.tokens;
|
|
113
|
+
}
|
|
114
|
+
scanText() {
|
|
115
|
+
const type = 'text';
|
|
116
|
+
const { html, position } = this;
|
|
117
|
+
let textEnd = findTextEnd(html, position.index);
|
|
118
|
+
if (textEnd === position.index) {
|
|
119
|
+
return;
|
|
120
|
+
}
|
|
121
|
+
if (textEnd === -1) {
|
|
122
|
+
textEnd = html.length;
|
|
123
|
+
}
|
|
124
|
+
const start = copyPosition(position);
|
|
125
|
+
const content = html.slice(position.index, textEnd);
|
|
126
|
+
jumpPosition(position, html, textEnd);
|
|
127
|
+
const end = copyPosition(position);
|
|
128
|
+
this.tokens.push({ type, content, position: { start, end } });
|
|
129
|
+
}
|
|
130
|
+
scanComment() {
|
|
131
|
+
const type = 'comment';
|
|
132
|
+
const { html, position } = this;
|
|
133
|
+
const start = copyPosition(position);
|
|
134
|
+
feedPosition(position, html, 4); // "<!--".length
|
|
135
|
+
let contentEnd = html.indexOf('-->', position.index);
|
|
136
|
+
let commentEnd = contentEnd + 3; // "-->".length
|
|
137
|
+
if (contentEnd === -1) {
|
|
138
|
+
contentEnd = commentEnd = html.length;
|
|
139
|
+
}
|
|
140
|
+
const content = html.slice(position.index, contentEnd);
|
|
141
|
+
jumpPosition(position, html, commentEnd);
|
|
142
|
+
this.tokens.push({
|
|
143
|
+
type,
|
|
144
|
+
content,
|
|
145
|
+
position: {
|
|
146
|
+
start,
|
|
147
|
+
end: copyPosition(position)
|
|
148
|
+
}
|
|
149
|
+
});
|
|
150
|
+
}
|
|
151
|
+
scanTag() {
|
|
152
|
+
this.scanTagStart();
|
|
153
|
+
const tagName = this.scanTagName();
|
|
154
|
+
this.scanAttrs();
|
|
155
|
+
this.scanTagEnd();
|
|
156
|
+
return tagName;
|
|
157
|
+
}
|
|
158
|
+
scanTagStart() {
|
|
159
|
+
const type = 'tag-start';
|
|
160
|
+
const { html, position } = this;
|
|
161
|
+
const secondChar = html.charAt(position.index + 1);
|
|
162
|
+
const close = secondChar === '/';
|
|
163
|
+
const start = copyPosition(position);
|
|
164
|
+
feedPosition(position, html, close ? 2 : 1);
|
|
165
|
+
this.tokens.push({ type, close, position: { start } });
|
|
166
|
+
}
|
|
167
|
+
scanTagEnd() {
|
|
168
|
+
const type = 'tag-end';
|
|
169
|
+
const { html, position } = this;
|
|
170
|
+
const firstChar = html.charAt(position.index);
|
|
171
|
+
const close = firstChar === '/';
|
|
172
|
+
feedPosition(position, html, close ? 2 : 1);
|
|
173
|
+
const end = copyPosition(position);
|
|
174
|
+
this.tokens.push({ type, close, position: { end } });
|
|
175
|
+
}
|
|
176
|
+
scanTagName() {
|
|
177
|
+
const type = 'tag';
|
|
178
|
+
const { html, position } = this;
|
|
179
|
+
const len = html.length;
|
|
180
|
+
let start = position.index;
|
|
181
|
+
while (start < len) {
|
|
182
|
+
const char = html.charAt(start);
|
|
183
|
+
const isTagChar = !(isWhitespaceChar(char) || char === '/' || char === '>');
|
|
184
|
+
if (isTagChar)
|
|
185
|
+
break;
|
|
186
|
+
start++;
|
|
187
|
+
}
|
|
188
|
+
let end = start + 1;
|
|
189
|
+
while (end < len) {
|
|
190
|
+
const char = html.charAt(end);
|
|
191
|
+
const isTagChar = !(isWhitespaceChar(char) || char === '/' || char === '>');
|
|
192
|
+
if (!isTagChar)
|
|
193
|
+
break;
|
|
194
|
+
end++;
|
|
195
|
+
}
|
|
196
|
+
jumpPosition(position, html, end);
|
|
197
|
+
const tagName = html.slice(start, end);
|
|
198
|
+
this.tokens.push({
|
|
199
|
+
type,
|
|
200
|
+
content: tagName
|
|
201
|
+
});
|
|
202
|
+
return tagName;
|
|
203
|
+
}
|
|
204
|
+
scanAttrs() {
|
|
205
|
+
const { html, position, tokens } = this;
|
|
206
|
+
let cursor = position.index;
|
|
207
|
+
let quote = null; // null, single-, or double-quote
|
|
208
|
+
let wordBegin = cursor; // index of word start
|
|
209
|
+
const words = []; // "key", "key=value", "key='value'", etc
|
|
210
|
+
const len = html.length;
|
|
211
|
+
while (cursor < len) {
|
|
212
|
+
const char = html.charAt(cursor);
|
|
213
|
+
if (quote) {
|
|
214
|
+
const isQuoteEnd = char === quote;
|
|
215
|
+
if (isQuoteEnd) {
|
|
216
|
+
quote = null;
|
|
217
|
+
}
|
|
218
|
+
cursor++;
|
|
219
|
+
continue;
|
|
220
|
+
}
|
|
221
|
+
const isTagEnd = char === '/' || char === '>';
|
|
222
|
+
if (isTagEnd) {
|
|
223
|
+
if (cursor !== wordBegin) {
|
|
224
|
+
words.push(html.slice(wordBegin, cursor));
|
|
225
|
+
}
|
|
226
|
+
break;
|
|
227
|
+
}
|
|
228
|
+
if (isWordEnd(cursor, wordBegin, html)) {
|
|
229
|
+
if (cursor !== wordBegin) {
|
|
230
|
+
words.push(html.slice(wordBegin, cursor));
|
|
231
|
+
}
|
|
232
|
+
wordBegin = cursor + 1;
|
|
233
|
+
cursor++;
|
|
234
|
+
continue;
|
|
235
|
+
}
|
|
236
|
+
const isQuoteStart = char === '\'' || char === '"';
|
|
237
|
+
if (isQuoteStart) {
|
|
238
|
+
quote = char;
|
|
239
|
+
cursor++;
|
|
240
|
+
continue;
|
|
241
|
+
}
|
|
242
|
+
cursor++;
|
|
243
|
+
}
|
|
244
|
+
jumpPosition(position, html, cursor);
|
|
245
|
+
const wLen = words.length;
|
|
246
|
+
const type = 'attribute';
|
|
247
|
+
for (let i = 0; i < wLen; i++) {
|
|
248
|
+
const word = words[i];
|
|
249
|
+
const isNotPair = word.includes('=');
|
|
250
|
+
if (isNotPair) {
|
|
251
|
+
const secondWord = words[i + 1];
|
|
252
|
+
if (secondWord && secondWord.startsWith('=')) {
|
|
253
|
+
if (secondWord.length > 1) {
|
|
254
|
+
const newWord = word + secondWord;
|
|
255
|
+
tokens.push({ type, content: newWord });
|
|
256
|
+
i += 1;
|
|
257
|
+
continue;
|
|
258
|
+
}
|
|
259
|
+
const thirdWord = words[i + 2];
|
|
260
|
+
i += 1;
|
|
261
|
+
if (thirdWord) {
|
|
262
|
+
const newWord = word + '=' + thirdWord;
|
|
263
|
+
tokens.push({ type, content: newWord });
|
|
264
|
+
i += 1;
|
|
265
|
+
continue;
|
|
266
|
+
}
|
|
267
|
+
}
|
|
268
|
+
}
|
|
269
|
+
if (word.endsWith('=')) {
|
|
270
|
+
const secondWord = words[i + 1];
|
|
271
|
+
if (secondWord && !secondWord.includes('=')) {
|
|
272
|
+
const newWord = word + secondWord;
|
|
273
|
+
tokens.push({ type, content: newWord });
|
|
274
|
+
i += 1;
|
|
275
|
+
continue;
|
|
276
|
+
}
|
|
277
|
+
const newWord = word.slice(0, -1);
|
|
278
|
+
tokens.push({ type, content: newWord });
|
|
279
|
+
continue;
|
|
280
|
+
}
|
|
281
|
+
tokens.push({ type, content: word });
|
|
282
|
+
}
|
|
283
|
+
}
|
|
284
|
+
scanSkipTag(tagName) {
|
|
285
|
+
const { html, position } = this;
|
|
286
|
+
const safeTagName = tagName.toLowerCase();
|
|
287
|
+
const len = html.length;
|
|
288
|
+
while (position.index < len) {
|
|
289
|
+
const nextTag = html.indexOf('</', position.index);
|
|
290
|
+
if (nextTag === -1) {
|
|
291
|
+
this.scanText();
|
|
292
|
+
break;
|
|
293
|
+
}
|
|
294
|
+
jumpPosition(position, html, nextTag);
|
|
295
|
+
const name = this.scanTag();
|
|
296
|
+
if (safeTagName === name.toLowerCase()) {
|
|
297
|
+
break;
|
|
298
|
+
}
|
|
299
|
+
}
|
|
300
|
+
}
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
export { Scaner };
|
|
304
|
+
//# sourceMappingURL=scaner.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"scaner.js","sources":["../../../src/dom-external/inner-html/scaner.ts"],"sourcesContent":["import { options } from '../../options'\n\ninterface Position {\n index: number\n column: number\n line: number\n}\n\nexport interface Token {\n type: string\n content?: string\n position?: {\n start?: Position\n end?: Position\n }\n close?: boolean\n}\n\nfunction initPosition (): Position {\n return {\n index: 0,\n column: 0,\n line: 0\n }\n}\n\nfunction feedPosition (position: Position, str: string, len: number) {\n const start = position.index\n const end = position.index = start + len\n for (let i = start; i < end; i++) {\n const char = str.charAt(i)\n if (char === '\\n') {\n position.line++\n position.column = 0\n } else {\n position.column++\n }\n }\n}\n\nfunction jumpPosition (position: Position, str: string, end: number) {\n const len = end - position.index\n return feedPosition(position, str, len)\n}\n\nfunction copyPosition (position: Position) {\n return {\n index: position.index,\n line: position.line,\n column: position.column\n }\n}\n\nconst whitespace = /\\s/\nfunction isWhitespaceChar (char: string) {\n return whitespace.test(char)\n}\n\nconst equalSign = /=/\nfunction isEqualSignChar (char: string) {\n return equalSign.test(char)\n}\n\nfunction shouldBeIgnore (tagName: string) {\n const name = tagName.toLowerCase()\n if (options.html!.skipElements.has(name)) {\n return true\n }\n return false\n}\n\nconst alphanumeric = /[A-Za-z0-9]/\n\nfunction findTextEnd (str: string, index: number) {\n while (true) {\n const textEnd = str.indexOf('<', index)\n if (textEnd === -1) {\n return textEnd\n }\n const char = str.charAt(textEnd + 1)\n if (char === '/' || char === '!' || alphanumeric.test(char)) {\n return textEnd\n }\n index = textEnd + 1\n }\n}\n\nfunction isWordEnd (cursor: number, wordBegin: number, html: string) {\n if (!isWhitespaceChar(html.charAt(cursor))) return false\n\n const len = html.length\n\n // backwrad\n for (let i = cursor - 1; i > wordBegin; i--) {\n const char = html.charAt(i)\n if (!isWhitespaceChar(char)) {\n if (isEqualSignChar(char)) return false\n break\n }\n }\n\n // forward\n for (let i = cursor + 1; i < len; i++) {\n const char = html.charAt(i)\n if (!isWhitespaceChar(char)) {\n if (isEqualSignChar(char)) return false\n return true\n }\n }\n}\n\nexport class Scaner {\n private tokens: Token[] = []\n\n private position: Position = initPosition()\n\n private html: string\n\n constructor (html: string) {\n this.html = html\n }\n\n public scan (): Token[] {\n const { html, position } = this\n const len = html.length\n\n while (position.index < len) {\n const start = position.index\n this.scanText()\n if (position.index === start) {\n const isComment = html.startsWith('!--', start + 1)\n if (isComment) {\n this.scanComment()\n } else {\n const tagName = this.scanTag()\n if (shouldBeIgnore(tagName)) {\n this.scanSkipTag(tagName)\n }\n }\n }\n }\n\n return this.tokens\n }\n\n private scanText () {\n const type = 'text'\n const { html, position } = this\n let textEnd = findTextEnd(html, position.index)\n if (textEnd === position.index) {\n return\n }\n if (textEnd === -1) {\n textEnd = html.length\n }\n\n const start = copyPosition(position)\n const content = html.slice(position.index, textEnd)\n jumpPosition(position, html, textEnd)\n const end = copyPosition(position)\n this.tokens.push({ type, content, position: { start, end } })\n }\n\n private scanComment () {\n const type = 'comment'\n const { html, position } = this\n const start = copyPosition(position)\n feedPosition(position, html, 4) // \"<!--\".length\n let contentEnd = html.indexOf('-->', position.index)\n let commentEnd = contentEnd + 3 // \"-->\".length\n if (contentEnd === -1) {\n contentEnd = commentEnd = html.length\n }\n\n const content = html.slice(position.index, contentEnd)\n jumpPosition(position, html, commentEnd)\n this.tokens.push({\n type,\n content,\n position: {\n start,\n end: copyPosition(position)\n }\n })\n }\n\n private scanTag () {\n this.scanTagStart()\n const tagName = this.scanTagName()\n this.scanAttrs()\n this.scanTagEnd()\n\n return tagName\n }\n\n private scanTagStart () {\n const type = 'tag-start'\n const { html, position } = this\n\n const secondChar = html.charAt(position.index + 1)\n const close = secondChar === '/'\n const start = copyPosition(position)\n feedPosition(position, html, close ? 2 : 1)\n this.tokens.push({ type, close, position: { start } })\n }\n\n private scanTagEnd () {\n const type = 'tag-end'\n const { html, position } = this\n\n const firstChar = html.charAt(position.index)\n const close = firstChar === '/'\n feedPosition(position, html, close ? 2 : 1)\n const end = copyPosition(position)\n this.tokens.push({ type, close, position: { end } })\n }\n\n private scanTagName (): string {\n const type = 'tag'\n const { html, position } = this\n const len = html.length\n let start = position.index\n while (start < len) {\n const char = html.charAt(start)\n const isTagChar = !(isWhitespaceChar(char) || char === '/' || char === '>')\n if (isTagChar) break\n start++\n }\n\n let end = start + 1\n while (end < len) {\n const char = html.charAt(end)\n const isTagChar = !(isWhitespaceChar(char) || char === '/' || char === '>')\n if (!isTagChar) break\n end++\n }\n\n jumpPosition(position, html, end)\n const tagName = html.slice(start, end)\n this.tokens.push({\n type,\n content: tagName\n })\n\n return tagName\n }\n\n private scanAttrs () {\n const { html, position, tokens } = this\n let cursor = position.index\n let quote: string | null = null // null, single-, or double-quote\n let wordBegin = cursor // index of word start\n const words: string[] = [] // \"key\", \"key=value\", \"key='value'\", etc\n const len = html.length\n while (cursor < len) {\n const char = html.charAt(cursor)\n if (quote) {\n const isQuoteEnd = char === quote\n if (isQuoteEnd) {\n quote = null\n }\n cursor++\n continue\n }\n\n const isTagEnd = char === '/' || char === '>'\n if (isTagEnd) {\n if (cursor !== wordBegin) {\n words.push(html.slice(wordBegin, cursor))\n }\n break\n }\n\n if (isWordEnd(cursor, wordBegin, html)) {\n if (cursor !== wordBegin) {\n words.push(html.slice(wordBegin, cursor))\n }\n wordBegin = cursor + 1\n cursor++\n continue\n }\n\n const isQuoteStart = char === '\\'' || char === '\"'\n if (isQuoteStart) {\n quote = char\n cursor++\n continue\n }\n\n cursor++\n }\n\n jumpPosition(position, html, cursor)\n\n const wLen = words.length\n const type = 'attribute'\n for (let i = 0; i < wLen; i++) {\n const word = words[i]\n const isNotPair = word.includes('=')\n if (isNotPair) {\n const secondWord = words[i + 1]\n if (secondWord && secondWord.startsWith('=')) {\n if (secondWord.length > 1) {\n const newWord = word + secondWord\n tokens.push({ type, content: newWord })\n i += 1\n continue\n }\n const thirdWord = words[i + 2]\n i += 1\n if (thirdWord) {\n const newWord = word + '=' + thirdWord\n tokens.push({ type, content: newWord })\n i += 1\n continue\n }\n }\n }\n if (word.endsWith('=')) {\n const secondWord = words[i + 1]\n if (secondWord && !secondWord.includes('=')) {\n const newWord = word + secondWord\n tokens.push({ type, content: newWord })\n i += 1\n continue\n }\n\n const newWord = word.slice(0, -1)\n tokens.push({ type, content: newWord })\n continue\n }\n\n tokens.push({ type, content: word })\n }\n }\n\n private scanSkipTag (tagName: string) {\n const { html, position } = this\n const safeTagName = tagName.toLowerCase()\n const len = html.length\n while (position.index < len) {\n const nextTag = html.indexOf('</', position.index)\n if (nextTag === -1) {\n this.scanText()\n break\n }\n\n jumpPosition(position, html, nextTag)\n const name = this.scanTag()\n if (safeTagName === name.toLowerCase()) {\n break\n }\n }\n }\n}\n"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import { ParsedTaroElement } from "./parser.js";
|
|
2
|
+
interface ISelector {
|
|
3
|
+
isChild: boolean;
|
|
4
|
+
isGeneralSibling: boolean;
|
|
5
|
+
isAdjacentSibling: boolean;
|
|
6
|
+
tag: string | null;
|
|
7
|
+
id: string | null;
|
|
8
|
+
class: string[];
|
|
9
|
+
attrs: {
|
|
10
|
+
all: boolean;
|
|
11
|
+
key: string;
|
|
12
|
+
value?: string | null;
|
|
13
|
+
}[];
|
|
14
|
+
}
|
|
15
|
+
interface IStyle {
|
|
16
|
+
content: string;
|
|
17
|
+
selectorList: ISelector[];
|
|
18
|
+
}
|
|
19
|
+
declare class StyleTagParser {
|
|
20
|
+
styles: IStyle[];
|
|
21
|
+
extractStyle(src: string): string;
|
|
22
|
+
stringToSelector(style: string): void;
|
|
23
|
+
parseSelector(src: string): ISelector[];
|
|
24
|
+
matchStyle(tagName: string, el: ParsedTaroElement, list: number[]): string;
|
|
25
|
+
matchCurrent(tagName: string, el: ParsedTaroElement, selector: ISelector): boolean;
|
|
26
|
+
}
|
|
27
|
+
export { StyleTagParser as default };
|
|
@@ -0,0 +1,235 @@
|
|
|
1
|
+
import { unquote } from './utils.js';
|
|
2
|
+
|
|
3
|
+
const LEFT_BRACKET = '{';
|
|
4
|
+
const RIGHT_BRACKET = '}';
|
|
5
|
+
const CLASS_SELECTOR = '.';
|
|
6
|
+
const ID_SELECTOR = '#';
|
|
7
|
+
const CHILD_COMBINATOR = '>';
|
|
8
|
+
const GENERAL_SIBLING_COMBINATOR = '~';
|
|
9
|
+
const ADJACENT_SIBLING_COMBINATOR = '+';
|
|
10
|
+
class StyleTagParser {
|
|
11
|
+
constructor() {
|
|
12
|
+
this.styles = [];
|
|
13
|
+
}
|
|
14
|
+
extractStyle(src) {
|
|
15
|
+
const REG_STYLE = /<style\s?[^>]*>((.|\n|\s)+?)<\/style>/g;
|
|
16
|
+
let html = src;
|
|
17
|
+
// let html = src.replace(/\n/g, '')
|
|
18
|
+
html = html.replace(REG_STYLE, (_, $1) => {
|
|
19
|
+
const style = $1.trim();
|
|
20
|
+
this.stringToSelector(style);
|
|
21
|
+
return '';
|
|
22
|
+
});
|
|
23
|
+
return html.trim();
|
|
24
|
+
}
|
|
25
|
+
stringToSelector(style) {
|
|
26
|
+
let lb = style.indexOf(LEFT_BRACKET);
|
|
27
|
+
while (lb > -1) {
|
|
28
|
+
const rb = style.indexOf(RIGHT_BRACKET);
|
|
29
|
+
const selectors = style.slice(0, lb).trim();
|
|
30
|
+
let content = style.slice(lb + 1, rb);
|
|
31
|
+
content = content.replace(/:(.*);/g, function (_, $1) {
|
|
32
|
+
const t = $1.trim().replace(/ +/g, '+++');
|
|
33
|
+
return `:${t};`;
|
|
34
|
+
});
|
|
35
|
+
content = content.replace(/ /g, '');
|
|
36
|
+
content = content.replace(/\+\+\+/g, ' ');
|
|
37
|
+
if (!(/;$/.test(content))) {
|
|
38
|
+
content += ';';
|
|
39
|
+
}
|
|
40
|
+
selectors.split(',').forEach(src => {
|
|
41
|
+
const selectorList = this.parseSelector(src);
|
|
42
|
+
this.styles.push({
|
|
43
|
+
content,
|
|
44
|
+
selectorList
|
|
45
|
+
});
|
|
46
|
+
});
|
|
47
|
+
style = style.slice(rb + 1);
|
|
48
|
+
lb = style.indexOf(LEFT_BRACKET);
|
|
49
|
+
}
|
|
50
|
+
// console.log('res this.styles: ', this.styles)
|
|
51
|
+
}
|
|
52
|
+
parseSelector(src) {
|
|
53
|
+
const list = src
|
|
54
|
+
.trim()
|
|
55
|
+
.replace(/ *([>~+]) */g, ' $1')
|
|
56
|
+
.replace(/ +/g, ' ')
|
|
57
|
+
.replace(/\[\s*([^[\]=\s]+)\s*=\s*([^[\]=\s]+)\s*\]/g, '[$1=$2]')
|
|
58
|
+
.split(' ');
|
|
59
|
+
const selectors = list.map(item => {
|
|
60
|
+
const firstChar = item.charAt(0);
|
|
61
|
+
const selector = {
|
|
62
|
+
isChild: firstChar === CHILD_COMBINATOR,
|
|
63
|
+
isGeneralSibling: firstChar === GENERAL_SIBLING_COMBINATOR,
|
|
64
|
+
isAdjacentSibling: firstChar === ADJACENT_SIBLING_COMBINATOR,
|
|
65
|
+
tag: null,
|
|
66
|
+
id: null,
|
|
67
|
+
class: [],
|
|
68
|
+
attrs: []
|
|
69
|
+
};
|
|
70
|
+
item = item.replace(/^[>~+]/, '');
|
|
71
|
+
// 属性选择器
|
|
72
|
+
item = item.replace(/\[(.+?)\]/g, function (_, $1) {
|
|
73
|
+
const [key, value] = $1.split('=');
|
|
74
|
+
const all = $1.indexOf('=') === -1;
|
|
75
|
+
const attr = {
|
|
76
|
+
all,
|
|
77
|
+
key,
|
|
78
|
+
value: all ? null : value
|
|
79
|
+
};
|
|
80
|
+
selector.attrs.push(attr);
|
|
81
|
+
return '';
|
|
82
|
+
});
|
|
83
|
+
item = item.replace(/([.#][A-Za-z0-9-_]+)/g, function (_, $1) {
|
|
84
|
+
if ($1[0] === ID_SELECTOR) {
|
|
85
|
+
// id 选择器
|
|
86
|
+
selector.id = $1.substr(1);
|
|
87
|
+
}
|
|
88
|
+
else if ($1[0] === CLASS_SELECTOR) {
|
|
89
|
+
// class 选择器
|
|
90
|
+
selector.class.push($1.substr(1));
|
|
91
|
+
}
|
|
92
|
+
return '';
|
|
93
|
+
});
|
|
94
|
+
// 标签选择器
|
|
95
|
+
if (item !== '') {
|
|
96
|
+
selector.tag = item;
|
|
97
|
+
}
|
|
98
|
+
return selector;
|
|
99
|
+
});
|
|
100
|
+
return selectors;
|
|
101
|
+
}
|
|
102
|
+
matchStyle(tagName, el, list) {
|
|
103
|
+
const res = sortStyles(this.styles).reduce((str, { content, selectorList }, i) => {
|
|
104
|
+
let idx = list[i];
|
|
105
|
+
let selector = selectorList[idx];
|
|
106
|
+
const nextSelector = selectorList[idx + 1];
|
|
107
|
+
if ((nextSelector === null || nextSelector === void 0 ? void 0 : nextSelector.isGeneralSibling) || (nextSelector === null || nextSelector === void 0 ? void 0 : nextSelector.isAdjacentSibling)) {
|
|
108
|
+
selector = nextSelector;
|
|
109
|
+
idx += 1;
|
|
110
|
+
list[i] += 1;
|
|
111
|
+
}
|
|
112
|
+
let isMatch = this.matchCurrent(tagName, el, selector);
|
|
113
|
+
if (isMatch && selector.isGeneralSibling) {
|
|
114
|
+
let prev = getPreviousElement(el);
|
|
115
|
+
while (prev) {
|
|
116
|
+
if (prev.h5tagName && this.matchCurrent(prev.h5tagName, prev, selectorList[idx - 1])) {
|
|
117
|
+
isMatch = true;
|
|
118
|
+
break;
|
|
119
|
+
}
|
|
120
|
+
prev = getPreviousElement(prev);
|
|
121
|
+
isMatch = false;
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
if (isMatch && selector.isAdjacentSibling) {
|
|
125
|
+
const prev = getPreviousElement(el);
|
|
126
|
+
if (!prev || !prev.h5tagName) {
|
|
127
|
+
isMatch = false;
|
|
128
|
+
}
|
|
129
|
+
else {
|
|
130
|
+
const isSiblingMatch = this.matchCurrent(prev.h5tagName, prev, selectorList[idx - 1]);
|
|
131
|
+
if (!isSiblingMatch) {
|
|
132
|
+
isMatch = false;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
}
|
|
136
|
+
if (isMatch) {
|
|
137
|
+
if (idx === selectorList.length - 1) {
|
|
138
|
+
return str + content;
|
|
139
|
+
}
|
|
140
|
+
else if (idx < selectorList.length - 1) {
|
|
141
|
+
list[i] += 1;
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
else {
|
|
145
|
+
// 直接子代组合器: >
|
|
146
|
+
if (selector.isChild && idx > 0) {
|
|
147
|
+
list[i] -= 1;
|
|
148
|
+
if (this.matchCurrent(tagName, el, selectorList[list[i]])) {
|
|
149
|
+
list[i] += 1;
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
}
|
|
153
|
+
return str;
|
|
154
|
+
}, '');
|
|
155
|
+
return res;
|
|
156
|
+
}
|
|
157
|
+
matchCurrent(tagName, el, selector) {
|
|
158
|
+
// 标签选择器
|
|
159
|
+
if (selector.tag && selector.tag !== tagName)
|
|
160
|
+
return false;
|
|
161
|
+
// id 选择器
|
|
162
|
+
if (selector.id && selector.id !== el.id)
|
|
163
|
+
return false;
|
|
164
|
+
// class 选择器
|
|
165
|
+
if (selector.class.length) {
|
|
166
|
+
const classList = el.className.split(' ');
|
|
167
|
+
for (let i = 0; i < selector.class.length; i++) {
|
|
168
|
+
const cls = selector.class[i];
|
|
169
|
+
if (classList.indexOf(cls) === -1) {
|
|
170
|
+
return false;
|
|
171
|
+
}
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
// 属性选择器
|
|
175
|
+
if (selector.attrs.length) {
|
|
176
|
+
for (let i = 0; i < selector.attrs.length; i++) {
|
|
177
|
+
const { all, key, value } = selector.attrs[i];
|
|
178
|
+
if (all && !el.hasAttribute(key)) {
|
|
179
|
+
return false;
|
|
180
|
+
}
|
|
181
|
+
else {
|
|
182
|
+
const attr = el.getAttribute(key);
|
|
183
|
+
if (attr !== unquote(value || '')) {
|
|
184
|
+
return false;
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
}
|
|
188
|
+
}
|
|
189
|
+
return true;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
function getPreviousElement(el) {
|
|
193
|
+
const parent = el.parentElement;
|
|
194
|
+
if (!parent)
|
|
195
|
+
return null;
|
|
196
|
+
const prev = el.previousSibling;
|
|
197
|
+
if (!prev)
|
|
198
|
+
return null;
|
|
199
|
+
if (prev.nodeType === 1 /* NodeType.ELEMENT_NODE */) {
|
|
200
|
+
return prev;
|
|
201
|
+
}
|
|
202
|
+
else {
|
|
203
|
+
return getPreviousElement(prev);
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
// 根据 css selector 权重排序: 权重大的靠后
|
|
207
|
+
// @WARN 不考虑伪类
|
|
208
|
+
// https://developer.mozilla.org/en-US/docs/Learn/CSS/Building_blocks/Cascade_and_inheritance#specificity_2
|
|
209
|
+
function sortStyles(styles) {
|
|
210
|
+
return styles.sort((s1, s2) => {
|
|
211
|
+
const hundreds1 = getHundredsWeight(s1.selectorList);
|
|
212
|
+
const hundreds2 = getHundredsWeight(s2.selectorList);
|
|
213
|
+
if (hundreds1 !== hundreds2)
|
|
214
|
+
return hundreds1 - hundreds2;
|
|
215
|
+
const tens1 = getTensWeight(s1.selectorList);
|
|
216
|
+
const tens2 = getTensWeight(s2.selectorList);
|
|
217
|
+
if (tens1 !== tens2)
|
|
218
|
+
return tens1 - tens2;
|
|
219
|
+
const ones1 = getOnesWeight(s1.selectorList);
|
|
220
|
+
const ones2 = getOnesWeight(s2.selectorList);
|
|
221
|
+
return ones1 - ones2;
|
|
222
|
+
});
|
|
223
|
+
}
|
|
224
|
+
function getHundredsWeight(selectors) {
|
|
225
|
+
return selectors.reduce((pre, cur) => pre + (cur.id ? 1 : 0), 0);
|
|
226
|
+
}
|
|
227
|
+
function getTensWeight(selectors) {
|
|
228
|
+
return selectors.reduce((pre, cur) => pre + cur.class.length + cur.attrs.length, 0);
|
|
229
|
+
}
|
|
230
|
+
function getOnesWeight(selectors) {
|
|
231
|
+
return selectors.reduce((pre, cur) => pre + (cur.tag ? 1 : 0), 0);
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
export { StyleTagParser as default };
|
|
235
|
+
//# sourceMappingURL=style.js.map
|