投稿一覧に列を追加する


プラグインでもできるんですが、そんなに難しくありません。シンプルなコードで様々な情報が表示できて便利です。

関連投稿

  1. 投稿一覧に列を追加する
  2. 投稿一覧に絞り込みを追加する
  3. 投稿一覧の追加列にソート機能をつける

プラグインやテーマ、カスタム投稿タイプの作成方法はここでは扱いません。

カスタム投稿タイプの構成

例えば、下記のようなカスタム投稿タイプの構成だとします

  • book 投稿タイプ「書籍」
  • 書籍投稿に設定する「ジャンル」genre タクソノミー
  • 著者を入力するカスタムフィールド written_by

デフォルトの管理画面ではタイトルと更新日、投稿ステータスぐらいしかありません。

下記のようにジャンルや著者の列を増やします。

ジャンルの列を表示する

register_taxonomy の引数で指定します。

'show_admin_column'     => true,

register_taxonomy() – Function | Developer.WordPress.org

カスタムフィールドの列を追加する

使用するフック

  1. manage_{$post_type}_posts_columns
  2. manage_{$post->post_type}_posts_custom_column

列を追加

book 投稿タイプの列をカスタマイズしたいので、実際に使うフックは manage_book_posts_columns フィルターになります。

add_filter(
	'manage_book_posts_columns',
	function ( $columns ){
		// $columns 引数に何らかの処理を加えて返す。
		return $new_columns;
	},
	10,
	1
);

このように無名関数を使うと楽です、関数名を考えなくていいし関数名の衝突も気にしなくていい。

ただし、無名関数を使う際の注意点

  1. 処理を使い回せない
  2. フックを外したい時に remove_action などで外せなくなる
    フィルターした状態など、特定の条件で列を表示したくない時にフックが外せません
  3. WordPress の標準コーディング規約では非推奨
    PHP コーディング規約 – Japanese Team – WordPress.org 日本語

では、実際の処理について。
フィルターの引数である $columns の実行時の中身は、下のような連想配列です。

array(3) {
  "cb" => "<input type="checkbox" />"
  "title" => "タイトル"
  "date" => "日付"
}

この配列に著者の要素を足します。キーは識別のために重複しない文字列にします。追加した要素の値が見出しになります。

add_filter(
	'manage_book_posts_columns',
	function ( $columns ){
		$written_by_column = array(
          "written_by" => "著者"
        );
		return $columns + $written_by_column;
	},
	10,
	1
);

分かりやすさのために、やや冗長なコードにしています。

上記のコードで、表示はこうなります。

$columns配列に単純に追加すると、一番後ろに列が作られます。

ということで、チェックボックスとタイトルの間に追加されるように修正します。

列の挿入位置を調整する

引数の$columns配列を array_sliceして分割します。PHP: array_slice – Manual

var_dump( array_slice( $columns, 0, 1 ));
// array(1) { ["cb"]=> string(25) "" }

var_dump( array_slice( $columns, 1, 2 ));
// array(2) { ["title"]=> string(12) "タイトル" ["date"]=> string(6) "日付" } 

二つに分けた配列の間に「著者」配列を挟む配列にします。

add_filter(
	'manage_book_posts_columns',
	function ( $columns ){
		$written_by_column = array(
			"written_by" => "著者"
		);

		$new_columns = array_slice( $columns, 0, 1 )
						+ $written_by_column
						+ array_slice( $columns, 1, count( $columns ) - 1 );

		return $new_columns;
	},
	10,
	1
);

二つ目の array_slice の個数の引数は動的にしておくと、他で列が増減してもコードを変えなくて済みます。

他に列を増やすプラグインがあったりすると引数に渡されてくる $columns の中身が増えます(フックの優先順位によってもどう増えるか変わる) 配列の分割位置をそれに応じて変えてやると自由な位置に挿入できます。

これでタイトルの前に列が増えました。

スタイルを当てて、列幅を調整します。

追加した列には、自動で column-<key> というクラスが追加されています。

<th scope="col" id="written_by" class="manage-column column-written_by">著者</th>
<td class="written_by column-written_by" data-colname="著者"></td>

管理画面用のスタイルを出力するフックを使って、列幅を指定。

add_action(
	'admin_print_styles',
	function () {
		echo '<style>
.column-written_by {
width: 7rem;
}
</style>' . PHP_EOL;
	}
);

増やした列に表示する内容

「列を増やす」項で作った列の中身の表示を実装します。

manage_book_posts_custom_column アクションは、投稿一覧テーブルの各セルが出力される度に呼び出されます。引数も都度、変わります。

「達人プログラマー」の投稿 ID が 5 だとすると、下図のようになります。

manage_book_posts_columns フックで追加したキー=列の識別子で、追加した「著者」列か判定します。

add_action(
	'manage_book_posts_custom_column',
	function ( $column_name, $id ) {
		if ( 'written_by' === $column_name ) {
			// 'written_by' 列に表示する内容の処理
            echo "著者";
		}
	},
	10,
	2
);

固定文字列でなく、投稿ごとに「著者」フィールドを取得して出力します。

add_action(
	'manage_book_posts_custom_column',
	function ( $column_name, $id ) {
		if ( 'written_by' === $column_name ) {
			echo get_post_meta( $id, 'written_by', true );
		}
	},
	10,
	2
);

次にソートや絞り込みを実装してみましょう。

  1. 投稿一覧に列を追加する (このページ)
  2. 投稿一覧に絞り込みを追加する
  3. 投稿一覧の追加列にソート機能をつける

完成コード例

add_filter(
	'manage_book_posts_columns',
	function ( $columns ){
		$written_by_column = array(
			"written_by" => "著者"
		);

		$new_columns = array_slice( $columns, 0, 1 )
				+ $written_by_column
				+ array_slice( $columns, 1, count( $columns ) - 1 );

		return $new_columns;
	},
	10,
	1
);

add_action(
	'manage_book_posts_custom_column',
	function ( $column_name, $id ) {
		if ( 'written_by' === $column_name ) {
			echo get_post_meta( $id, 'written_by', true );
			//echo implode( '<br>', get_post_meta( $id, 'written_by' ) );
		}
	},
	10,
	2
);

add_action(
	'admin_print_styles',
	function () {
		echo '<style>
.column-written_by {
width: 10rem;
}
</style>' . PHP_EOL;
	}
);

カテゴリー:

最終更新: