Section
A section is the building block of the page, below is an example of a header section.
TIP
Examples use pug template language to make it easier to work with templates.
<template lang="pug">
section.header(
v-styler="$sectionData.classes"
:class="[{'is-editable': $builder.isEditing}, $sectionData.classes]"
)
.container
.grid
.column.is-desktop-6.add-center-vertical
h3.header-title(
:class="{'is-editable': $builder.isEditing}"
v-html="$sectionData.title"
v-styler="$sectionData.title"
)
p.header-content(
:class="{'is-editable': $builder.isEditing}"
v-html="$sectionData.content"
v-styler="$sectionData.content"
)
a.button(
:class="[{'is-editable': $builder.isEditing}, $sectionData.button.classes]"
:href="$sectionData.button.href"
v-html="$sectionData.button.text"
v-styler="$sectionData.button"
)
.column.is-desktop-6
uploader(
class="header-image"
path="$sectionData.images[0]"
)
</template>
<script>
import { types } from 'vuse';
export default {
name: 'hero1',
cover: '../covers/hero1.png',
$schema: {
title: types.Title,
content: types.Text,
images: [types.Image],
button: types.Button,
classes: types.ClassList
},
props: {
id: {
type: Number,
required: true
}
}
};
</script>
Each section has several elements that can be edited. Section data are stored in $sectionData
object which is reactive.
Adding the ability to edit elements in a section
- Add
is-editable
class to it. Since editable state can be toggled off/on, it's always good to bindis-editable
class to change when editing mode changes. e.g.:class="{'is-editable': $builder.isEditing}"
- Add
v-styler
directive to the element - Bind the element’s innerHTML with its equivalent data e.g.
v-html="$sectionData.button.text"
- If you have any other data that
v-styler
changes, you have to bind it too. e.g.:href="$sectionData.button.href"
Putting it all together
<a
:class="[{'button', 'is-editable': $builder.isEditing}, $sectionData.button.classes]"
:href="$sectionData.button.href"
v-html="$sectionData.button.text"
v-styler="$sectionData.button"
></a>
After creating the HTML structure, you should configure the section schema to use the built-in seeder to provide you with initial/fake values when the component is instantiated in build/edit mode. Or you can set the initial values yourself instead of seeding them.
<script>
import { types } from 'vuse';
export default {
// section name
name: 'hero1',
// section cover image
cover: '../cover-hero1.png',
// group multiple sections
group: 'heros',
// section data schema
$schema: {
// main title
title: types.Text,
// main content
content: types.Text,
// section classes
classes: types.ClassList,
// array of section's images
images: [
types.Image,
types.Image
],
// object holds button data, href etc..
button: types.Button,
// if section has many columns you can use
// a columns array to separate each column's data
columns: [
{
title: types.Title,
content: types.Text,
group: types.group
},
{
title: types.Title,
group: types.group
}
]
},
props: {
id: { type: Number, required: true } // it is required to have an id prop.
}
};
</script>
Using the section
Until now, we have only been creating our section component, we now need to introduce it to our builder so it can use it:
import Builder from 'vuse';
import section from './components/sections/section';
// Builder has Vue-like API when registering components.
Builder.component(section);
Vue.use(Builder);
new Vue({
el: '#app'
});
<div id="app">
<b-builder></b-builder>
</div>
You only have to register the component on the Builder plugin, which has a Vue-like API. This ensures your Vue global scope isn't polluted by the builder and keeps everything contained within the b-builder
component.