style-to-object 0.2.0 → 0.3.0
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/CHANGELOG.md +56 -1
- package/README.md +98 -34
- package/dist/style-to-object.js +251 -590
- package/dist/style-to-object.min.js +2 -1
- package/dist/style-to-object.min.js.map +1 -0
- package/index.d.ts +38 -0
- package/index.js +17 -11
- package/package.json +40 -22
package/dist/style-to-object.js
CHANGED
|
@@ -1,647 +1,308 @@
|
|
|
1
1
|
(function (global, factory) {
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
2
|
+
typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() :
|
|
3
|
+
typeof define === 'function' && define.amd ? define(factory) :
|
|
4
|
+
(global = global || self, global.StyleToObject = factory());
|
|
5
5
|
}(this, (function () { 'use strict';
|
|
6
6
|
|
|
7
|
-
// http://www.w3.org/TR/CSS21/grammar.html
|
|
8
|
-
// https://github.com/visionmedia/css-parse/pull/49#issuecomment-30088027
|
|
9
|
-
var
|
|
7
|
+
// http://www.w3.org/TR/CSS21/grammar.html
|
|
8
|
+
// https://github.com/visionmedia/css-parse/pull/49#issuecomment-30088027
|
|
9
|
+
var COMMENT_REGEX = /\/\*[^*]*\*+([^/*][^*]*\*+)*\//g;
|
|
10
10
|
|
|
11
|
-
var
|
|
12
|
-
|
|
11
|
+
var NEWLINE_REGEX = /\n/g;
|
|
12
|
+
var WHITESPACE_REGEX = /^\s*/;
|
|
13
13
|
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
14
|
+
// declaration
|
|
15
|
+
var PROPERTY_REGEX = /^(\*?[-#/*\\\w]+(\[[0-9a-z_-]+\])?)\s*/;
|
|
16
|
+
var COLON_REGEX = /^:\s*/;
|
|
17
|
+
var VALUE_REGEX = /^((?:'(?:\\'|.)*?'|"(?:\\"|.)*?"|\([^)]*?\)|[^};])+)/;
|
|
18
|
+
var SEMICOLON_REGEX = /^[;\s]*/;
|
|
17
19
|
|
|
18
|
-
|
|
19
|
-
var
|
|
20
|
-
|
|
21
|
-
/**
|
|
22
|
-
* Update lineno and column based on `str`.
|
|
23
|
-
*/
|
|
24
|
-
|
|
25
|
-
function updatePosition(str) {
|
|
26
|
-
var lines = str.match(/\n/g);
|
|
27
|
-
if (lines) lineno += lines.length;
|
|
28
|
-
var i = str.lastIndexOf('\n');
|
|
29
|
-
column = ~i ? str.length - i : column + str.length;
|
|
30
|
-
}
|
|
20
|
+
// https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/String/Trim#Polyfill
|
|
21
|
+
var TRIM_REGEX = /^\s+|\s+$/g;
|
|
31
22
|
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
23
|
+
// strings
|
|
24
|
+
var NEWLINE = '\n';
|
|
25
|
+
var FORWARD_SLASH = '/';
|
|
26
|
+
var ASTERISK = '*';
|
|
27
|
+
var EMPTY_STRING = '';
|
|
35
28
|
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
node.position = new Position(start);
|
|
40
|
-
whitespace();
|
|
41
|
-
return node;
|
|
42
|
-
};
|
|
43
|
-
}
|
|
29
|
+
// types
|
|
30
|
+
var TYPE_COMMENT = 'comment';
|
|
31
|
+
var TYPE_DECLARATION = 'declaration';
|
|
44
32
|
|
|
45
33
|
/**
|
|
46
|
-
*
|
|
34
|
+
* @param {String} style
|
|
35
|
+
* @param {Object} [options]
|
|
36
|
+
* @return {Object[]}
|
|
37
|
+
* @throws {TypeError}
|
|
38
|
+
* @throws {Error}
|
|
47
39
|
*/
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
this.end = { line: lineno, column: column };
|
|
52
|
-
this.source = options.source;
|
|
53
|
-
}
|
|
54
|
-
|
|
55
|
-
/**
|
|
56
|
-
* Non-enumerable source string
|
|
57
|
-
*/
|
|
58
|
-
|
|
59
|
-
Position.prototype.content = css;
|
|
60
|
-
|
|
61
|
-
/**
|
|
62
|
-
* Error `msg`.
|
|
63
|
-
*/
|
|
64
|
-
|
|
65
|
-
var errorsList = [];
|
|
66
|
-
|
|
67
|
-
function error(msg) {
|
|
68
|
-
var err = new Error(options.source + ':' + lineno + ':' + column + ': ' + msg);
|
|
69
|
-
err.reason = msg;
|
|
70
|
-
err.filename = options.source;
|
|
71
|
-
err.line = lineno;
|
|
72
|
-
err.column = column;
|
|
73
|
-
err.source = css;
|
|
74
|
-
|
|
75
|
-
if (options.silent) {
|
|
76
|
-
errorsList.push(err);
|
|
77
|
-
} else {
|
|
78
|
-
throw err;
|
|
40
|
+
var inlineStyleParser = function(style, options) {
|
|
41
|
+
if (typeof style !== 'string') {
|
|
42
|
+
throw new TypeError('First argument must be a string');
|
|
79
43
|
}
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
/**
|
|
83
|
-
* Parse stylesheet.
|
|
84
|
-
*/
|
|
85
|
-
|
|
86
|
-
function stylesheet() {
|
|
87
|
-
var rulesList = rules();
|
|
88
44
|
|
|
89
|
-
return
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
function close() {
|
|
111
|
-
return match(/^}/);
|
|
112
|
-
}
|
|
113
|
-
|
|
114
|
-
/**
|
|
115
|
-
* Parse ruleset.
|
|
116
|
-
*/
|
|
117
|
-
|
|
118
|
-
function rules() {
|
|
119
|
-
var node;
|
|
120
|
-
var rules = [];
|
|
121
|
-
whitespace();
|
|
122
|
-
comments(rules);
|
|
123
|
-
while (css.length && css.charAt(0) != '}' && (node = atrule() || rule())) {
|
|
124
|
-
if (node !== false) {
|
|
125
|
-
rules.push(node);
|
|
126
|
-
comments(rules);
|
|
127
|
-
}
|
|
45
|
+
if (!style) return [];
|
|
46
|
+
|
|
47
|
+
options = options || {};
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Positional.
|
|
51
|
+
*/
|
|
52
|
+
var lineno = 1;
|
|
53
|
+
var column = 1;
|
|
54
|
+
|
|
55
|
+
/**
|
|
56
|
+
* Update lineno and column based on `str`.
|
|
57
|
+
*
|
|
58
|
+
* @param {String} str
|
|
59
|
+
*/
|
|
60
|
+
function updatePosition(str) {
|
|
61
|
+
var lines = str.match(NEWLINE_REGEX);
|
|
62
|
+
if (lines) lineno += lines.length;
|
|
63
|
+
var i = str.lastIndexOf(NEWLINE);
|
|
64
|
+
column = ~i ? str.length - i : column + str.length;
|
|
128
65
|
}
|
|
129
|
-
return rules;
|
|
130
|
-
}
|
|
131
66
|
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
/**
|
|
146
|
-
* Parse whitespace.
|
|
147
|
-
*/
|
|
148
|
-
|
|
149
|
-
function whitespace() {
|
|
150
|
-
match(/^\s*/);
|
|
151
|
-
}
|
|
67
|
+
/**
|
|
68
|
+
* Mark position and patch `node.position`.
|
|
69
|
+
*
|
|
70
|
+
* @return {Function}
|
|
71
|
+
*/
|
|
72
|
+
function position() {
|
|
73
|
+
var start = { line: lineno, column: column };
|
|
74
|
+
return function(node) {
|
|
75
|
+
node.position = new Position(start);
|
|
76
|
+
whitespace();
|
|
77
|
+
return node;
|
|
78
|
+
};
|
|
79
|
+
}
|
|
152
80
|
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
81
|
+
/**
|
|
82
|
+
* Store position information for a node.
|
|
83
|
+
*
|
|
84
|
+
* @constructor
|
|
85
|
+
* @property {Object} start
|
|
86
|
+
* @property {Object} end
|
|
87
|
+
* @property {undefined|String} source
|
|
88
|
+
*/
|
|
89
|
+
function Position(start) {
|
|
90
|
+
this.start = start;
|
|
91
|
+
this.end = { line: lineno, column: column };
|
|
92
|
+
this.source = options.source;
|
|
93
|
+
}
|
|
156
94
|
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
95
|
+
/**
|
|
96
|
+
* Non-enumerable source string.
|
|
97
|
+
*/
|
|
98
|
+
Position.prototype.content = style;
|
|
99
|
+
|
|
100
|
+
/**
|
|
101
|
+
* Error `msg`.
|
|
102
|
+
*
|
|
103
|
+
* @param {String} msg
|
|
104
|
+
* @throws {Error}
|
|
105
|
+
*/
|
|
106
|
+
function error(msg) {
|
|
107
|
+
var err = new Error(
|
|
108
|
+
options.source + ':' + lineno + ':' + column + ': ' + msg
|
|
109
|
+
);
|
|
110
|
+
err.reason = msg;
|
|
111
|
+
err.filename = options.source;
|
|
112
|
+
err.line = lineno;
|
|
113
|
+
err.column = column;
|
|
114
|
+
err.source = style;
|
|
115
|
+
|
|
116
|
+
if (options.silent) ; else {
|
|
117
|
+
throw err;
|
|
163
118
|
}
|
|
164
119
|
}
|
|
165
|
-
return rules;
|
|
166
|
-
}
|
|
167
120
|
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
return error('End of comment missing');
|
|
121
|
+
/**
|
|
122
|
+
* Match `re` and return captures.
|
|
123
|
+
*
|
|
124
|
+
* @param {RegExp} re
|
|
125
|
+
* @return {undefined|Array}
|
|
126
|
+
*/
|
|
127
|
+
function match(re) {
|
|
128
|
+
var m = re.exec(style);
|
|
129
|
+
if (!m) return;
|
|
130
|
+
var str = m[0];
|
|
131
|
+
updatePosition(str);
|
|
132
|
+
style = style.slice(str.length);
|
|
133
|
+
return m;
|
|
182
134
|
}
|
|
183
135
|
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
return pos({
|
|
191
|
-
type: 'comment',
|
|
192
|
-
comment: str
|
|
193
|
-
});
|
|
194
|
-
}
|
|
195
|
-
|
|
196
|
-
/**
|
|
197
|
-
* Parse selector.
|
|
198
|
-
*/
|
|
199
|
-
|
|
200
|
-
function selector() {
|
|
201
|
-
var m = match(/^([^{]+)/);
|
|
202
|
-
if (!m) return;
|
|
203
|
-
/* @fix Remove all comments from selectors
|
|
204
|
-
* http://ostermiller.org/findcomment.html */
|
|
205
|
-
return trim(m[0])
|
|
206
|
-
.replace(/\/\*([^*]|[\r\n]|(\*+([^*/]|[\r\n])))*\*\/+/g, '')
|
|
207
|
-
.replace(/"(?:\\"|[^"])*"|'(?:\\'|[^'])*'/g, function(m) {
|
|
208
|
-
return m.replace(/,/g, '\u200C');
|
|
209
|
-
})
|
|
210
|
-
.split(/\s*(?![^(]*\)),\s*/)
|
|
211
|
-
.map(function(s) {
|
|
212
|
-
return s.replace(/\u200C/g, ',');
|
|
213
|
-
});
|
|
214
|
-
}
|
|
215
|
-
|
|
216
|
-
/**
|
|
217
|
-
* Parse declaration.
|
|
218
|
-
*/
|
|
219
|
-
|
|
220
|
-
function declaration() {
|
|
221
|
-
var pos = position();
|
|
222
|
-
|
|
223
|
-
// prop
|
|
224
|
-
var prop = match(/^(\*?[-#\/\*\\\w]+(\[[0-9a-z_-]+\])?)\s*/);
|
|
225
|
-
if (!prop) return;
|
|
226
|
-
prop = trim(prop[0]);
|
|
227
|
-
|
|
228
|
-
// :
|
|
229
|
-
if (!match(/^:\s*/)) return error("property missing ':'");
|
|
230
|
-
|
|
231
|
-
// val
|
|
232
|
-
var val = match(/^((?:'(?:\\'|.)*?'|"(?:\\"|.)*?"|\([^\)]*?\)|[^};])+)/);
|
|
233
|
-
|
|
234
|
-
var ret = pos({
|
|
235
|
-
type: 'declaration',
|
|
236
|
-
property: prop.replace(commentre, ''),
|
|
237
|
-
value: val ? trim(val[0]).replace(commentre, '') : ''
|
|
238
|
-
});
|
|
239
|
-
|
|
240
|
-
// ;
|
|
241
|
-
match(/^[;\s]*/);
|
|
242
|
-
|
|
243
|
-
return ret;
|
|
244
|
-
}
|
|
245
|
-
|
|
246
|
-
/**
|
|
247
|
-
* Parse declarations.
|
|
248
|
-
*/
|
|
249
|
-
|
|
250
|
-
function declarations() {
|
|
251
|
-
var decls = [];
|
|
252
|
-
|
|
253
|
-
if (!open()) return error("missing '{'");
|
|
254
|
-
comments(decls);
|
|
136
|
+
/**
|
|
137
|
+
* Parse whitespace.
|
|
138
|
+
*/
|
|
139
|
+
function whitespace() {
|
|
140
|
+
match(WHITESPACE_REGEX);
|
|
141
|
+
}
|
|
255
142
|
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
143
|
+
/**
|
|
144
|
+
* Parse comments.
|
|
145
|
+
*
|
|
146
|
+
* @param {Object[]} [rules]
|
|
147
|
+
* @return {Object[]}
|
|
148
|
+
*/
|
|
149
|
+
function comments(rules) {
|
|
150
|
+
var c;
|
|
151
|
+
rules = rules || [];
|
|
152
|
+
while ((c = comment())) {
|
|
153
|
+
if (c !== false) {
|
|
154
|
+
rules.push(c);
|
|
155
|
+
}
|
|
262
156
|
}
|
|
157
|
+
return rules;
|
|
263
158
|
}
|
|
264
159
|
|
|
265
|
-
|
|
266
|
-
|
|
267
|
-
|
|
160
|
+
/**
|
|
161
|
+
* Parse comment.
|
|
162
|
+
*
|
|
163
|
+
* @return {Object}
|
|
164
|
+
* @throws {Error}
|
|
165
|
+
*/
|
|
166
|
+
function comment() {
|
|
167
|
+
var pos = position();
|
|
168
|
+
if (FORWARD_SLASH != style.charAt(0) || ASTERISK != style.charAt(1)) return;
|
|
169
|
+
|
|
170
|
+
var i = 2;
|
|
171
|
+
while (
|
|
172
|
+
EMPTY_STRING != style.charAt(i) &&
|
|
173
|
+
(ASTERISK != style.charAt(i) || FORWARD_SLASH != style.charAt(i + 1))
|
|
174
|
+
) {
|
|
175
|
+
++i;
|
|
176
|
+
}
|
|
177
|
+
i += 2;
|
|
268
178
|
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
179
|
+
if (EMPTY_STRING === style.charAt(i - 1)) {
|
|
180
|
+
return error('End of comment missing');
|
|
181
|
+
}
|
|
272
182
|
|
|
273
|
-
|
|
274
|
-
|
|
275
|
-
|
|
276
|
-
|
|
183
|
+
var str = style.slice(2, i - 2);
|
|
184
|
+
column += 2;
|
|
185
|
+
updatePosition(str);
|
|
186
|
+
style = style.slice(i);
|
|
187
|
+
column += 2;
|
|
277
188
|
|
|
278
|
-
|
|
279
|
-
|
|
280
|
-
|
|
189
|
+
return pos({
|
|
190
|
+
type: TYPE_COMMENT,
|
|
191
|
+
comment: str
|
|
192
|
+
});
|
|
281
193
|
}
|
|
282
194
|
|
|
283
|
-
|
|
284
|
-
|
|
285
|
-
|
|
286
|
-
|
|
287
|
-
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
195
|
+
/**
|
|
196
|
+
* Parse declaration.
|
|
197
|
+
*
|
|
198
|
+
* @return {Object}
|
|
199
|
+
* @throws {Error}
|
|
200
|
+
*/
|
|
201
|
+
function declaration() {
|
|
202
|
+
var pos = position();
|
|
291
203
|
|
|
292
|
-
|
|
293
|
-
|
|
294
|
-
|
|
204
|
+
// prop
|
|
205
|
+
var prop = match(PROPERTY_REGEX);
|
|
206
|
+
if (!prop) return;
|
|
207
|
+
comment();
|
|
295
208
|
|
|
296
|
-
|
|
297
|
-
|
|
298
|
-
var m = match(/^@([-\w]+)?keyframes\s*/);
|
|
209
|
+
// :
|
|
210
|
+
if (!match(COLON_REGEX)) return error("property missing ':'");
|
|
299
211
|
|
|
300
|
-
|
|
301
|
-
|
|
212
|
+
// val
|
|
213
|
+
var val = match(VALUE_REGEX);
|
|
302
214
|
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
215
|
+
var ret = pos({
|
|
216
|
+
type: TYPE_DECLARATION,
|
|
217
|
+
property: trim(prop[0].replace(COMMENT_REGEX, EMPTY_STRING)),
|
|
218
|
+
value: val
|
|
219
|
+
? trim(val[0].replace(COMMENT_REGEX, EMPTY_STRING))
|
|
220
|
+
: EMPTY_STRING
|
|
221
|
+
});
|
|
307
222
|
|
|
308
|
-
|
|
223
|
+
// ;
|
|
224
|
+
match(SEMICOLON_REGEX);
|
|
309
225
|
|
|
310
|
-
|
|
311
|
-
var frames = comments();
|
|
312
|
-
while (frame = keyframe()) {
|
|
313
|
-
frames.push(frame);
|
|
314
|
-
frames = frames.concat(comments());
|
|
226
|
+
return ret;
|
|
315
227
|
}
|
|
316
228
|
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
326
|
-
|
|
327
|
-
|
|
328
|
-
|
|
329
|
-
|
|
330
|
-
|
|
331
|
-
|
|
332
|
-
|
|
333
|
-
|
|
334
|
-
|
|
335
|
-
if (!m) return;
|
|
336
|
-
var supports = trim(m[1]);
|
|
337
|
-
|
|
338
|
-
if (!open()) return error("@supports missing '{'");
|
|
339
|
-
|
|
340
|
-
var style = comments().concat(rules());
|
|
341
|
-
|
|
342
|
-
if (!close()) return error("@supports missing '}'");
|
|
343
|
-
|
|
344
|
-
return pos({
|
|
345
|
-
type: 'supports',
|
|
346
|
-
supports: supports,
|
|
347
|
-
rules: style
|
|
348
|
-
});
|
|
349
|
-
}
|
|
350
|
-
|
|
351
|
-
/**
|
|
352
|
-
* Parse host.
|
|
353
|
-
*/
|
|
354
|
-
|
|
355
|
-
function athost() {
|
|
356
|
-
var pos = position();
|
|
357
|
-
var m = match(/^@host\s*/);
|
|
358
|
-
|
|
359
|
-
if (!m) return;
|
|
360
|
-
|
|
361
|
-
if (!open()) return error("@host missing '{'");
|
|
362
|
-
|
|
363
|
-
var style = comments().concat(rules());
|
|
364
|
-
|
|
365
|
-
if (!close()) return error("@host missing '}'");
|
|
366
|
-
|
|
367
|
-
return pos({
|
|
368
|
-
type: 'host',
|
|
369
|
-
rules: style
|
|
370
|
-
});
|
|
371
|
-
}
|
|
372
|
-
|
|
373
|
-
/**
|
|
374
|
-
* Parse media.
|
|
375
|
-
*/
|
|
376
|
-
|
|
377
|
-
function atmedia() {
|
|
378
|
-
var pos = position();
|
|
379
|
-
var m = match(/^@media *([^{]+)/);
|
|
380
|
-
|
|
381
|
-
if (!m) return;
|
|
382
|
-
var media = trim(m[1]);
|
|
383
|
-
|
|
384
|
-
if (!open()) return error("@media missing '{'");
|
|
385
|
-
|
|
386
|
-
var style = comments().concat(rules());
|
|
387
|
-
|
|
388
|
-
if (!close()) return error("@media missing '}'");
|
|
389
|
-
|
|
390
|
-
return pos({
|
|
391
|
-
type: 'media',
|
|
392
|
-
media: media,
|
|
393
|
-
rules: style
|
|
394
|
-
});
|
|
395
|
-
}
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
/**
|
|
399
|
-
* Parse custom-media.
|
|
400
|
-
*/
|
|
401
|
-
|
|
402
|
-
function atcustommedia() {
|
|
403
|
-
var pos = position();
|
|
404
|
-
var m = match(/^@custom-media\s+(--[^\s]+)\s*([^{;]+);/);
|
|
405
|
-
if (!m) return;
|
|
406
|
-
|
|
407
|
-
return pos({
|
|
408
|
-
type: 'custom-media',
|
|
409
|
-
name: trim(m[1]),
|
|
410
|
-
media: trim(m[2])
|
|
411
|
-
});
|
|
412
|
-
}
|
|
413
|
-
|
|
414
|
-
/**
|
|
415
|
-
* Parse paged media.
|
|
416
|
-
*/
|
|
417
|
-
|
|
418
|
-
function atpage() {
|
|
419
|
-
var pos = position();
|
|
420
|
-
var m = match(/^@page */);
|
|
421
|
-
if (!m) return;
|
|
422
|
-
|
|
423
|
-
var sel = selector() || [];
|
|
424
|
-
|
|
425
|
-
if (!open()) return error("@page missing '{'");
|
|
426
|
-
var decls = comments();
|
|
229
|
+
/**
|
|
230
|
+
* Parse declarations.
|
|
231
|
+
*
|
|
232
|
+
* @return {Object[]}
|
|
233
|
+
*/
|
|
234
|
+
function declarations() {
|
|
235
|
+
var decls = [];
|
|
236
|
+
|
|
237
|
+
comments(decls);
|
|
238
|
+
|
|
239
|
+
// declarations
|
|
240
|
+
var decl;
|
|
241
|
+
while ((decl = declaration())) {
|
|
242
|
+
if (decl !== false) {
|
|
243
|
+
decls.push(decl);
|
|
244
|
+
comments(decls);
|
|
245
|
+
}
|
|
246
|
+
}
|
|
427
247
|
|
|
428
|
-
|
|
429
|
-
var decl;
|
|
430
|
-
while (decl = declaration()) {
|
|
431
|
-
decls.push(decl);
|
|
432
|
-
decls = decls.concat(comments());
|
|
248
|
+
return decls;
|
|
433
249
|
}
|
|
434
250
|
|
|
435
|
-
|
|
436
|
-
|
|
437
|
-
|
|
438
|
-
type: 'page',
|
|
439
|
-
selectors: sel,
|
|
440
|
-
declarations: decls
|
|
441
|
-
});
|
|
442
|
-
}
|
|
443
|
-
|
|
444
|
-
/**
|
|
445
|
-
* Parse document.
|
|
446
|
-
*/
|
|
447
|
-
|
|
448
|
-
function atdocument() {
|
|
449
|
-
var pos = position();
|
|
450
|
-
var m = match(/^@([-\w]+)?document *([^{]+)/);
|
|
451
|
-
if (!m) return;
|
|
452
|
-
|
|
453
|
-
var vendor = trim(m[1]);
|
|
454
|
-
var doc = trim(m[2]);
|
|
455
|
-
|
|
456
|
-
if (!open()) return error("@document missing '{'");
|
|
457
|
-
|
|
458
|
-
var style = comments().concat(rules());
|
|
459
|
-
|
|
460
|
-
if (!close()) return error("@document missing '}'");
|
|
461
|
-
|
|
462
|
-
return pos({
|
|
463
|
-
type: 'document',
|
|
464
|
-
document: doc,
|
|
465
|
-
vendor: vendor,
|
|
466
|
-
rules: style
|
|
467
|
-
});
|
|
468
|
-
}
|
|
251
|
+
whitespace();
|
|
252
|
+
return declarations();
|
|
253
|
+
};
|
|
469
254
|
|
|
470
255
|
/**
|
|
471
|
-
*
|
|
256
|
+
* Trim `str`.
|
|
257
|
+
*
|
|
258
|
+
* @param {String} str
|
|
259
|
+
* @return {String}
|
|
472
260
|
*/
|
|
473
|
-
|
|
474
|
-
|
|
475
|
-
var pos = position();
|
|
476
|
-
var m = match(/^@font-face\s*/);
|
|
477
|
-
if (!m) return;
|
|
478
|
-
|
|
479
|
-
if (!open()) return error("@font-face missing '{'");
|
|
480
|
-
var decls = comments();
|
|
481
|
-
|
|
482
|
-
// declarations
|
|
483
|
-
var decl;
|
|
484
|
-
while (decl = declaration()) {
|
|
485
|
-
decls.push(decl);
|
|
486
|
-
decls = decls.concat(comments());
|
|
487
|
-
}
|
|
488
|
-
|
|
489
|
-
if (!close()) return error("@font-face missing '}'");
|
|
490
|
-
|
|
491
|
-
return pos({
|
|
492
|
-
type: 'font-face',
|
|
493
|
-
declarations: decls
|
|
494
|
-
});
|
|
261
|
+
function trim(str) {
|
|
262
|
+
return str ? str.replace(TRIM_REGEX, EMPTY_STRING) : EMPTY_STRING;
|
|
495
263
|
}
|
|
496
264
|
|
|
497
265
|
/**
|
|
498
|
-
*
|
|
499
|
-
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
*
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
var atnamespace = _compileAtrule('namespace');
|
|
514
|
-
|
|
515
|
-
/**
|
|
516
|
-
* Parse non-block at-rules
|
|
517
|
-
*/
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
function _compileAtrule(name) {
|
|
521
|
-
var re = new RegExp('^@' + name + '\\s*([^;]+);');
|
|
522
|
-
return function() {
|
|
523
|
-
var pos = position();
|
|
524
|
-
var m = match(re);
|
|
525
|
-
if (!m) return;
|
|
526
|
-
var ret = { type: name };
|
|
527
|
-
ret[name] = m[1].trim();
|
|
528
|
-
return pos(ret);
|
|
266
|
+
* Parses inline style to object.
|
|
267
|
+
*
|
|
268
|
+
* @example
|
|
269
|
+
* // returns { 'line-height': '42' }
|
|
270
|
+
* StyleToObject('line-height: 42;');
|
|
271
|
+
*
|
|
272
|
+
* @param {String} style - The inline style.
|
|
273
|
+
* @param {Function} [iterator] - The iterator function.
|
|
274
|
+
* @return {null|Object}
|
|
275
|
+
*/
|
|
276
|
+
function StyleToObject(style, iterator) {
|
|
277
|
+
var output = null;
|
|
278
|
+
if (!style || typeof style !== 'string') {
|
|
279
|
+
return output;
|
|
529
280
|
}
|
|
530
|
-
}
|
|
531
|
-
|
|
532
|
-
/**
|
|
533
|
-
* Parse at rule.
|
|
534
|
-
*/
|
|
535
|
-
|
|
536
|
-
function atrule() {
|
|
537
|
-
if (css[0] != '@') return;
|
|
538
|
-
|
|
539
|
-
return atkeyframes()
|
|
540
|
-
|| atmedia()
|
|
541
|
-
|| atcustommedia()
|
|
542
|
-
|| atsupports()
|
|
543
|
-
|| atimport()
|
|
544
|
-
|| atcharset()
|
|
545
|
-
|| atnamespace()
|
|
546
|
-
|| atdocument()
|
|
547
|
-
|| atpage()
|
|
548
|
-
|| athost()
|
|
549
|
-
|| atfontface();
|
|
550
|
-
}
|
|
551
|
-
|
|
552
|
-
/**
|
|
553
|
-
* Parse rule.
|
|
554
|
-
*/
|
|
555
|
-
|
|
556
|
-
function rule() {
|
|
557
|
-
var pos = position();
|
|
558
|
-
var sel = selector();
|
|
559
281
|
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
|
|
567
|
-
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
574
|
-
|
|
575
|
-
|
|
576
|
-
|
|
577
|
-
function trim(str) {
|
|
578
|
-
return str ? str.replace(/^\s+|\s+$/g, '') : '';
|
|
579
|
-
}
|
|
580
|
-
|
|
581
|
-
/**
|
|
582
|
-
* Adds non-enumerable parent node reference to each node.
|
|
583
|
-
*/
|
|
584
|
-
|
|
585
|
-
function addParent(obj, parent) {
|
|
586
|
-
var isNode = obj && typeof obj.type === 'string';
|
|
587
|
-
var childParent = isNode ? obj : parent;
|
|
588
|
-
|
|
589
|
-
for (var k in obj) {
|
|
590
|
-
var value = obj[k];
|
|
591
|
-
if (Array.isArray(value)) {
|
|
592
|
-
value.forEach(function(v) { addParent(v, childParent); });
|
|
593
|
-
} else if (value && typeof value === 'object') {
|
|
594
|
-
addParent(value, childParent);
|
|
282
|
+
var declaration;
|
|
283
|
+
var declarations = inlineStyleParser(style);
|
|
284
|
+
var hasIterator = typeof iterator === 'function';
|
|
285
|
+
var property;
|
|
286
|
+
var value;
|
|
287
|
+
|
|
288
|
+
for (var i = 0, len = declarations.length; i < len; i++) {
|
|
289
|
+
declaration = declarations[i];
|
|
290
|
+
property = declaration.property;
|
|
291
|
+
value = declaration.value;
|
|
292
|
+
|
|
293
|
+
if (hasIterator) {
|
|
294
|
+
iterator(property, value, declaration);
|
|
295
|
+
} else if (value) {
|
|
296
|
+
output || (output = {});
|
|
297
|
+
output[property] = value;
|
|
298
|
+
}
|
|
595
299
|
}
|
|
596
|
-
}
|
|
597
300
|
|
|
598
|
-
|
|
599
|
-
Object.defineProperty(obj, 'parent', {
|
|
600
|
-
configurable: true,
|
|
601
|
-
writable: true,
|
|
602
|
-
enumerable: false,
|
|
603
|
-
value: parent || null
|
|
604
|
-
});
|
|
605
|
-
}
|
|
606
|
-
|
|
607
|
-
return obj;
|
|
608
|
-
}
|
|
609
|
-
|
|
610
|
-
/**
|
|
611
|
-
* Parses inline style.
|
|
612
|
-
*
|
|
613
|
-
* Example: 'color:red' => { color: 'red' }
|
|
614
|
-
*
|
|
615
|
-
* @param {String} style - The inline style.
|
|
616
|
-
* @param {Function} [iterator] - The iterator function.
|
|
617
|
-
* @return {null|Object}
|
|
618
|
-
*/
|
|
619
|
-
var styleToObject = function parseInlineStyle(style, iterator) {
|
|
620
|
-
if (!style || typeof style !== 'string') return null;
|
|
621
|
-
|
|
622
|
-
// make sure to wrap declarations in placeholder
|
|
623
|
-
var declarations = parse('p{' + style + '}').stylesheet.rules[0].declarations;
|
|
624
|
-
var declaration, property, value;
|
|
625
|
-
|
|
626
|
-
var output = null;
|
|
627
|
-
var hasIterator = typeof iterator === 'function';
|
|
628
|
-
|
|
629
|
-
for (var i = 0, len = declarations.length; i < len; i++) {
|
|
630
|
-
declaration = declarations[i];
|
|
631
|
-
property = declaration.property;
|
|
632
|
-
value = declaration.value;
|
|
633
|
-
|
|
634
|
-
if (hasIterator) {
|
|
635
|
-
iterator(property, value, declaration);
|
|
636
|
-
} else if (value) {
|
|
637
|
-
output || (output = {});
|
|
638
|
-
output[property] = value;
|
|
639
|
-
}
|
|
301
|
+
return output;
|
|
640
302
|
}
|
|
641
303
|
|
|
642
|
-
|
|
643
|
-
};
|
|
304
|
+
var styleToObject = StyleToObject;
|
|
644
305
|
|
|
645
|
-
return styleToObject;
|
|
306
|
+
return styleToObject;
|
|
646
307
|
|
|
647
308
|
})));
|