UNPKG

1.65 kBJavaScriptView Raw
1// tooling
2import { list } from 'postcss';
3import getReplacedString from './get-replaced-string';
4import transformNode from './transform-node';
5import setVariable from './set-variable';
6
7// transform @for at-rules
8export default function transformForAtrule(rule, opts) {
9 // if @for is supported
10 if (opts.transform.includes('@for')) {
11 // @for options
12 const { varname, start, end, increment } = getForOpts(rule, opts);
13 const direction = start <= end ? 1 : -1;
14 const replacements = [];
15
16 // for each iteration
17 for (let incrementor = start; incrementor * direction <= end * direction; incrementor += increment * direction) {
18 // set the current variable
19 setVariable(rule, varname, incrementor, opts);
20
21 // clone the @for at-rule
22 const clone = rule.clone({
23 parent: rule.parent,
24 variables: rule.variables
25 });
26
27 // transform the clone children
28 transformNode(clone, opts);
29
30 // push the clone children to the replacements array
31 replacements.push(...clone.nodes);
32 }
33
34 // replace the @for at-rule with the replacements
35 rule.parent.insertBefore(rule, replacements);
36
37 rule.remove();
38 }
39}
40
41// return the @for statement options (@for NAME from START through END, @for NAME from START through END by INCREMENT)
42const getForOpts = (node, opts) => {
43 const params = list.space(node.params);
44 const varname = params[0].trim().slice(1);
45 const start = Number(getReplacedString(params[2], node, opts));
46 const end = Number(getReplacedString(params[4], node, opts));
47 const increment = 6 in params && Number(getReplacedString(params[6], node, opts)) || 1;
48
49 return { varname, start, end, increment };
50};