Skip to content

Commit 2a78d16

Browse files
authored
Merge pull request #37 from Paneon/master
Update master
2 parents a3b9275 + 20d8564 commit 2a78d16

12 files changed

+154
-19
lines changed

src/Compiler.php

Lines changed: 20 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -122,7 +122,7 @@ class Compiler
122122
protected $attributesWithIf = ['checked', 'selected', 'disabled'];
123123

124124
/**
125-
* @var array
125+
* @var int[]
126126
*/
127127
protected $slotFallbackCounter = [];
128128

@@ -227,15 +227,16 @@ public function convert(): string
227227
$resultNode = $this->convertNode($templateElement);
228228
$html = $this->document->saveHTML($resultNode);
229229

230-
if (count($this->rawBlocks)) {
231-
$html = implode("\n", $this->rawBlocks) . "\n" . $html;
232-
}
233-
234230
if (!$html) {
235231
throw new Exception('Generating html during conversion process failed.');
236232
}
237233

238-
$html = $this->addVariableBlocks($html);
234+
$this->rawBlocks[] = $this->createVariableBlock();
235+
236+
if (count($this->rawBlocks)) {
237+
$html = implode("\n", $this->rawBlocks) . "\n" . $html;
238+
}
239+
239240
$html = $this->replacePlaceholders($html);
240241
$html = $this->replaceScopedPlaceholders($html);
241242
$html = $this->replaceAttributeWithIfConditionPlaceholders($html);
@@ -350,7 +351,7 @@ public function convertNode(DOMNode $node, int $level = 0): DOMNode
350351
$include = $this->document->createTextNode(
351352
$this->builder->createIncludePartial(
352353
$usedComponent->getPath(),
353-
$this->preparePropertiesForInclude($usedComponent->getProperties()),
354+
$this->preparePropertiesForInclude($usedComponent->getProperties(), $level === 1),
354355
$this->vBind
355356
)
356357
);
@@ -414,7 +415,7 @@ public function convertNode(DOMNode $node, int $level = 0): DOMNode
414415
*
415416
* @return Property[]
416417
*/
417-
private function preparePropertiesForInclude(array $variables): array
418+
private function preparePropertiesForInclude(array $variables, bool $isRootNode = false): array
418419
{
419420
$values = [];
420421
$hasScopedStyleAttribute = false;
@@ -457,11 +458,15 @@ private function preparePropertiesForInclude(array $variables): array
457458
if ($attribute === 'style') {
458459
$glue = ' ~ "; " ~ ';
459460
}
460-
$variables[] = new Property(
461-
$attribute,
462-
$values[$attribute] ?? null ? implode($glue, $values[$attribute]) : '""',
463-
false
464-
);
461+
$value = $values[$attribute] ?? null ? implode($glue, $values[$attribute]) : '""';
462+
if ($isRootNode) {
463+
$value = $value . $glue . $attribute . '|default(\'\')';
464+
}
465+
$variables[] = new Property($attribute, $value, false);
466+
}
467+
468+
if ($isRootNode) {
469+
$variables[] = new Property('dataScopedStyleAttribute', 'dataScopedStyleAttribute|default(\'\')', false);
465470
}
466471

467472
return $variables;
@@ -1287,15 +1292,15 @@ protected function addVariable(string $name, $value): void
12871292
$this->variables[$name] = $value;
12881293
}
12891294

1290-
protected function addVariableBlocks(string $string): string
1295+
protected function createVariableBlock(): string
12911296
{
12921297
$blocks = [];
12931298

12941299
foreach ($this->variables as $varName => $varValue) {
12951300
$blocks[] = $this->builder->createMultilineVariable($varName, $varValue);
12961301
}
12971302

1298-
return implode('', $blocks) . $string;
1303+
return implode('', $blocks);
12991304
}
13001305

13011306
/**

src/Utils/StyleBuilder.php

Lines changed: 23 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -93,11 +93,30 @@ public function compile(?DOMElement $styleElement): ?string
9393

9494
if ($styleElement->hasAttribute('scoped')) {
9595
$this->hasScoped = true;
96-
$style = preg_replace(
97-
'/((?:^|\s)\s*[^@\s,][a-z0-9-_]+?)((?::{1,2}[a-z-]+)?\s*[{,])/i',
98-
'$1[' . $this->scopedAttribute . ']$2',
99-
$style
96+
preg_match_all(
97+
'/(?:^|\s)\s*[^@\s][\.a-z0-9-_:,\/\s]+?\s*[{]/i',
98+
$style,
99+
$matches,
100+
PREG_SET_ORDER
100101
);
102+
foreach ($matches as $match) {
103+
$selectors = explode(',', $match[0]);
104+
$selectorsCount = count($selectors);
105+
$count = 0;
106+
foreach ($selectors as $selector) {
107+
if (++$count < $selectorsCount) {
108+
$selector .= ',';
109+
}
110+
$regex = strpos($selector, '/deep/') !== false
111+
? '/((?:^|\s)\s*[^@\s][a-z0-9-_]+?)((?::{1,2}[a-z-]+)?\s*)(?:\/deep\/)/i'
112+
: '/((?:^|\s)\s*[^@\s][a-z0-9-_]+?)((?::{1,2}[a-z-]+)?\s*(?:[,{]|$))/i';
113+
$style = str_replace(
114+
$selector,
115+
preg_replace($regex, '$1[' . $this->scopedAttribute . ']$2', $selector),
116+
$style
117+
);
118+
}
119+
}
101120
}
102121

103122
return '<style>' . $style . '</style>';
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
<style>
2+
.foo[data-v-9a0d9603def78653cb6bac3e7905721b] { transition: all 400ms ease; overflow: hidden; will-change: height, margin, padding, opacity; }
3+
</style>
4+
<div class="foo {{ class|default('') }}" data-v-9a0d9603def78653cb6bac3e7905721b {{ dataScopedStyleAttribute|default('') }} style="{{ style|default('') }}"></div>
Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
<template>
2+
<div class="foo"></div>
3+
</template>
4+
5+
<style scoped>
6+
.foo {
7+
transition: all 400ms ease;
8+
overflow: hidden;
9+
will-change: height, margin, padding, opacity;
10+
}
11+
</style>
12+
13+
<script>
14+
export default {
15+
}
16+
</script>
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
<style>.grow-enter[data-v-de62703e2bdacde95c4bc73d69f14aa5], .grow-leave-to[data-v-de62703e2bdacde95c4bc73d69f14aa5] { width: 0 !important; }.grow-enter-active[data-v-de62703e2bdacde95c4bc73d69f14aa5], .grow-leave-active[data-v-de62703e2bdacde95c4bc73d69f14aa5] { transition: width 0.6s ease; }</style>
2+
<div class="bar {{ class|default('') }}" data-v-de62703e2bdacde95c4bc73d69f14aa5 {{ dataScopedStyleAttribute|default('') }} style="{{ style|default('') }}"></div>
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
<template>
2+
<div class="bar">
3+
</div>
4+
</template>
5+
6+
<script lang="ts">
7+
import { Vue, Component } from 'vue-property-decorator';
8+
9+
@Component
10+
export default class Progressbar extends Vue {
11+
}
12+
</script>
13+
14+
<style lang="scss" scoped>
15+
.grow-enter,
16+
.grow-leave-to {
17+
width: 0 !important;
18+
}
19+
.grow-enter-active,
20+
.grow-leave-active {
21+
transition: width 0.6s ease;
22+
}
23+
</style>
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
<style>
2+
.foo[data-v-34e67cc3ec28c53ca40eb2cd78aa6d35] { color: red; }
3+
.foo[data-v-34e67cc3ec28c53ca40eb2cd78aa6d35] .bar { color: blue; }
4+
</style>
5+
<div data-v-34e67cc3ec28c53ca40eb2cd78aa6d35 {{ dataScopedStyleAttribute|default('') }} class="{{ class|default('') }}" style="{{ style|default('') }}">
6+
<div class="foo" data-v-34e67cc3ec28c53ca40eb2cd78aa6d35>
7+
foo
8+
</div>
9+
</div>
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
<template>
2+
<div>
3+
<div class="foo">
4+
foo
5+
</div>
6+
</div>
7+
</template>
8+
9+
<style scoped>
10+
.foo {
11+
color: red;
12+
}
13+
.foo /deep/ .bar {
14+
color: blue;
15+
}
16+
</style>
17+
18+
<script>
19+
export default {
20+
}
21+
</script>
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
{% include "/templates/ChildComponent.twig" with { 'slot_default': "", 'class': "foo" ~ " " ~ class|default(''), 'style': "color: black" ~ "; " ~ style|default(''), 'dataScopedStyleAttribute': dataScopedStyleAttribute|default('') } %}
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
<template>
2+
<ChildComponent class="foo" style="color: black" />
3+
</template>
4+
5+
<script>
6+
export default {
7+
name: 'ComponentWithComponentOnRoot',
8+
component: {
9+
ChildComponent,
10+
}
11+
};
12+
</script>
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
{% set text = text|default('foo') %}
2+
{% set slot_default_fallback %}{{ text }}{% endset %}
3+
{% set slot_default_value %}{{ slot_default|default(slot_default_fallback) }}{% endset %}
4+
{% include "/templates/ChildComponent.twig" with { 'slot_default': slot_default_value, 'class': "", 'style': "" } %}
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
<template>
2+
<ChildComponent>
3+
<slot>{{ text }}</slot>
4+
</ChildComponent>
5+
</template>
6+
<script>
7+
export default {
8+
name: 'ComponentWithSlot',
9+
component: {
10+
ChildComponent,
11+
},
12+
props: {
13+
text: {
14+
type: String,
15+
default: 'foo'
16+
},
17+
},
18+
};
19+
</script>

0 commit comments

Comments
 (0)