1 |
|
2 |
|
3 |
|
4 |
|
5 | export class CSSNativeScript {
|
6 | parseStylesheet(stylesheet) {
|
7 | return {
|
8 | type: 'stylesheet',
|
9 | stylesheet: {
|
10 | rules: this.parseRules(stylesheet.rules),
|
11 | },
|
12 | };
|
13 | }
|
14 | parseRules(rules) {
|
15 | return rules.map((rule) => this.parseRule(rule));
|
16 | }
|
17 | parseRule(rule) {
|
18 | if (rule.type === 'at-rule') {
|
19 | return this.parseAtRule(rule);
|
20 | }
|
21 | else if (rule.type === 'qualified-rule') {
|
22 | return this.parseQualifiedRule(rule);
|
23 | }
|
24 | }
|
25 | parseAtRule(rule) {
|
26 | if (rule.name === 'import') {
|
27 |
|
28 | return {
|
29 | import: rule.prelude
|
30 | .map((m) => (typeof m === 'string' ? m : m.text))
|
31 | .join('')
|
32 | .trim(),
|
33 | type: 'import',
|
34 | };
|
35 | }
|
36 | return;
|
37 | }
|
38 | parseQualifiedRule(rule) {
|
39 | return {
|
40 | type: 'rule',
|
41 | selectors: this.preludeToSelectorsStringArray(rule.prelude),
|
42 | declarations: this.ruleBlockToDeclarations(rule.block.values),
|
43 | };
|
44 | }
|
45 | ruleBlockToDeclarations(declarationsInputTokens) {
|
46 |
|
47 | const declarations = [];
|
48 | let property = '';
|
49 | let value = '';
|
50 | let reading = 'property';
|
51 | for (let i = 0; i < declarationsInputTokens.length; i++) {
|
52 | const inputToken = declarationsInputTokens[i];
|
53 | if (reading === 'property') {
|
54 | if (inputToken === ':') {
|
55 | reading = 'value';
|
56 | }
|
57 | else if (typeof inputToken === 'string') {
|
58 | property += inputToken;
|
59 | }
|
60 | else {
|
61 | property += inputToken.text;
|
62 | }
|
63 | }
|
64 | else {
|
65 | if (inputToken === ';') {
|
66 | property = property.trim();
|
67 | value = value.trim();
|
68 | declarations.push({ type: 'declaration', property, value });
|
69 | property = '';
|
70 | value = '';
|
71 | reading = 'property';
|
72 | }
|
73 | else if (typeof inputToken === 'string') {
|
74 | value += inputToken;
|
75 | }
|
76 | else {
|
77 | value += inputToken.text;
|
78 | }
|
79 | }
|
80 | }
|
81 | property = property.trim();
|
82 | value = value.trim();
|
83 | if (property || value) {
|
84 | declarations.push({ type: 'declaration', property, value });
|
85 | }
|
86 | return declarations;
|
87 | }
|
88 | preludeToSelectorsStringArray(prelude) {
|
89 | const selectors = [];
|
90 | let selector = '';
|
91 | prelude.forEach((inputToken) => {
|
92 | if (typeof inputToken === 'string') {
|
93 | if (inputToken === ',') {
|
94 | if (selector) {
|
95 | selectors.push(selector.trim());
|
96 | }
|
97 | selector = '';
|
98 | }
|
99 | else {
|
100 | selector += inputToken;
|
101 | }
|
102 | }
|
103 | else if (typeof inputToken === 'object') {
|
104 | selector += inputToken.text;
|
105 | }
|
106 | });
|
107 | if (selector) {
|
108 | selectors.push(selector.trim());
|
109 | }
|
110 | return selectors;
|
111 | }
|
112 | }
|
113 |
|
\ | No newline at end of file |