WordpressのGutenbergでできるカスタマイズ・開発に役立つことをまとめてみる

Wordpress5.0リリースから標準エディターとなったGutenergのカスタマイズが結構充実しているので自分が主に使っているもの、使う予定のものをメモ。
随時追加していく予定です。

#開発環境
Wordpress 5.0
create-guten-block 1.13.0
npm 6.4.1
node 10.13.0

ブロックのカスタマイズをする場合、[create-guten-block](https://github.com/ahmadawais/create-guten-block)を使うとほとんど設定を行う必要なく開発ができます。
実装方法など[こちら](https://qiita.com/yumayamada1029/items/2da4044afe56b5677012)でまとめてます。

#ブロックのカスタマイズ
独自のブロック要素の追加や既存のブロックのカスタマイズについて。

##ブロックの追加
registerBlockType関数で独自のブロック要素を登録します。
registerBlockTypeの第一引数にブロック要素の名前を入れるのですが、「名前空間/ブロック名」という形式で指定する必要があります。
名前空間はプラグイン名(create-guten-blockなどでプラグイン化してブロック要素を作成する場合)か、テンプレートの名前を入れます。
第二引数に詳細な設定をしていきます。

各種詳細な設定は[こちら](https://wordpress.org/gutenberg/handbook/designers-developers/developers/block-api/block-registration/)で参照可能です。(後日追記予定)

```block.js
registerBlockType( 'my-plugin/my-block', {
	title: 'my-block', //ブロック要素のタイトル,(required)
	description: 'this is a my-block description', //ブロックの説明
	category: 'layout', // common,formatting,layout,widgets,embedから選択(required）
	icon: 'book-alt', //　https://developer.wordpress.org/resource/dashicons/ から指定,
	keywords: [ image, photo, pics ], //ブロック要素検索時のタグキーワード
	styles: [
		// ブロック要素のスタイルを設定
		{
			name: 'default', //.is-style-defaultクラスが生成される
			label: __( 'Rounded' ), //エディターでの表示名
			isDefault: true, //trueでこれがデフォルトスタイルになる
		},
		{
			name: 'squared', //.is-style-squaredクラスが生成される
			label: __( 'Squared' ),
		},
	],
	attributes: {
		//ブロック要素内のコンテンツをどのように表示させるか、という属性を指定する(https://wordpress.org/gutenberg/handbook/designers-developers/developers/block-api/block-attributes/)
		content: {
			type: 'string',
			source: 'html',
			selector: 'p',
		},
		align: {
			type: 'string',
		},
	},
	transforms: {
		//ブロックタイプの変更
		from: [
			//どのブロックタイプから変更できるようにするか
			{
				type: 'block',
				blocks: [ 'core/paragraph' ],
				transform: function( content ) {
					return createBlock( 'core/heading', {
						content,
					} );
				},
			},
		],
		to: [
			//どのブロックタイプへ変更できるようにするか
			{
				type: 'block',
				blocks: [ 'core/paragraph' ],
				transform: function( content ) {
					return createBlock( 'core/paragraph', {
						content,
					} );
				},
			},
		],
	},
	parent: [ 'core/columns' ], //ブロック要素を入れ子にする場合、入れ子にできるブロックを指定する
	supports: {
		//save関数で返される要素に対する設定
		align: true, //(default:false) ブロックのalign設定。配列で個別指定も可能 (left, center, right, wide, full)
		alignWide: false, //(default:true)全幅・幅広表示の設定。falseで無効にする
		anchor: true, //(default:false)アンカーリンクの設定。
		customClassName: false, //(default:true)クラス名の設定。有効にするとオリジナルのクラス名を入力する欄が表示される。
		className: false, //(default:true)ブロック要素を作成した際に付く　.wp-block-[ブロック名]で自動生成されるクラス名の設定。
		html: false, //(default:true)HTMLでの編集設定。通常Gutenbergはビジュアル編集ですが、trueでHTML編集が選択可能になります。
		inserter: false, //(default:true)trueで「ブロックの追加」ボタンからこのブロック要素を選択可能にします。falseでブロック要素の選択画面からこのブロック要素を隠します。
		multiple: false, //(default:true)trueでこのブロック要素を一つのページで複数作成可能になります。
		reusable: false, //(default:true)trueで再利用可能なブロックに追加する設定が選択可能になります。
	},
	edit() {
		//エディターでの表示設定
		return 'テスト';
	},
	save() {
		//公開記事での表示設定
		return 'テスト';
	},
} );

```

###edit関数

edit関数はregisterBlockType関数で登録したブロック要素をエディター画面でどのように表示させるかという設定を行います。
この関数は以下の引数を受け取ります。

####attributes
registerBlockType関数のattributesに設定した値を取得できます。
例えば、上記コードのattributesにはalignとcontentの設定をしているため、それぞれattributes.align, attributes.contentでそれぞれの値を取得できます。

```jsx

edit( { attributes } ) {
    return <div style={ { textAlign: attributes.align } }>{ attributes.content }</div>;
}
```

####className
公開記事上で自動的に追加されるクラス(`.wp-block-`)を取得できます。
このクラス名はエディター内では自動適用されないため、独自に`.wp-block-`にスタイルを追加している場合に要素に追加して使うことができます。

```jsx
edit( { attributes, className } ) {
    return <div className={ className }>{ attributes.content }</div>;
}
```

####isSelected
ブロック要素が現在選択されているかどうかを取得できます。

####setAttributes
各attributesの値に対してユーザー側の入力があった場合、更新された値を取得できます。

```jsx

edit( { attributes, className, setAttributes } ) {
		const { content, align } = attributes;

		function onChangeContent( newContent ) {
			setAttributes( { content: newContent } );
		}

		function onChangeAlignment( newAlignment ) {
			setAttributes( { align: newAlignment } );
		}

		return (
			<Fragment>
				<div className={ className }>
					<RichText
						key="editable"
						tagName="p"
						style={ { textAlign: align } }
						onChange={ onChangeContent }
						value={ content }
					/>
				</div>
			</Fragment>
		);
	},
```

###save関数

save関数はregisterBlockType関数で登録したブロック要素を公開記事上でどのように表示させるかという設定を行います。
この関数は以下の引数を受け取ります。

####attributes
edit関数と同様、registerBlockType関数のattributesに設定した値を取得できます。


edit関数,save関数の設定は[こちら](https://wordpress.org/gutenberg/handbook/designers-developers/developers/block-api/block-edit-save/)で参照可能です。

###attributesについて
registerBlockType関数におけるattributesは、保存された記事のマークアップから該当するattributes(content,align等)を抽出するために使用されます。

例えば、段落ブロックをattributesのalignのcenter（text-alignを定義するattributes）を使用した場合と使用していない場合、以下のように表示されます。
![a2c1ff43024843f6d397633913aad54b.png](https://qiita-image-store.s3.amazonaws.com/0/100132/929fa5bb-c6a3-834b-33ea-8f31ea6e6b49.png)

一方で、これをクラシックエディター(wordpress5.0以前のテキストエディター)で表示させると以下のように表示されます。
ブロックの箇所が`<!-- -->`で表現され、その内部にコンテンツが入力されます。
attributesに属するコンテンツがあった場合、`<!-- wp:paragraph {"align":"center"} -->`のように使用しているattributesがオブジェクト型で表示され、このオブジェクトに対応した表示がブロックエディターで行われます。

```html

<!-- wp:paragraph -->
<p>これは段落ブロックです。こっちはattributesに属していません。</p>
<!-- /wp:paragraph -->

<!-- wp:paragraph {"align":"center"} -->
<p style="text-align:center">これは段落ブロックです。alignのattributesに属しています。</p>
<!-- /wp:paragraph -->

```


#エディターのカスタマイズ
エディター、公開記事のレイアウト、デザインのカスタマイズ方法など

##背景色、テキストカラーを色指定タブに追加する
デフォルトで数種類の背景色、テキストカラーが用意されているのですが、これらの他に追加ができます。
以下のコードを追加するとデフォルトの11色が上書きされ、コードに追加された色のみが適用されます。

![f8a8160d4852c6adb27f73cbe32a05a2.png](https://qiita-image-store.s3.amazonaws.com/0/100132/370240d6-7aa6-8d60-205f-ae9c1e75c5fd.png)


```functions.php
function mytheme_setup_theme_supported_features()
{
    add_theme_support('editor-color-palette', array(
        array(
            'name' => __('black', 'themeLangDomain'),
            'slug' => 'black',
            'color' => '#000',
        ),
        array(
            'name' => __('white', 'themeLangDomain'),
            'slug' => 'white',
            'color' => '#fff',
        ),
    ));
}
```

公開記事にも同様のスタイルを適用するため、has-[slugに追加した文字列]-background-color,has-[slugに追加した文字列]-colorをcssに追加します。

```style.css
.has-black-background-color {
    background-color: #000;
}

.has-black-color {
    color: #000;
}
```

##カラーの自由な指定を無効にする
デフォルトでユーザー側で色をカスタマイズできるカラーパレットがあるのですが、これを以下のコードで無効化できます。
![スクリーンショット 2018-12-10 18.02.34.png](https://qiita-image-store.s3.amazonaws.com/0/100132/663dfcc5-20f7-238b-0bef-0b225cc36fc1.png)

```functions.php
add_theme_support( 'disable-custom-colors' );
```

##フォントサイズのセットを作成する
フォントのサイズのセット(小、標準、大、特大等）を作成できます。
以下のコードを追加するとデフォルトのセットが上書きされ、指定したセットが追加されます。

```functions.php

add_theme_support( 'editor-font-sizes', array(
    array(
        'name' => __( 'regular', 'themeLangDomain' ),
        'shortName' => __( 'M', 'themeLangDomain' ),
        'size' => 16,
        'slug' => 'regular'
    )
) );

```

公開記事にも同様のスタイルを適用するため、has-[slugに追加した文字列]-font-sizeをcssに追加します。

```style.css
.has-regular-font-size {
    font-size: 16px;
}
```

##フォントサイズの自由な指定を無効にする
デフォルトでユーザー側でフォントサイズを自由に指定できるのですが、これを以下のコードで無効化できます。
これにより、デフォルトまたはカスタマイズで追加したフォントサイズのセットのみが指定できるようになります。

```functions.php
add_theme_support('disable-custom-font-sizes');
```

##画像の幅広・全幅表示を有効にする
画像の幅を100%で表示させたい場合、以下のコードで有効にします。

```functions.php
add_theme_support( 'align-wide' );
```

すると、画像ブロックを指定した際にエディタ上部に「幅広」「全幅」のオプションが表示されます。
![8ff8be338e250eb70eaf622037a957c9.png](https://qiita-image-store.s3.amazonaws.com/0/100132/918abf62-decc-8801-05fc-4eb6257ad6a0.png)


現状デフォルトのCSSはwidth:100%が追加されるのみで、公開記事での表示は変化がありません。
「幅広」でimg要素のラッパー要素(figure要素)に対して.alignwideが、「全幅」で.alignfullクラスが追加されるため、このクラスに対してスタイルを追加してカスタマイズするといった使い方ができそうです。

##iframeをレスポンシブ対応(16:9)にする
Gutenbergの埋め込みブロックから埋め込みを行うとレスポンシブではありませんが、以下のコードを記述することで16:9のアスペクト比を保って表示させます。

```functions.php
add_theme_support( 'responsive-embeds' );
```

##独自のCSSを適用する
add_editor_styleでCSSを適用します。
ここで指定したCSSはエディターのみに適用されるため、管理画面の他パーツへと干渉することがありません。

```functions.php
function custom_editor_css()
{
    add_theme_support('editor-styles');
    add_editor_style('style-editor.css');
}

add_action('after_setup_theme', 'custom_editor_css');

```

##エディターのダークモードを有効にする
独自のCSSをエディター適用した際、場合によってはエディター全体の背景を黒系に変更する場合があります。
その際、エディタ内のボタン等の色を変更することができます。

```functions.php
function editor_dark_mode()
{
    add_theme_support('editor-styles');
    add_theme_support('dark-editor-style');
}

add_action('after_setup_theme', 'editor_dark_mode');

```

##エディターと同じスタイルを公開記事にも適用する
テーブルや引用、区切り等一部のブロックはGutenberg独自のスタイルが割り当てられています。
デフォルトではこれら独自のスタイルがエディターには適用されているのですが、公開記事では適用されていません。
以下のコードを記述することで、エディターにのみ適用されているスタイルを公開記事でも適用することができるようになります。


```functions.php
function editor_block_styles()
{
    add_theme_support('editor-styles');
    add_theme_support('wp-block-styles');
}

add_action('after_setup_theme', 'editor_block_styles');

```

#パッケージ
Gutenbergでは開発に役立つJavascriptパッケージが用意されています。
使用するにはPHPからパッケージを読み込むか、npmを使用する方法があります。

PHPの場合、`wp_enqueue_scripts`で使用するパッケージを第三引数に渡します。

```php
wp_enqueue_script(
    'my-custom-block',
    plugins_url( $block_path, __FILE__ ),
    array( 'wp-blocks', 'wp-editor', 'wp-element', 'wp-i18n' )
);
```

するとwpというグローバルオブジェクトに選択したパッケージが読み込まれます。

```js
const { PlainText } = wp.editor;
```

npmの場合は[ここ](https://www.npmjs.com/org/wordpress)から使用するパッケージを選択してインストールします。

```
npm install @wordpress/editor --save
```

##コンポーネント
コンポーネントはGutenbergのエディターで使われているUI(ボタン、チェックボックス、ツールバーなど)に関するパッケージです。


```
npm install @wordpress/components --save
```

その他随時追加予定です。