Layout Builderに独自のレイアウトを追加する方法

前回Layout Builderを使ってみようでは、Layout Builderモジュールの簡単な使い方についてご説明しました。そのときはDrupalコアですでに用意されているレイアウトを使用したのですが、もちろん独自のレイアウトを追加することも可能です。今回はLayout Builderに独自のレイアウトを追加する方法をご説明いたします。今回の内容は開発者向けのお話となります。
※2018年11月現在、Layout Builderモジュールは試験的モジュールです。今後変更される可能性がありますので、本番サイトではまだ使用しないでください。
独自のレイアウトを提供するカスタムモジュールを作成する
それではレイアウトを追加する手順を見ていきましょう。 今回は例として以下の画像のような、サイドバー付きのsidebarレイアウトを追加したいと思います。

レイアウトの基礎を作成する
レイアウトの基礎部分を作成します。まずはレイアウト作成画面で新たなレイアウトを選択できるようにしていきます。
- まずはカスタムモジュールを作成し、
*.info.ymlファイルを作成します。例ではcustom_layoutモジュールとして、custom_layout.info.ymlを作成します。 - カスタムモジュールの直下に、レイアウトを定義するための
*.layouts.ymlファイルを作成します。例ではcustom_layout.layouts.ymlファイルを作成します。 *.layouts.ymlファイルに以下の内容を入力します。設定する項目の詳細については後述の補足1でご説明します
sidebar:
label: 'Sidebar'
category: 'My layouts'
template: templates/sidebar
library: custom_layout/sidebar
regions:
top:
label: Top
first:
label: First
second:
label: Second
bottom:
label: Bottom
sidebar:
label: Sidebar
- sidebarレイアウトのテンプレートファイルを作成します。カスタムモジュールの直下に、
templatesディレクトリを作成し、その中にsidebar.html.twigファイルを作成してます。 sidebar.html.twigファイルに以下の内容を入力します。こちらも詳細については補足2でご説明します。
{% if content %}
<div>
<div class="layout-main-content">
{% if content.top %}
<div>
{{ content.top }}
</div>
{% endif %}
{% if content.first %}
<div>
{{ content.first }}
</div>
{% endif %}
{% if content.second %}
<div>
{{ content.second }}
</div>
{% endif %}
{% if content.bottom %}
<div>
{{ content.bottom }}
</div>
{% endif %}
</div>
<div class="layout-sidebar">
<div region_attributes.sidebar div>
{{ content.sidebar }}
</div>
</div>
</div>
{% endif %}
以上が完了したら、レイアウト作成画面を確認してみましょう。Add Sectionをクリックすると、Sidebarレイアウトが新しく選択できるようになっていると思います。

レイアウトにCSSを適用する
レイアウトの追加はできましたが、今のままではサイドバーのようなスタイルが適用されておりません。そこでSidebarレイアウトにCSSを適用します。
- CSSを作成します。モジュールの直下にcssディレクトリを作成し、その中に
sidebar.cssを作成します。 sidebar.cssファイルに以下の内容を入力します。
.layout--sidebar {
display: flex;
}
.layout--sidebar > .layout-main-content {
width: 70%;
display: flex;
flex-wrap: wrap;
}
.layout--sidebar > .layout-sidebar {
width: 30%;
}
.layout--sidebar > .layout-main-content > .layout-main-content__region {
flex: 0 1 100%;
}
.layout--sidebar > .layout-main-content > .layout-main-content__region--first,
.layout--sidebar > .layout-main-content > .layout-main-content__region--second {
flex: 0 1 50%;
}
- モジュール直下に
*.libraries.ymlファイルを作成し、以下の内容を追加します。例ではcustom_layout.libraries.ymlを作成します。
sidebar:
version: 1.x
css:
theme:
css/sidebar.css: {}
*.layouts.ymlにlibrary情報を追加します。
sidebar:
label: 'Sidebar'
# 〜略〜
library: custom_layout/sidebar
regions:
# 〜略〜
以上が完了したらキャッシュクリアして、レイアウト作成画面を確認してみましょう。Sidebarレイアウトを選択すると、それっぽいスタイルが適用されているかと思います。

アイコンの登録
最後にアイコンを設定します。ここでいうアイコンとはレイアウトを選択するときに表示される、レイアウトの概要を模した画像のことです。
驚くことにアイコン用の画像を用意する必要はありません。`*.layouts.yml`に設定をしておくだけで、自動でSVG化して表示されます。
以下のようにicon_mapを定義すると、アイコンが表示されるようになります。
sidebar:
label: 'Sidebar'
# 〜略〜
icon_map:
- [top, top, sidebar]
- [first, second, sidebar]
- [bottom, bottom, sidebar]
regions:
# 〜略〜
icon_mapは二次元配列で定義します。配列の要素は*.layouts.ymlに定義したリージョン名にしておくと良いでしょう。
topやbottomのように複数列にまたがるリージョンは、top, topのように同じリージョン名を続けて設定します。また、sidebarのように複数行にまたがるリージョンの場合も、各行の同じ位置(例だと3列目)に同じリージョン名を設定します。
キャッシュクリアしてレイアウト作成画面を確認すると、Sidebarレイアウトにアイコンが表示されています。
![]()
今回作成したモジュールの構成
今回作成したcustom_layoutモジュールの最終的な構成は以下のようになります。

補足1 layouts.ymlファイルの項目について
*.layouts.ymlには以下のキーが必須です
| label | 人が識別するための名前です。 |
|---|---|
| category | レイアウトが所属するカテゴリ名です |
| regions | レイアウト内にあるリージョンの配列です。キーはリージョンの内部名称で、値には以下の要素が含まれます。 label: 人が識別するためのリージョン名です(必須項目です)。 |
| theme | レイアウトを描画するためのテーマフックを指定します。この項目を指定する場合は後述のtemplateは指定できません |
| template | レイアウトを描画するためのテンプレートを、html.twig抜きで相対パスで指定します。この項目が指定された場合、テンプレートは自動的にテーマシステムに登録されます。また、この項目を指定する場合は前述のthemeは指定できません |
以下は省略可能なオプションキーです。
| default_region | デフォルトリージョンの内部名称です。 |
|---|---|
| icon_map | レイアウトビルダーのUIで使用するアイコンをYML形式で記述します。 |
| description | レイアウトに関する説明です。 |
| path | テンプレートなどのリソースまでの相対パスです。 |
| library | このレイアウトのためにロードするライブラリです。この項目を使う場合、レイアウトを登録しているモジュールまたはテーマは、*.libraries.ymlファイル内に対象のライブラリが登録されている必要があります。 |
補足2 レイアウトで使用するtwigについて
他のtwigテンプレートと基本的には変わりません。content.topのようにcontentの後にリージョン名を指定すると、そのリージョンに登録されているコンテンツを出力します。
注意点としては、以下をお守りいただいた方が良さそうです(ドラッグアンドドロップでブロックを設置した際、Javascriptエラーとなって設置ができません)。
- レイアウト全体はdiv等で囲み、
<div attributes>のように変数attributesを展開してください - 変数
region_attributesには各リージョンに必要な属性が含まれています。
各リージョンのルートでは`




