Blocks


Registering and compiling blocks might take a bit to wrap your head around, but it offers more flexibility, which is the trade-off.

Your can include any css or javascript using the Enqueue Assets options in the config

First lets take a look on how to register a block:

'blocks' => [
        [
            'name' => 'testimonials',
            'title' => 'Testimonials',
            // FontAwesome without the fa- prefix
            'icon' => 'quote-right',
            // Setting a group to true will allow for 
            // nested or repeated blocks. 
            // For example when using a carousel or quotes.
            'group' => true,
            'options' => [],
            // List all fields in the block. 
            // allow_blocks will enable the block picker.
            'fields' => [
                ['name' => 'quote' , 'value' => '', 'placeholder' => 'Quote', 'allow_blocks' => false] ,
                ['name' => 'author', 'value' => '', 'placeholder' => 'Author, Position', 'allow_blocks' => false] ,
                ['name' => 'image', 'value' => '', 'placeholder' => 'Author Image', 'allow_blocks' => true ]
            ],
            // Options for each grouped item. You can bascially do anything you want.
            'group_options' => [
                [ 'type' => 'color', 'name' => 'background_color' , 'label' => 'Background Color', 'value' => '' ],
                [ 'type' => 'text', 'name' => 'padding', 'label' => 'Padding', 'value' => '0px' ],
                [ 'type' => 'dropdown', 'name' => 'text_alignment', 'label' => 'Text Alignment', 'value' => '', 'options' => [
                        ['label' => 'Left', 'value' => 'left'],
                    ]
                ],
            ],
            // Neutrino has both a CMS template and the view compiler.
            // This allows easier customization for the admin area versus the compiled view
            'template'  => 'Newelement\\Neutrino\\Http\\Controllers\\BlocksController@testimonial',
            'compiler' => 'Newelement\\Neutrino\\Http\\Controllers\\BlocksController@testimonialCompiler'
        ]
    ],

Once a block is registered you will need to create the template that a user will see when adding content to the block.

The admin template is written in vue js, in a blade. Hold on before you freak out. We are doing this so you can easier pass data to your blade like you normally would from a controller.

Inside your template blade you will create how the block will look in the admin area.

$blockData is the config data passed to the compiler.

public function testimonial($blockData)
{
    $html = view('neutrino::blocks.testimonials.testimonials', [ 'data' => $blockData ])->render();
    return  $html;
}

In this blade example we are using the parent draggable element since there can be more than one testimonial from group = true.

The testimonials blade:

<draggable v-if="block.field_groups" v-model="block.field_groups" class="testimonials"  group="blockitems" handle=".block-item-drag-handle">
    <div v-for="(blockItem, itemIndex) in block.field_groups" class="testimonial" style="margin-bottom: 32px;">
        <block-item-actions :block-item="blockItem" :block-index="blockIndex"></block-item-actions>
        <div class="author-quote">
            <div class="quote">
                <tinymce-editor v-model="blockItem.fields[0].value" :init="$root.tinyInitInlineBlockquote" :tag-name="$root.tag.p" inline></tinymce-editor>
            </div>
            <div class="author">
                <tinymce-editor v-model="blockItem.fields[1].value" :init="$root.tinyInitInlineParagraph" :tag-name="$root.tag.p" inline></tinymce-editor>
            </div>
        </div>
        <div class="author-image" :style="'background-image: url(' +  blockItem.fields[2].value +')' ">
            <child-block-chooser :field="blockItem.fields[2]" />
            <child-blocks :field="blockItem.fields[2]" />
            <button type="button" class="btn btn-dark btn-sm" @click.prevent="chooseBlockImage( blockIndex, itemIndex, 2 )">Choose Image</button>
        </div>
    </div>
</draggable>

Now you will to compile your block for the HTML output.

public function testimonialCompiler($json)
{
    $html = view('neutrino::blocks.testimonials.testimonials-compiled', [ 'data' => $json ])->render();
    return  $html;
}

The testimonials-compiled blade:

Note: the blade directives were removed because Laravel will try to compile the below example.

<div class="testimonials">
    foreach( $data->field_groups as $quote )
    <div class="testimonial">
        <div class="author-quote">
            <div class="quote">
            getBlockField($quote, 'quote')
            </div>
            <div class="author">
            getBlockField($quote, 'author')
            </div>
        </div>
        <div class="author-image" style="background-image: url(' getBlockField($quote, 'image') ')">
        </div>
    </div>
    endforeach
</div>