• LIGの広告成功事例
WEB

WordPressカスタマイズの幅が劇的に広がる、フィルターフックとアクションフックの使い方

WordPressカスタマイズの幅が劇的に広がる、フィルターフックとアクションフックの使い方

こんにちは、日々WordPressをカスタマイズしているエンジニアのひろゆきです。

今回はWordPressのカスタマイズの際に活躍するフィルターフック、アクションフックについてまとめました。
本稿ではフックを知ってもらって、とりあえず使ってみることを目的としますので、詳しい動作原理や本来の目的などについてはCodexなどを見てくださいね!

参考:プラグイン API – WordPress Codex 日本語版

また、過去に弊社CTOのづやが便利なアクションフックについての記事「wordpressでよく使った管理画面用アクションフック」を書いておりますので、こちらもあわせて見てみてください!

フィルターフック、アクションフックとは

まずはフィルターフックとアクションフックの違いについてですが、それぞれフックの種類によって便宜的に分けられているものの、機能としては同じです。
なので、本稿ではこれらについてあまり意識せずに解説を進めたいと思います。それぞれをまとめて、以下ではフックと呼びます。

また、そもそもフックとは何かということですが、簡単にいうと「きっかけ」のことです。WordPressには以下のように様々なタイミングでフックが用意されています。

  • the_title()が実行されたタイミング
  • wp_head()が実行されたタイミング
  • 記事が公開されたタイミング

フックを使うということは、これらのタイミングにあわせて自分が用意した関数を実行させるということです。例えばthe_title()が実行されたのをきっかけに、何かの処理をさせようという訳です。

実装方法

言葉で説明するのは難しいので、習うより慣れろ!方式で、実際にどんな関数を使うとどういう挙動になるのかを見ていきましょう。

add_action()もしくはadd_filter()を使う

フックを利用する際にはadd_filter()またはadd_action()という関数を使います。どちらも機能は同じですので、どちらかを使えば動きます。
フィルターフックを使うときはadd_filter()、アクションフックのときはadd_action()を使うぐらいの認識で問題ないかと思います。

参考:フィルターフック一覧

参考:アクションフック一覧

add_filter( $tag, $function_to_add, $priority, $accepted_args );

関数はこのように記述します。それぞれ役割を説明します。

  • $tag→フックの名前を指定します。
  • $function_to_add→フックしたタイミングで実行したい関数を指定します。
  • $priority→優先順位を整数で指定します。同じフック処理がある場合に数値が小さい方から実行されます。
  • $accepted_args→関数で使用する引数の数を指定します。指定できる引数の数はフックによって異なりますが、複数指定の場合でも1つ目の引数が本来の値で、2つ目以降の引数はフックされた時に利用する為の追加の要素にすぎません。

使用例

 

例1. 記事タイトルの前にIDを表示させる

それでは実際にフックを使ってWordPressの挙動を変えてみます。下記をfunctions.phpなどに追加します。

function my_the_title($title, $id) { 
    return 'ID='.$id.$title; 
}
add_filter('the_title', 'my_the_title', 10, 2);

これで、the_title()を実行するとID=〜タイトルという形で出力されます。ただこれだとフックせずともテンプレート側で実装できますね。

 

例2. 新規投稿の際のタイトルプレースホルダを変更する

次はもう少し実用的な使い方を試しましょう。新規投稿の際にタイトル欄に表示されている「タイトルを入力してください」というプレースホルダを「タイトルを入力してや!」に変更してみます。

プレースホルダを出力する直前に実行されるenter_title_hereというフックを使います。

function my_enter_title_here($title){
	return 'タイトルを入力してや!';
}
add_filter('enter_title_here', 'my_enter_title_here', 10, 1);

引数を見てみると、中身には「タイトルを入力してください」という文字列が入っていましたので、そのまま「タイトルを入力してや!」という文字列を返してあげました。
これで、記事を新規登録するプレースホルダは「タイトルを入力してや!」となっているはずです。

なんとなくイメージは掴めたでしょうか?フックは数多く存在するので、自分が実行したいタイミングのフックを見つけて処理を追加するイメージです。

注意点

フィルターフック、アクションフックを使う際、特に気をつけていただきたいのが影響範囲です。例1をもう一度見てみます。

function my_the_title($title, $id) { 
    return 'ID='.$id.$title; 
}
add_filter('the_title', 'my_the_title', 10, 2);

実装する際にはこれをfunctions.phpなどに記述するわけですが、the_titleというフックはthe_title()やget_the_title()が実行されるときのフックであり、非常に影響範囲が広いです。
全体に適応したい場合は上記の記述で問題ないですが、限定したい場合は対策が必要です。方法は主に2通りあります。

1. remove_filterを使ってadd_filterを取り消す

remove_filter()を使い、add_filter()を取り消すことができます。

<?php add_filter('the_title', 'my_the_title', 10, 2); ?>
<h2><?php the_title(); ?></h2>
<?php remove_filter ('the_title', 'my_the_title'); ?>

使い方はこんな感じ。この記述だと上記のthe_title()1行にしか影響しません。

2. 実行する関数の中で条件分岐させる

もう1つはフックで実行する関数の中で条件分岐させる方法です。今度は例2で見てみます。

function my_enter_title_here($title){
	return 'タイトルを入力してや!';
}
add_filter('enter_title_here', 'my_enter_title_here', 10, 1);

これだとどの投稿でも新規作成の場合は「タイトルを入力してや!」となってしまいます。これをpostの投稿タイプのみで表示されるように調整してみましょう。

function my_enter_title_here($title) {
	global $post;
	if(is_admin() && !empty($post->post_type) && $post->post_type == "post"){
		return 'タイトルを入力してや!';
	}
	return $title;
}
add_filter('enter_title_here', 'my_enter_title_here', 10, 1);

こんな感じになります。is_admin()というのは管理画面かどうかの判定で、念のために記述しています。これでpostの投稿タイプのときだけ、新規作成のプレスホルダが「タイトルを入力してや!」になるわけです。

例えば製品情報をpostと別の投稿タイプで扱っているときなどに、製品記事の投稿タイプでのみ「製品タイトルを入力してください」とかにしてあげると親切かもしれないですね。

フックを使ったWPカスタマイズ例をご紹介

最後にいくつか便利なフィルターをご紹介します!

メインクエリを変更する(pre_get_posts)

記事の表示件数やソートをする時に使う有名なやつです。query_postsでやってたようなことができます。

function change_posts_per_page($query) {
	if ( is_admin() || ! $query->is_main_query() )
		return;

	if($query->is_category()){
		$query->set( 'posts_per_page', '10' );//件数変更
		$query->set( 'orderby', 'post_date' );//ソート指定
		$query->set( 'order', 'DESC' );//ソート順番
	}
}
add_action( 'pre_get_posts', 'change_posts_per_page' );

上記の記述だとカテゴリ一覧の場合に10件の記事が表示されます。

本文の自動整形を外す(the_content)

Wordpressには本文を自動整形する機能があって、pタグがついたりbrタグが利かなかったりします。普通に使う分には便利なのですが、htmlを直接反映させたい場合などは不都合です。そんなときは下記のフィルターを使いましょう。

remove_filter( ‘the_content’, ‘wpautop’ );

the_contentから自動整形するフィルターを解除できます。

ログインメッセージを変更する(admin_bar_menu)

デフォルトでは「こんにちは、〇〇さん!」となってる管理画面のメッセージですが、自分のテンションが上がるように自由に変えることができます。

function replace_hello_text( $wp_admin_bar ) {
	$my_account = $wp_admin_bar->get_node( 'my-account' );
	$newtitle = str_replace( 'こんにちは、', 'おかえりなさい、', $my_account->title );
	$wp_admin_bar->add_menu( array(
			'id' => 'my-account',
			'title' => $newtitle,
			'meta' => false
	) );
}
add_filter( 'admin_bar_menu', 'replace_hello_text', 25 );

これで「おかえりなさい、〇〇さん!」となります。うまく工夫すれば記事の入効率がアップするかもしれませんね!

まとめ

最初はちょっとわかりにくいフィルター、アクションフックですが、便利なので是非使ってみてくださいね!今回はあまり概念的なところや仕組みには触れなかったのですが、慣れてきたら各自冒頭のリンク先で調べてみてください。

ではまた!

この記事を書いた人

ひろゆき
ひろゆき バックエンドエンジニア 2010年入社
エンジニアのひろゆきや。大阪生まれの大阪育ち。LIGを代表するエンジニアになるため、頑張るで。ほんま、よろしくやで。