@iconify/tools 2.2.5 → 3.0.0-beta.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.
Files changed (85) hide show
  1. package/README.md +8 -2
  2. package/lib/colors/detect.cjs +4 -4
  3. package/lib/colors/detect.d.ts +1 -1
  4. package/lib/colors/detect.mjs +5 -5
  5. package/lib/colors/parse.cjs +275 -129
  6. package/lib/colors/parse.d.ts +14 -5
  7. package/lib/colors/parse.mjs +278 -133
  8. package/lib/colors/validate.cjs +11 -2
  9. package/lib/colors/validate.d.ts +10 -2
  10. package/lib/colors/validate.mjs +12 -4
  11. package/lib/download/api/download.cjs +4 -4
  12. package/lib/download/api/download.mjs +4 -4
  13. package/lib/download/api/index.cjs +0 -1
  14. package/lib/download/api/index.mjs +0 -1
  15. package/lib/download/git/index.cjs +1 -1
  16. package/lib/download/git/index.mjs +1 -1
  17. package/lib/download/git/reset.cjs +1 -1
  18. package/lib/download/git/reset.mjs +1 -1
  19. package/lib/download/github/hash.cjs +0 -1
  20. package/lib/download/github/hash.mjs +0 -1
  21. package/lib/download/github/index.cjs +1 -1
  22. package/lib/download/github/index.mjs +1 -1
  23. package/lib/download/gitlab/hash.cjs +0 -1
  24. package/lib/download/gitlab/hash.mjs +0 -1
  25. package/lib/download/gitlab/index.cjs +1 -1
  26. package/lib/download/gitlab/index.mjs +1 -1
  27. package/lib/download/helpers/unzip.cjs +5 -1
  28. package/lib/download/index.cjs +1 -1
  29. package/lib/download/index.mjs +1 -1
  30. package/lib/download/npm/index.cjs +1 -1
  31. package/lib/download/npm/index.mjs +1 -1
  32. package/lib/icon-set/index.cjs +18 -0
  33. package/lib/icon-set/index.d.ts +7 -1
  34. package/lib/icon-set/index.mjs +18 -0
  35. package/lib/icon-set/tags.cjs +2 -2
  36. package/lib/icon-set/tags.d.ts +1 -1
  37. package/lib/icon-set/tags.mjs +2 -2
  38. package/lib/icon-set/types.d.ts +5 -4
  39. package/lib/import/directory.cjs +101 -28
  40. package/lib/import/directory.d.ts +12 -5
  41. package/lib/import/directory.mjs +103 -31
  42. package/lib/import/figma/index.cjs +1 -2
  43. package/lib/import/figma/index.mjs +1 -2
  44. package/lib/import/figma/query.cjs +0 -1
  45. package/lib/import/figma/query.mjs +0 -1
  46. package/lib/index.cjs +9 -1
  47. package/lib/index.d.ts +7 -6
  48. package/lib/index.mjs +8 -7
  49. package/lib/misc/scan.cjs +61 -8
  50. package/lib/misc/scan.d.ts +12 -6
  51. package/lib/misc/scan.mjs +62 -10
  52. package/lib/optimise/origin.cjs +23 -0
  53. package/lib/optimise/origin.d.ts +10 -0
  54. package/lib/optimise/origin.mjs +21 -0
  55. package/lib/optimise/scale.cjs +17 -15
  56. package/lib/optimise/scale.mjs +17 -15
  57. package/lib/svg/analyse.cjs +2 -2
  58. package/lib/svg/analyse.d.ts +1 -1
  59. package/lib/svg/analyse.mjs +4 -4
  60. package/lib/svg/cleanup/attribs.cjs +2 -2
  61. package/lib/svg/cleanup/attribs.d.ts +1 -1
  62. package/lib/svg/cleanup/attribs.mjs +3 -3
  63. package/lib/svg/cleanup/bad-tags.cjs +2 -2
  64. package/lib/svg/cleanup/bad-tags.d.ts +1 -1
  65. package/lib/svg/cleanup/bad-tags.mjs +3 -3
  66. package/lib/svg/cleanup/inline-style.cjs +2 -2
  67. package/lib/svg/cleanup/inline-style.d.ts +1 -1
  68. package/lib/svg/cleanup/inline-style.mjs +3 -3
  69. package/lib/svg/cleanup/root-style.cjs +1 -1
  70. package/lib/svg/cleanup/root-style.d.ts +1 -5
  71. package/lib/svg/cleanup/root-style.mjs +2 -2
  72. package/lib/svg/cleanup/svgo-style.cjs +2 -2
  73. package/lib/svg/cleanup/svgo-style.d.ts +1 -1
  74. package/lib/svg/cleanup/svgo-style.mjs +3 -3
  75. package/lib/svg/cleanup.cjs +6 -6
  76. package/lib/svg/cleanup.d.ts +1 -1
  77. package/lib/svg/cleanup.mjs +6 -6
  78. package/lib/svg/index.cjs +5 -1
  79. package/lib/svg/parse-style.cjs +149 -89
  80. package/lib/svg/parse-style.d.ts +6 -1
  81. package/lib/svg/parse-style.mjs +150 -91
  82. package/lib/svg/parse.cjs +56 -18
  83. package/lib/svg/parse.d.ts +8 -2
  84. package/lib/svg/parse.mjs +56 -19
  85. package/package.json +23 -20
@@ -9,41 +9,58 @@ require('../css/parser/error.cjs');
9
9
  require('../css/parser/strings.cjs');
10
10
  require('../css/parser/text.cjs');
11
11
 
12
- async function parseSVGStyle(svg, callback) {
13
- return svg_parse.parseSVG(svg, async (item) => {
14
- const tagName = item.tagName;
15
- const $element = item.$element;
16
- if (tagName === "style") {
17
- const content = $element.text();
18
- if (typeof content !== "string") {
19
- $element.remove();
20
- return;
12
+ function parseItem(item, callback, done) {
13
+ const tagName = item.tagName;
14
+ const $element = item.$element;
15
+ function parseStyleItem(done2) {
16
+ const content = $element.text();
17
+ if (typeof content !== "string") {
18
+ $element.remove();
19
+ return done2();
20
+ }
21
+ const tokens = css_parser_tokens.getTokens(content);
22
+ if (!(tokens instanceof Array)) {
23
+ throw new Error("Error parsing style");
24
+ }
25
+ let changed2 = false;
26
+ const selectorStart = [];
27
+ const newTokens = [];
28
+ const parsedTokens = () => {
29
+ if (changed2) {
30
+ const tree = css_parser_tree.tokensTree(
31
+ newTokens.filter((token) => token !== null)
32
+ );
33
+ if (!tree.length) {
34
+ $element.remove();
35
+ } else {
36
+ const newContent = css_parser_export.tokensToString(tree);
37
+ item.$element.text(newContent);
38
+ }
21
39
  }
22
- const tokens = css_parser_tokens.getTokens(content);
23
- if (!(tokens instanceof Array)) {
24
- throw new Error("Error parsing style");
40
+ done2();
41
+ };
42
+ const nextToken = () => {
43
+ const token = tokens.shift();
44
+ if (token === void 0) {
45
+ return parsedTokens();
25
46
  }
26
- let changed2 = false;
27
- const selectorStart = [];
28
- const newTokens = [];
29
- for (let i = 0; i < tokens.length; i++) {
30
- const token = tokens[i];
31
- switch (token.type) {
32
- case "selector":
33
- case "at-rule":
34
- selectorStart.push(newTokens.length);
35
- break;
36
- case "close":
37
- selectorStart.pop();
38
- break;
39
- }
40
- if (token.type !== "rule") {
41
- newTokens.push(token);
42
- continue;
43
- }
44
- const value = token.value;
45
- const selectorTokens = selectorStart.map((index) => newTokens[index]).filter((item2) => item2 !== null);
46
- let result = callback({
47
+ switch (token.type) {
48
+ case "selector":
49
+ case "at-rule":
50
+ selectorStart.push(newTokens.length);
51
+ break;
52
+ case "close":
53
+ selectorStart.pop();
54
+ break;
55
+ }
56
+ if (token.type !== "rule") {
57
+ newTokens.push(token);
58
+ return nextToken();
59
+ }
60
+ const value = token.value;
61
+ const selectorTokens = selectorStart.map((index) => newTokens[index]).filter((item2) => item2 !== null);
62
+ callback(
63
+ {
47
64
  type: "global",
48
65
  prop: token.prop,
49
66
  value,
@@ -61,77 +78,120 @@ async function parseSVGStyle(svg, callback) {
61
78
  []
62
79
  ),
63
80
  prevTokens: newTokens,
64
- nextTokens: tokens.slice(i + 1)
65
- });
66
- if (result instanceof Promise) {
67
- result = await result;
68
- }
69
- if (result !== void 0) {
70
- if (result !== value) {
81
+ nextTokens: tokens.slice(0)
82
+ },
83
+ (result) => {
84
+ if (result !== void 0) {
85
+ if (result !== value) {
86
+ changed2 = true;
87
+ token.value = result;
88
+ }
89
+ newTokens.push(token);
90
+ } else {
71
91
  changed2 = true;
72
- token.value = result;
73
92
  }
74
- newTokens.push(token);
75
- } else {
76
- changed2 = true;
93
+ nextToken();
77
94
  }
78
- }
79
- if (!changed2) {
80
- return;
81
- }
82
- const tree = css_parser_tree.tokensTree(
83
- newTokens.filter((token) => token !== null)
84
95
  );
85
- if (!tree.length) {
86
- $element.remove();
87
- return;
96
+ };
97
+ nextToken();
98
+ }
99
+ if (tagName === "style") {
100
+ return parseStyleItem(done);
101
+ }
102
+ const attribs = item.element.attribs;
103
+ if (attribs.style === void 0) {
104
+ return done();
105
+ }
106
+ const parsedStyle = css_parse.parseInlineStyle(attribs.style);
107
+ if (parsedStyle === null) {
108
+ $element.removeAttr("style");
109
+ return done();
110
+ }
111
+ const propsQueue = Object.keys(parsedStyle);
112
+ let changed = false;
113
+ const parsedProps = () => {
114
+ if (changed) {
115
+ const newStyle = Object.keys(parsedStyle).map((key) => key + ":" + parsedStyle[key] + ";").join("");
116
+ if (!newStyle.length) {
117
+ $element.removeAttr("style");
118
+ } else {
119
+ $element.attr("style", newStyle);
88
120
  }
89
- const newContent = css_parser_export.tokensToString(tree);
90
- item.$element.text(newContent);
91
- return;
92
121
  }
93
- const attribs = item.element.attribs;
94
- if (attribs.style === void 0) {
95
- return;
122
+ done();
123
+ };
124
+ const nextProp = () => {
125
+ const prop = propsQueue.shift();
126
+ if (prop === void 0) {
127
+ return parsedProps();
96
128
  }
97
- const parsedStyle = css_parse.parseInlineStyle(attribs.style);
98
- if (parsedStyle === null) {
99
- $element.removeAttr("style");
100
- return;
101
- }
102
- const props = Object.keys(parsedStyle);
103
- let changed = false;
104
- for (let i = 0; i < props.length; i++) {
105
- const prop = props[i];
106
- const value = parsedStyle[prop];
107
- let result = callback({
129
+ const value = parsedStyle[prop];
130
+ callback(
131
+ {
108
132
  type: "inline",
109
133
  prop,
110
134
  value,
111
135
  item
112
- });
113
- if (result instanceof Promise) {
114
- result = await result;
136
+ },
137
+ (result) => {
138
+ if (result !== value) {
139
+ changed = true;
140
+ if (result === void 0) {
141
+ delete parsedStyle[prop];
142
+ } else {
143
+ parsedStyle[prop] = result;
144
+ }
145
+ }
146
+ nextProp();
115
147
  }
116
- if (result !== value) {
117
- changed = true;
118
- if (result === void 0) {
119
- delete parsedStyle[prop];
120
- } else {
121
- parsedStyle[prop] = result;
148
+ );
149
+ };
150
+ nextProp();
151
+ }
152
+ async function parseSVGStyle(svg, callback) {
153
+ return svg_parse.parseSVG(svg, (item) => {
154
+ return new Promise((fulfill, reject) => {
155
+ try {
156
+ parseItem(
157
+ item,
158
+ (styleItem, done) => {
159
+ try {
160
+ const result = callback(styleItem);
161
+ if (result instanceof Promise) {
162
+ result.then(done).catch(reject);
163
+ } else {
164
+ done(result);
165
+ }
166
+ } catch (err) {
167
+ reject(err);
168
+ }
169
+ },
170
+ fulfill
171
+ );
172
+ } catch (err) {
173
+ reject(err);
174
+ }
175
+ });
176
+ });
177
+ }
178
+ function parseSVGStyleSync(svg, callback) {
179
+ let isSync = true;
180
+ svg_parse.parseSVGSync(svg, (item) => {
181
+ parseItem(
182
+ item,
183
+ (styleItem, done) => {
184
+ done(callback(styleItem));
185
+ },
186
+ () => {
187
+ if (!isSync) {
188
+ throw new Error("parseSVGStyleSync callback was async");
122
189
  }
123
190
  }
124
- }
125
- if (!changed) {
126
- return;
127
- }
128
- const newStyle = Object.keys(parsedStyle).map((key) => key + ":" + parsedStyle[key] + ";").join("");
129
- if (!newStyle.length) {
130
- $element.removeAttr("style");
131
- } else {
132
- $element.attr("style", newStyle);
133
- }
191
+ );
134
192
  });
193
+ isSync = false;
135
194
  }
136
195
 
137
196
  exports.parseSVGStyle = parseSVGStyle;
197
+ exports.parseSVGStyleSync = parseSVGStyleSync;
@@ -33,6 +33,7 @@ type ParseSVGStyleCallbackResult = string | undefined;
33
33
  * Callback function
34
34
  */
35
35
  type ParseSVGStyleCallback = (item: ParseSVGStyleCallbackItem) => ParseSVGStyleCallbackResult | Promise<ParseSVGStyleCallbackResult>;
36
+ type ParseSVGStyleCallbackSync = (item: ParseSVGStyleCallbackItem) => ParseSVGStyleCallbackResult;
36
37
  /**
37
38
  * Parse styles in SVG
38
39
  *
@@ -41,5 +42,9 @@ type ParseSVGStyleCallback = (item: ParseSVGStyleCallbackItem) => ParseSVGStyleC
41
42
  * Callback can be asynchronous.
42
43
  */
43
44
  declare function parseSVGStyle(svg: SVG, callback: ParseSVGStyleCallback): Promise<void>;
45
+ /**
46
+ * Synchronous version
47
+ */
48
+ declare function parseSVGStyleSync(svg: SVG, callback: ParseSVGStyleCallbackSync): void;
44
49
 
45
- export { ParseSVGStyleCallback, ParseSVGStyleCallbackItem, ParseSVGStyleCallbackResult, parseSVGStyle };
50
+ export { ParseSVGStyleCallback, ParseSVGStyleCallbackItem, ParseSVGStyleCallbackResult, ParseSVGStyleCallbackSync, parseSVGStyle, parseSVGStyleSync };
@@ -2,46 +2,63 @@ import { parseInlineStyle } from '../css/parse.mjs';
2
2
  import { tokensToString } from '../css/parser/export.mjs';
3
3
  import { getTokens } from '../css/parser/tokens.mjs';
4
4
  import { tokensTree } from '../css/parser/tree.mjs';
5
- import { parseSVG } from './parse.mjs';
5
+ import { parseSVG, parseSVGSync } from './parse.mjs';
6
6
  import '../css/parser/error.mjs';
7
7
  import '../css/parser/strings.mjs';
8
8
  import '../css/parser/text.mjs';
9
9
 
10
- async function parseSVGStyle(svg, callback) {
11
- return parseSVG(svg, async (item) => {
12
- const tagName = item.tagName;
13
- const $element = item.$element;
14
- if (tagName === "style") {
15
- const content = $element.text();
16
- if (typeof content !== "string") {
17
- $element.remove();
18
- return;
10
+ function parseItem(item, callback, done) {
11
+ const tagName = item.tagName;
12
+ const $element = item.$element;
13
+ function parseStyleItem(done2) {
14
+ const content = $element.text();
15
+ if (typeof content !== "string") {
16
+ $element.remove();
17
+ return done2();
18
+ }
19
+ const tokens = getTokens(content);
20
+ if (!(tokens instanceof Array)) {
21
+ throw new Error("Error parsing style");
22
+ }
23
+ let changed2 = false;
24
+ const selectorStart = [];
25
+ const newTokens = [];
26
+ const parsedTokens = () => {
27
+ if (changed2) {
28
+ const tree = tokensTree(
29
+ newTokens.filter((token) => token !== null)
30
+ );
31
+ if (!tree.length) {
32
+ $element.remove();
33
+ } else {
34
+ const newContent = tokensToString(tree);
35
+ item.$element.text(newContent);
36
+ }
19
37
  }
20
- const tokens = getTokens(content);
21
- if (!(tokens instanceof Array)) {
22
- throw new Error("Error parsing style");
38
+ done2();
39
+ };
40
+ const nextToken = () => {
41
+ const token = tokens.shift();
42
+ if (token === void 0) {
43
+ return parsedTokens();
23
44
  }
24
- let changed2 = false;
25
- const selectorStart = [];
26
- const newTokens = [];
27
- for (let i = 0; i < tokens.length; i++) {
28
- const token = tokens[i];
29
- switch (token.type) {
30
- case "selector":
31
- case "at-rule":
32
- selectorStart.push(newTokens.length);
33
- break;
34
- case "close":
35
- selectorStart.pop();
36
- break;
37
- }
38
- if (token.type !== "rule") {
39
- newTokens.push(token);
40
- continue;
41
- }
42
- const value = token.value;
43
- const selectorTokens = selectorStart.map((index) => newTokens[index]).filter((item2) => item2 !== null);
44
- let result = callback({
45
+ switch (token.type) {
46
+ case "selector":
47
+ case "at-rule":
48
+ selectorStart.push(newTokens.length);
49
+ break;
50
+ case "close":
51
+ selectorStart.pop();
52
+ break;
53
+ }
54
+ if (token.type !== "rule") {
55
+ newTokens.push(token);
56
+ return nextToken();
57
+ }
58
+ const value = token.value;
59
+ const selectorTokens = selectorStart.map((index) => newTokens[index]).filter((item2) => item2 !== null);
60
+ callback(
61
+ {
45
62
  type: "global",
46
63
  prop: token.prop,
47
64
  value,
@@ -59,77 +76,119 @@ async function parseSVGStyle(svg, callback) {
59
76
  []
60
77
  ),
61
78
  prevTokens: newTokens,
62
- nextTokens: tokens.slice(i + 1)
63
- });
64
- if (result instanceof Promise) {
65
- result = await result;
66
- }
67
- if (result !== void 0) {
68
- if (result !== value) {
79
+ nextTokens: tokens.slice(0)
80
+ },
81
+ (result) => {
82
+ if (result !== void 0) {
83
+ if (result !== value) {
84
+ changed2 = true;
85
+ token.value = result;
86
+ }
87
+ newTokens.push(token);
88
+ } else {
69
89
  changed2 = true;
70
- token.value = result;
71
90
  }
72
- newTokens.push(token);
73
- } else {
74
- changed2 = true;
91
+ nextToken();
75
92
  }
76
- }
77
- if (!changed2) {
78
- return;
79
- }
80
- const tree = tokensTree(
81
- newTokens.filter((token) => token !== null)
82
93
  );
83
- if (!tree.length) {
84
- $element.remove();
85
- return;
94
+ };
95
+ nextToken();
96
+ }
97
+ if (tagName === "style") {
98
+ return parseStyleItem(done);
99
+ }
100
+ const attribs = item.element.attribs;
101
+ if (attribs.style === void 0) {
102
+ return done();
103
+ }
104
+ const parsedStyle = parseInlineStyle(attribs.style);
105
+ if (parsedStyle === null) {
106
+ $element.removeAttr("style");
107
+ return done();
108
+ }
109
+ const propsQueue = Object.keys(parsedStyle);
110
+ let changed = false;
111
+ const parsedProps = () => {
112
+ if (changed) {
113
+ const newStyle = Object.keys(parsedStyle).map((key) => key + ":" + parsedStyle[key] + ";").join("");
114
+ if (!newStyle.length) {
115
+ $element.removeAttr("style");
116
+ } else {
117
+ $element.attr("style", newStyle);
86
118
  }
87
- const newContent = tokensToString(tree);
88
- item.$element.text(newContent);
89
- return;
90
119
  }
91
- const attribs = item.element.attribs;
92
- if (attribs.style === void 0) {
93
- return;
120
+ done();
121
+ };
122
+ const nextProp = () => {
123
+ const prop = propsQueue.shift();
124
+ if (prop === void 0) {
125
+ return parsedProps();
94
126
  }
95
- const parsedStyle = parseInlineStyle(attribs.style);
96
- if (parsedStyle === null) {
97
- $element.removeAttr("style");
98
- return;
99
- }
100
- const props = Object.keys(parsedStyle);
101
- let changed = false;
102
- for (let i = 0; i < props.length; i++) {
103
- const prop = props[i];
104
- const value = parsedStyle[prop];
105
- let result = callback({
127
+ const value = parsedStyle[prop];
128
+ callback(
129
+ {
106
130
  type: "inline",
107
131
  prop,
108
132
  value,
109
133
  item
110
- });
111
- if (result instanceof Promise) {
112
- result = await result;
134
+ },
135
+ (result) => {
136
+ if (result !== value) {
137
+ changed = true;
138
+ if (result === void 0) {
139
+ delete parsedStyle[prop];
140
+ } else {
141
+ parsedStyle[prop] = result;
142
+ }
143
+ }
144
+ nextProp();
113
145
  }
114
- if (result !== value) {
115
- changed = true;
116
- if (result === void 0) {
117
- delete parsedStyle[prop];
118
- } else {
119
- parsedStyle[prop] = result;
146
+ );
147
+ };
148
+ nextProp();
149
+ }
150
+ async function parseSVGStyle(svg, callback) {
151
+ return parseSVG(svg, (item) => {
152
+ return new Promise((fulfill, reject) => {
153
+ try {
154
+ parseItem(
155
+ item,
156
+ (styleItem, done) => {
157
+ try {
158
+ const result = callback(styleItem);
159
+ if (result instanceof Promise) {
160
+ result.then(done).catch(reject);
161
+ } else {
162
+ done(result);
163
+ }
164
+ } catch (err) {
165
+ reject(err);
166
+ }
167
+ },
168
+ fulfill
169
+ );
170
+ } catch (err) {
171
+ reject(err);
172
+ }
173
+ });
174
+ });
175
+ }
176
+ function parseSVGStyleSync(svg, callback) {
177
+ let isSync = true;
178
+ parseSVGSync(svg, (item) => {
179
+ parseItem(
180
+ item,
181
+ (styleItem, done) => {
182
+ done(callback(styleItem));
183
+ },
184
+ () => {
185
+ if (!isSync) {
186
+ throw new Error("parseSVGStyleSync callback was async");
120
187
  }
121
188
  }
122
- }
123
- if (!changed) {
124
- return;
125
- }
126
- const newStyle = Object.keys(parsedStyle).map((key) => key + ":" + parsedStyle[key] + ";").join("");
127
- if (!newStyle.length) {
128
- $element.removeAttr("style");
129
- } else {
130
- $element.attr("style", newStyle);
131
- }
189
+ );
132
190
  });
191
+ isSync = false;
133
192
  }
134
193
 
135
- export { parseSVGStyle };
194
+ export { parseSVGStyle, parseSVGStyleSync };
package/lib/svg/parse.cjs CHANGED
@@ -1,9 +1,9 @@
1
1
  'use strict';
2
2
 
3
- async function parseSVG(svg, callback) {
4
- async function checkNode(element, parents) {
3
+ function parse(svg, callback, done) {
4
+ function checkNode(element, parents, done2) {
5
5
  if (element.type !== "tag") {
6
- return;
6
+ return done2();
7
7
  }
8
8
  const $element = cheerio(element);
9
9
  const tagName = element.tagName;
@@ -16,25 +16,63 @@ async function parseSVG(svg, callback) {
16
16
  testChildren: true,
17
17
  removeNode: false
18
18
  };
19
- const result = callback(item);
20
- if (result instanceof Promise) {
21
- await result;
22
- }
23
- const newParents = parents.slice(0);
24
- newParents.unshift(item);
25
- if (tagName !== "style" && item.testChildren && !item.removeNode) {
26
- const children = $element.children().toArray();
27
- for (let i = 0; i < children.length; i++) {
28
- await checkNode(children[i], newParents);
19
+ callback(item, () => {
20
+ const newParents = parents.slice(0);
21
+ newParents.unshift(item);
22
+ let queue = [];
23
+ if (tagName !== "style" && item.testChildren && !item.removeNode) {
24
+ const children = $element.children().toArray();
25
+ queue = children.slice(0);
29
26
  }
30
- }
31
- if (item.removeNode) {
32
- $element.remove();
33
- }
27
+ const next = () => {
28
+ const queueItem = queue.shift();
29
+ if (!queueItem) {
30
+ if (item.removeNode) {
31
+ $element.remove();
32
+ }
33
+ return done2();
34
+ }
35
+ checkNode(queueItem, newParents, next);
36
+ };
37
+ next();
38
+ });
34
39
  }
35
40
  const cheerio = svg.$svg;
36
41
  const $root = svg.$svg(":root");
37
- await checkNode($root.get(0), []);
42
+ checkNode($root.get(0), [], done);
43
+ }
44
+ function parseSVG(svg, callback) {
45
+ return new Promise((fulfill, reject) => {
46
+ parse(
47
+ svg,
48
+ (item, next) => {
49
+ const result = callback(item);
50
+ if (result instanceof Promise) {
51
+ result.then(next).catch(reject);
52
+ } else {
53
+ next();
54
+ }
55
+ },
56
+ fulfill
57
+ );
58
+ });
59
+ }
60
+ function parseSVGSync(svg, callback) {
61
+ let isSync = true;
62
+ parse(
63
+ svg,
64
+ (item, next) => {
65
+ callback(item);
66
+ next();
67
+ },
68
+ () => {
69
+ if (!isSync) {
70
+ throw new Error("parseSVGSync callback was async");
71
+ }
72
+ }
73
+ );
74
+ isSync = false;
38
75
  }
39
76
 
40
77
  exports.parseSVG = parseSVG;
78
+ exports.parseSVGSync = parseSVGSync;
@@ -18,7 +18,9 @@ interface ParseSVGCallbackItem {
18
18
  /**
19
19
  * Callback function
20
20
  */
21
- type ParseSVGCallback = (item: ParseSVGCallbackItem) => void | Promise<void>;
21
+ type Callback<T> = (item: ParseSVGCallbackItem) => T;
22
+ type ParseSVGCallback = Callback<void | Promise<void>>;
23
+ type ParseSVGCallbackSync = Callback<void>;
22
24
  /**
23
25
  * Parse SVG
24
26
  *
@@ -26,5 +28,9 @@ type ParseSVGCallback = (item: ParseSVGCallbackItem) => void | Promise<void>;
26
28
  * Callback can be asynchronous.
27
29
  */
28
30
  declare function parseSVG(svg: SVG, callback: ParseSVGCallback): Promise<void>;
31
+ /**
32
+ * Sync version
33
+ */
34
+ declare function parseSVGSync(svg: SVG, callback: ParseSVGCallbackSync): void;
29
35
 
30
- export { ParseSVGCallback, ParseSVGCallbackItem, parseSVG };
36
+ export { ParseSVGCallback, ParseSVGCallbackItem, ParseSVGCallbackSync, parseSVG, parseSVGSync };