Passed
Pull Request — 2.x (#1308)
by Harings
07:25
created

HasBlocks::getBlockClass()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 9
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 6

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 2
eloc 6
c 1
b 0
f 0
nc 2
nop 3
dl 0
loc 9
rs 10
ccs 0
cts 0
cp 0
crap 6
1
<?php
2
3
namespace A17\Twill\Models\Behaviors;
4
5
use A17\Twill\Helpers\TwillBlock;
6
use A17\Twill\Models\Block;
7
use Illuminate\Support\Str;
8
9 21
trait HasBlocks
10
{
11 21
    /**
12
     * Defines the one-to-many relationship for block objects.
13
     *
14 2
     * @return \Illuminate\Database\Eloquent\Relations\MorphMany
15
     */
16 2
    public function blocks()
17 2
    {
18 2
        return $this->morphMany(Block::class, 'blockable')->orderBy(
0 ignored issues
show
Bug introduced by
It seems like morphMany() must be provided by classes using this trait. How about adding it as abstract method to this trait? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

18
        return $this->/** @scrutinizer ignore-call */ morphMany(Block::class, 'blockable')->orderBy(
Loading history...
19
            config('twill.blocks_table', 'twill_blocks') . '.position',
20 2
            'asc'
21
        );
22
    }
23 2
24
    public function renderNamedBlocks($name = 'default', $renderChilds = true, $blockViewMappings = [], $data = [])
25
    {
26 2
        return $this->blocks
27
            ->filter(function ($block) use ($name) {
28 2
                return $name === 'default'
29
                    ? ($block->editor_name === $name || $block->editor_name === null)
30 2
                    : $block->editor_name === $name;
31 2
            })
32
            ->where('parent_id', null)
33
            ->map(function ($block) use ($blockViewMappings, $renderChilds, $data) {
34 2
                if ($renderChilds) {
35
                    $childBlocks = $this->blocks->where('parent_id', $block->id);
36 2
37
                    $renderedChildViews = $childBlocks->map(function ($childBlock) use ($blockViewMappings, $data) {
38 2
                        $view = $this->getBlockView($childBlock->type, $blockViewMappings);
39
40
                        if ($class = $this->getBlockClass($view, $childBlock, $data)) {
41
                            $data = $class->getData();
42 2
                        }
43
44
                        return view($view, $data)->with('block', $childBlock)->render();
45
                    })->implode('');
46
                }
47
48
                $block->childs = $this->blocks->where('parent_id', $block->id);
49
50
                $view = $this->getBlockView($block->type, $blockViewMappings);
51
52
                if ($class = $this->getBlockClass($view, $block, $data)) {
53
                    $data = $class->getData();
54
                }
55
56
                return view($view, $data)->with('block', $block)->render() . ($renderedChildViews ?? '');
57
            })->implode('');
58
    }
59
60
    private function getBlockClass(string $view, Block $block, array $data): ?TwillBlock
61
    {
62
        $exploded = explode('.', $view);
63
        $transformed = Str::studly(array_pop($exploded)) . 'Block';
64
        $className = "\App\Twill\Block\\$transformed";
65
        if (class_exists($className)) {
66
            return new $className($block, $data);
67
        }
68
        return null;
69
    }
70
71
    /**
72
     * Returns the rendered Blade views for all attached blocks in their proper order.
73
     *
74
     * @param bool $renderChilds Include all child blocks in the rendered output.
75
     * @param array $blockViewMappings Provide alternate Blade views for blocks. Format: `['block-type' => 'view.path']`.
76
     * @param array $data Provide extra data to Blade views.
77
     * @return string
78
     */
79
    public function renderBlocks($renderChilds = true, $blockViewMappings = [], $data = [])
80
    {
81
        return $this->renderNamedBlocks('default', $renderChilds, $blockViewMappings, $data);
82
    }
83
84
    private function getBlockView($blockType, $blockViewMappings = [])
85
    {
86
        $view = config('twill.block_editor.block_views_path') . '.' . $blockType;
87
88
        if (array_key_exists($blockType, $blockViewMappings)) {
89
            $view = $blockViewMappings[$blockType];
90
        }
91
92
        return $view;
93
    }
94
}
95