Skip to content

Commit 3abb740

Browse files
committed
partial @at-root support (leafo#193)
1 parent a8e987c commit 3abb740

File tree

5 files changed

+109
-1
lines changed

5 files changed

+109
-1
lines changed

src/Compiler.php

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -530,6 +530,36 @@ protected function mediaParent($scope)
530530
return $scope;
531531
}
532532

533+
/**
534+
* Compile at-root
535+
*
536+
* @param \stdClass $block
537+
*/
538+
protected function compileAtRoot($block)
539+
{
540+
$env = $this->pushEnv($block);
541+
542+
$envs = $this->compactEnv($env);
543+
544+
if (isset($block->with)) {
545+
// @todo move outside of nested directives, e.g., (without: all), (without: media supports), (with: rule)
546+
} else {
547+
// exclude selectors by default
548+
$this->env->parent = $this->rootEnv;
549+
}
550+
551+
$this->scope = $this->makeOutputBlock('at-root');
552+
$this->scope->depth = 1;
553+
$this->scope->parent->children[] = $this->scope;
554+
555+
$this->compileChildren($block->children, $this->scope);
556+
557+
$this->scope = $this->scope->parent;
558+
$this->env = $this->extractEnv($envs);
559+
560+
$this->popEnv();
561+
}
562+
533563
/**
534564
* Compile keyframe block
535565
*
@@ -1084,6 +1114,10 @@ protected function compileChild($child, $out)
10841114
}
10851115
break;
10861116

1117+
case 'at-root':
1118+
$this->compileAtRoot($child[1]);
1119+
break;
1120+
10871121
case 'media':
10881122
$this->compileMedia($child[1]);
10891123
break;

src/Parser.php

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -241,6 +241,20 @@ protected function parseChunk()
241241

242242
// the directives
243243
if (isset($this->buffer[$this->count]) && $this->buffer[$this->count] === '@') {
244+
if ($this->literal('@at-root') &&
245+
($this->selectors($selector) || true) &&
246+
($this->map($with) || true) &&
247+
$this->literal('{')
248+
) {
249+
$atRoot = $this->pushSpecialBlock('at-root', $s);
250+
$atRoot->selector = $selector;
251+
$atRoot->with = $with;
252+
253+
return true;
254+
}
255+
256+
$this->seek($s);
257+
244258
if ($this->literal('@media') && $this->mediaQueryList($mediaQueryList) && $this->literal('{')) {
245259
$media = $this->pushSpecialBlock('media', $s);
246260
$media->queryList = $mediaQueryList[2];
@@ -1393,7 +1407,9 @@ protected function map(&$out)
13931407
{
13941408
$s = $this->seek();
13951409

1396-
$this->literal('(');
1410+
if (! $this->literal('(')) {
1411+
return false;
1412+
}
13971413

13981414
$keys = array();
13991415
$values = array();

tests/inputs/at_root.scss

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
.first {
2+
color: red;
3+
}
4+
body{
5+
.second {
6+
color: white;
7+
8+
@at-root {
9+
.nested1 {
10+
color: blue;
11+
@at-root {
12+
.nested2 {
13+
color: yellow;
14+
}
15+
}
16+
color: orange;
17+
}
18+
}
19+
color: black;
20+
}
21+
}
22+
.third {
23+
color: green;
24+
}

tests/outputs/at_root.css

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
.first {
2+
color: red; }
3+
4+
body .second {
5+
color: white;
6+
color: black; }
7+
8+
.nested1 {
9+
color: blue;
10+
color: orange; }
11+
.nested2 {
12+
color: yellow; }
13+
14+
.third {
15+
color: green; }

tests/outputs_numbered/at_root.css

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
/* line 1, inputs/at_root.scss */
2+
.first {
3+
color: red; }
4+
/* line 4, inputs/at_root.scss */
5+
/* line 5, inputs/at_root.scss */
6+
body .second {
7+
color: white;
8+
color: black; }
9+
10+
/* line 9, inputs/at_root.scss */
11+
.nested1 {
12+
color: blue;
13+
color: orange; }
14+
/* line 12, inputs/at_root.scss */
15+
.nested2 {
16+
color: yellow; }
17+
/* line 22, inputs/at_root.scss */
18+
.third {
19+
color: green; }

0 commit comments

Comments
 (0)