管理メニュー

PHP

【WordPress】管理画面に自作管理メニューとサブメニューを追加する方法

更新日:2023/02/02

WordPressの管理画面には自作のメニューを追加できます。
とりあえずやってみると、とても簡単でした。

そこで今回は、管理画面に自作管理メニューを追加し、さらにサブメニューで階層化する方法をお伝えします。

 

自作管理メニューを追加する方法

管理メニューはサブメニューで階層化できますが、まずは一階層での追加方法をお伝えします。

コード例

管理メニューに自作メニューを追加する、単純なコード例です。

add_action('admin_menu', 'my_admin_menu');
 
function my_admin_menu(){
	add_menu_page( 'myメニュー' , 'myメニュー' , 'manage_options' , 'my_menu'
			  , 'echo_my_menu' , '' , 3 );
}

add_action( 'admin_init', 'register_my_menu' );
 
function register_my_menu(){
    register_setting( 'my_option_group' , 'my_option_1' );
}

function echo_my_menu() {
	?>
	<div class="wrap">
		<h2>myメニュー</h2>
		<form method="post" action="options.php">
	<?php 
		settings_fields( 'my_option_group' );
	?>
		<table class="form-table">
		<tr><th scope="row" >項目1</th>
		<td>
		<?php $value = esc_textarea( get_option('my_option_1','') ); ?>
		<textarea id="my_option_1" name="my_option_1" cols="160" rows="7"><?= $value ?></textarea>
		</td></tr>
		</table>
		<?php submit_button(); ?>
		</form>
	</div>
<?php
}

admin_initアクションは、admin_menuアクションの後に実行されます。
そのため、最後に紹介しているコードmy_admin_menu()関数の中でadmin_initアクションを登録しています。

管理メニュー登録:add_menu_page()関数

自作管理メニューを追加するには、まずadmin_menuアクションでadd_menu_page()関数を実行します。

実行例

add_action('admin_menu', 'my_admin_menu');

function my_admin_menu(){
	add_menu_page( 'myメニュー' , 'myメニュー' , 'manage_options' , 'my_menu'
			  , 'echo_my_menu' , '' , 3 );
}

add_menu_page()の定義

add_menu_page( $page_title, $menu_title, $capability, $menu_slug, $callback = '', $icon_url = '', $position = null )

add_menu_page()関数は、7つの引数を受け付けます。

オプション名の登録:register_setting()関数

次にregister_setting()関数を使用して、optionsテーブルに保存するときに必要なオプション名を登録します。
admin_initアクションで実行します。

実行例

add_action( 'admin_init', 'register_my_menu' );

function register_my_menu(){
    register_setting( 'my_option_group' , 'my_option_1' );
}

register_setting()関数は、管理画面でデータベースに保存する入力項目個数だけ呼び出します。

register_setting()の定義

register_setting( $option_group, $option_name, $args = array() )

register_setting()関数は、3つの引数を受け付けます。

  • $option_group:

    オプションのグループ名。
    基本的には、同じ管理画面なら同じ値。

  • $option_name:

    オプションの名前。
    get_option()関数の第一引数に指定すると、データベースから設置値を取得できる。

  • $args:

    オプションの値をサニタイズするコールバック関数。
    他の意味を持たせることができるが、それほど有用ではない(と思う)ので説明しない。

管理メニューの表示

add_menu_page()関数の5番目の引数$callbackで指定した関数で、管理メニューに表示するhtmlを生成します。

function echo_my_menu() {
	?>
	<div class="wrap">
		<h2>myメニュー</h2>
		<form method="post" action="options.php">
	<?php 
		settings_fields( 'my_option_group' );
	?>
		<table class="form-table">
		<tr><th scope="row" >項目1</th>
		<td>
		<?php $value = esc_textarea( get_option('my_option_1','') ); ?>
		<textarea id="my_option_1" name="my_option_1" cols="160" rows="7"><?= $value ?></textarea>
		</td></tr>
		</table>
		<?php submit_button(); ?>
		</form>
	</div>
<?php
}

コールバック関数は、formタグを使用してoptions.phpを呼び出します。

次にformタグ内でsettings_fields()関数を実行します。
これにより、hidden属性でnonce等の情報が出力されます。

settings_fields()関数の引数は、register_setting()関数の一番目の引数です。

次に入力項目を出力します。
textareaやinput、selectなど目的に合わせて入力用のタグを選択します。
その際、入力タグのidとname属性にはオプション名を指定します。

全ての入力項目を出力したら、submit_button()関数を呼び出します。
これにより、変更を保存ボタンが出力されます。

 

サブメニューを追加する方法

次はサブメニューを追加して、自作メニューを階層化する方法です。

この項の例は個別にアクションフックを登録していますが、親ページのフックと一緒に記述しても大丈夫です。

サブメニューの登録:add_submenu_page()

サブメニューを追加するときは、add_submenu_page()関数を使用します。

実行例

add_action('admin_menu', 'my_admin_menu_sub');

function my_admin_menu_sub(){
	add_submenu_page( 'my_menu' , 'subメニュー' , 'subメニュー' , 'manage_options' , 'my_sub_menu'
			  , 'echo_my_sub_menu' , '' );
}

add_submenu_page()の定義

add_submenu_page( $parent_slug, $page_title, $menu_title, $capability, $menu_slug, $callback = '', $position = null )

引数は8つです。

第一引数は親メニューのスラッグです。

以降はadd_menu_page()と同じです。

サブメニューのオプション登録:register_setting()

サブメニューのオプション登録は、親ページと同じようにregister_setting()で行います。

実行例

add_action( 'admin_init', 'register_my_menu_sub' );
     
function register_my_menu_sub(){
    register_setting( 'my_sub_option_group' , 'my_sub_option_1' ); // サブメニュー
}

サブメニューの表示

サブメニューの表示方法は、add_menu_page()で登録した親ページと同じです。
コールバック関数に、管理メニューの表示と同じ流れでコードを記述します。

function echo_my_sub_menu() {
	?>
	<div class="wrap">
		<h2>myメニュー</h2>
		<form method="post" action="options.php">
	<?php 
		settings_fields( 'my_sub_option_group' );
	?>
		<table class="form-table">
		<tr><th scope="row" >項目1</th>
		<td>
		<?php $value = esc_textarea( get_option('my_sub_option_1','') ); ?>
		<textarea id="my_sub_option_1" name="my_sub_option_1" cols="160" rows="7"><?= $value ?></textarea>
		</td></tr>
		</table>
		<?php submit_button(); ?>
		</form>
	</div>
<?php
}

 

入力した値を検証してエラー表示する方法

入力された値をデータベースに登録する前に検証してエラーを表示したいケースがあります。

方法については次の記事で紹介しているので、参考にしてみてください。

 

少しだけ汎用性を考慮したコード

自作メニュー追加で、後々の項目追加を容易にするコードを作成しました。
一階層での例です。

add_action('admin_menu', function() {
	$menu_slug = 'my_setting_menu';
	$data = array(
		'title' => 'My設定',
		'option_group' => 'my_setting_menu_group',
		'option_data' => array(
			array( 'name'=>'my_opt1' , 'title'=>'設定1' , 'type'=>'textarea' , 'value'=>'' , 'description'=>'' ),
			array( 'name'=>'my_opt2' , 'title'=>'設定2' , 'type'=>'checkbox' , 'value'=>'1' , 'description'=>'チェック' ),
			array( 'name'=>'my_opt3' , 'title'=>'設定3' , 'type'=>'select'   , 'value'=>'cat,dog,panda' , 'description'=>'猫,犬,ぱんだ' ),
		)
	);
		// メニュー登録
	add_menu_page($data['title'], $data['title'], 'manage_options' , $menu_slug
			  , function() use($data){ echo_my_setting_menu($data); },'',3);

	add_action( 'admin_init',
			function() use($data){ register_my_setting_menu($data);});
},98);

	// 設定項目を登録
function register_my_setting_menu($data){

	foreach( $data['option_data'] as $option_data){
		register_setting( $data['option_group'], $option_data['name'] );
	}

}

	// 管理画面の表示
function echo_my_setting_menu($data) {
	?>
	<div class="wrap">
		<h2><?php echo $data['title']; ?></h2>
			<form method="post" action="options.php">
	<?php 
			settings_fields( $data['option_group'] );
	?>
			<table class="form-table">
	<?php
				foreach($data['option_data'] as $option_data){
					echo '<tr><th scope="row" >'.$option_data['title'].'</th><td>';

					$id = $option_data['name'];

					switch( $option_data['type'] ){

					case 'textarea':

						echo '<textarea id="'.$id.'" name="'.$id.'" cols="160" rows="7">'
							.esc_textarea( get_option($id,$option_data['value'])).'</textarea>';
						break;

					case 'checkbox':

						$value = $option_data['value'];
						$checked = get_option($id,'') === $value ? ' checked' : '';
						echo '<input type="checkbox" id="'.$id.'" name="'.$id.'" value="'.$value.'"'.$checked.'>'
								.$option_data['description'].'</label>';
						break;

					case 'select':

						$values = explode(',', $option_data['value']);
						$descriptions = explode(',', $option_data['description']);
						$current_value = get_option($id,'');
						if( !in_array($current_value,$values) ) $current_value = $values[0];

						echo '<select id="'.$id.'" name="'.$id.'">';
						foreach( $values as $index => $v ){
							$selected = $current_value === $v ? ' selected' : '';
							echo '<option value="'.$v.'"'.$selected.'>'.$descriptions[$index].'</option>';
						}
						echo '</select>';
						break;
					}
					echo '</td></tr>';
				}
	  ?>
		</table>
		<?php submit_button(); ?>
	</form>
	</div>
	<?php
}

textarea、checkbox、selectを追加するときは、add_action()のコールバック関数の$data['option_data']に項目の情報を追加するだけでいいようになっています。

WordPressはHTMやCSSの知識も必要。総合的な知識を身につけよう。

更新日:2023/02/02

書いた人(管理人):けーちゃん

スポンサーリンク

記事の内容について

null

こんにちはけーちゃんです。
説明するのって難しいですね。

「なんか言ってることおかしくない?」
たぶん、こんなご意見あると思います。

裏付けを取りながら記事を作成していますが、僕の勘違いだったり、そもそも情報源の内容が間違えていたりで、正確でないことが多いと思います。
そんなときは、ご意見もらえたら嬉しいです。

掲載コードについては事前に動作確認をしていますが、貼り付け後に体裁を整えるなどをした結果動作しないものになっていることがあります。
生暖かい視線でスルーするか、ご指摘ください。

ご意見、ご指摘はこちら。
https://note.affi-sapo-sv.com/info.php

 

このサイトは、リンクフリーです。大歓迎です。