06
JULY
ウェブMONDAY 2020 / 7 / 6
pre _get_posts でアーカイブページの表示件数や順番を指定する
Text by Shinji Sato
こんにちは。
佐藤です。
今日はワードプレスのアクションフック「pre_get_posts」を使ってアーカイブページの表示件数や順番を指定する方法を解説していきます。
その前にまず「pre_get_posts」について少し解説しておきましょう。
「pre_get_posts」はワードプレスのアクションフックです。
使用する際は
add_action('pre_get_posts','関数名');
とまぁこんな感じで記述していきます。
説明を読んでみると
Fires after the query variable object is created, but before the actual query is run.
(クエリ変数オブジェクトが作成された後、実際のクエリが実行される前に発生します。)
とのことです。
参考:https://developer.wordpress.org/reference/hooks/pre_get_posts/
平たく言うとクエリ変数が読み込まれる前にクエリ変数を書き換えることができるアクションフックですね。
では早速使い方を見ていきましょう。
function original_pre_get_posts( $query ) { if ( is_admin() || ! $query->is_main_query() ){ return; } /* 処理を記述 */ } add_action('pre_get_posts','original_pre_get_posts');
基本の形はこれ、
これをfunction.phpにでも記述していきまっしょう。
そして関数の中に
if ( is_admin() || ! $query->is_main_query() ){ return; }
という記述が既にありますがおまじないだと思って記述しておきましょう。
詳しく知りたい人は上の方のリンク先ページを参照してください。
ここからが本番です。
まず
”クエリ変数オブジェクトが作成された後、実際のクエリが実行される前に発生します。”
との言葉通りこちらのpre_get_postsは至る所で呼び出されます。
そのためまず必ず必要になってくるのが
クエリ変数を書き換えたいページかどうか判別すること
これが一番大事。
判別するには$query変数の中身を直接見るか
wordpressの「条件分岐タグ」を用いて判別するのが一般的です。
参考までに条件分岐タグを一部ご紹介
is_archive() | アーカイブページか判定 ※パラメータは受付けない |
is_post_type_archive( ‘movie’ ) | 特定のスラッグのアーカイブページか判定 ※パラメータで投稿タイプを指定(例では’movie’) |
is_category() | カテゴリーアーカイブページか判定 ※パラメータでカテゴリ毎にも判定可能 |
is_tag() | タグのアーカイブページか指定 ※パラメータでタグ毎にも判定可能 |
is_tax() | タクソノミーのアーカイブページか指定 ※パラメータでタクソノミー毎にも指定可能 |
is_tax(‘mens’,array(‘tops’,’outer’)) | タクソノミーのアーカイブページで更にtermを指定する場合 ※例ではmensタクソノミーのtopsとouterタームのアーカイブページを指定 |
is_year() | 年別アーカイブページか判別 |
is_month() | 月別アーカイブページか判別 |
is_serch() | 検索結果ページか判別 |
使用例:
function original_pre_get_posts( $query ) { if ( is_admin() || ! $query->is_main_query() ){ return; } // カスタム投稿タイプ「movie」のみ if(is_post_type_archive( 'movie' )){ /* 処理内容 */ } } add_action('pre_get_posts','original_pre_get_posts');
ちなみに$query変数の中身を見て判別したい場合は
if($query->query['post_type'] == 'movie')
みたいにすればできます。
これでページを判別できたので
いよいよ$query変数を書き換えていきましょう。
書き換えは$queryクラス内のsetメソッドを使って行います。
$query->set('posts_per_page',6);
この時に使用できるパラメータは「get_posts」と同じですが
少し違うのは配列でまとめて与えるのではなく一つずつ設定する必要があるのでそこだけ注意しましょう。
/* get_postsの場合 */ $args = array( 'posts_per_page' => -1, 'post_type' => 'post', 'order' => 'ASC', 'orderby' => 'date', 'author' => '1,2,3', 'offset' => 3, ); $customPosts = get_posts($args); /* $query->set()の場合 */ $query->set('posts_per_page',-1); $query->set('post_type','post'); $query->set('order','ASC'); $query->set('orderby','date'); $query->set('author','1,2,3'); $query->set('offset',3);
項目が多くなってめんどくさい時はforeachとか使って
テキトーにやっちゃってください。
$sl = array( 'posts_per_page'=>-1, 'post_type'=>'post', 'order'=>'ASC', 'orderby'=>'date', 'author'=>'1,2,3', 'offset'=> 3, ); foreach($sl as $k => $s){ $query->set($k,$s); }
ちなみにクエリの指定で使用できるパラメータは下記サイトがとても参考になります。
http://notnil-creative.com/blog/archives/1288
という訳で完成形がこちら
/* カスタム投稿タイプ「movie」のアーカイブのみ 12件毎、降順で表示する場合の例 */ function original_pre_get_posts( $query ) { if ( is_admin() || ! $query->is_main_query() ){ return; } // カスタム投稿タイプ「movie」のみ if(is_post_type_archive( 'movie' )){ $query->set('posts_per_page',12); $query->set('order','DESC') } } add_action('pre_get_posts','original_pre_get_posts');