ループの詳細
基本的なループは:
<?php
if ( have_posts() ) :
while ( have_posts() ) : the_post();
// Display post content
endwhile;
endif;
?>
このループは、投稿がある場合にそれらをループして表示することを示しています。詳細に分解すると:
have_posts()
関数は、投稿があるかどうかを確認します。- 投稿がある場合、
while
ループは、括弧内の条件が論理的に真である限り実行され続けます。have_posts()
が真である限り、ループは続きます。
ループの使用
ループは index.php
に配置する必要があり、投稿情報を表示するために使用される他のテンプレートにも配置する必要があります。ヘッダーを何度も重複させたくないため、ループは常に get_header()
の呼び出しの後に配置する必要があります。例えば:
<?php
get_header();
if ( have_posts() ) :
while ( have_posts() ) : the_post();
// Display post content
endwhile;
endif;
?>
上記の例では、ループの終わりは endwhile
と endif
で示されています。ループは常に上記のように同じ if
と while
ステートメントで始まり、同じ終了ステートメントで終わる必要があります。
すべての テンプレートタグ は、開始と終了のステートメントの間に存在する必要があります。
指定された条件に一致する投稿がない場合に表示されるカスタム404「見つかりません」メッセージを含めることができます。このメッセージは、以下の例に示すように endwhile
と endif
ステートメントの間に配置する必要があります。
非常にシンプルな index.php
ファイルは次のようになります:
<?php
get_header();
if ( have_posts() ) :
while ( have_posts() ) : the_post();
the_content();
endwhile;
else :
_e( 'Sorry, no posts matched your criteria.', 'textdomain' );
endif;
get_sidebar();
get_footer();
?>
ループが表示できるもの
ループは、各投稿のさまざまな要素を表示できます。例えば、多くのテーマで使用される一般的な テンプレートタグ は次のとおりです:
next_post_link()
– 現在の投稿の後に時系列で公開された投稿へのリンクprevious_post_link()
– 現在の投稿の前に時系列で公開された投稿へのリンクthe_category()
– 表示されている投稿またはページに関連付けられたカテゴリthe_author()
– 投稿またはページの著者the_content()
– 投稿またはページの主要なコンテンツthe_excerpt()
– 投稿の主要なコンテンツの最初の55語の後に省略記号(…)または全文へのリンクが続きます。また、投稿の「抜粋」フィールドを使用して特定の抜粋の長さをカスタマイズすることもできます。the_ID()
– 投稿またはページのIDthe_meta()
– 投稿またはページに関連付けられたカスタムフィールドthe_shortlink()
– サイトのURLと投稿またはページのIDを使用してページまたは投稿へのリンクthe_tags()
– 投稿に関連付けられたタグthe_title()
– 投稿またはページのタイトルthe_time()
– 投稿またはページの時間または日付。これは、標準のphp日付関数のフォーマットを使用してカスタマイズできます。
また、次のような 条件タグ を使用することもできます:
is_home()
– 現在のページがホームページである場合は真を返しますis_admin()
– 管理画面内にいる場合は真を返し、それ以外は偽を返しますis_single()
– 現在のページが単一の投稿を表示している場合は真を返しますis_page()
– 現在のページが単一のページを表示している場合は真を返しますis_page_template()
– ページが特定のテンプレートを使用しているかどうかを判断するために使用できます。例えば:is_page_template('about-page.php')
is_category()
– ページまたは投稿が指定されたカテゴリを持っている場合は真を返します。例えば:is_category('news')
is_tag()
– ページまたは投稿が指定されたタグを持っている場合は真を返しますis_author()
– 著者のアーカイブページ内にいる場合は真を返しますis_search()
– 現在のページが検索結果ページである場合は真を返しますis_404()
– 現在のページが存在しない場合は真を返しますhas_excerpt()
– 投稿またはページに抜粋がある場合は真を返します
例
基本的な例
ブログアーカイブ
ほとんどのブログにはブログアーカイブページがあり、投稿のタイトル、サムネイル、抜粋などを表示できます。以下の例は、投稿があるかどうかを確認し、ある場合は各投稿のタイトル、サムネイル、抜粋を出力するシンプルなループを示しています。投稿が存在しない場合は、括弧内のメッセージが表示されます。
<?php
if ( have_posts() ) :
while ( have_posts() ) : the_post();
the_title( '<h2>', '</h2>' );
the_post_thumbnail();
the_excerpt();
endwhile;
else:
_e( 'Sorry, no posts matched your criteria.', 'textdomain' );
endif;
?>
個別投稿
WordPressでは、各投稿にはその投稿に関連する情報を表示する独自のページがあります。テンプレートタグを使用すると、表示したい情報をカスタマイズできます。
以下の例では、ループが投稿のタイトルとコンテンツを出力します。この例を投稿またはページのテンプレートファイルで使用して、投稿に関する最も基本的な情報を表示できます。また、このテンプレートをカスタマイズして、投稿にカテゴリなどの追加データを追加することもできます。
<?php
if ( have_posts() ) :
while ( have_posts() ) : the_post();
the_title( '<h1>', '</h1>' );
the_content();
endwhile;
else:
_e( 'Sorry, no pages matched your criteria.', 'textdomain' );
endif;
?>
中級例
特定のカテゴリの投稿を異なるスタイルで表示
以下の例では、いくつかのことを行います:
- まず、各投稿をそのタイトル、時間、著者、コンテンツ、カテゴリとともに表示します。これは上記の個別投稿の例に似ています。
- 次に、カテゴリIDが「3」の投稿を異なるスタイルで表示できるように、
in_category()
テンプレートタグを利用します。
この例のコードコメントは、ループの各段階での詳細を提供します:
<?php
// Start the Loop.
if ( have_posts() ) :
while ( have_posts() ) : the_post();
/* * See if the current post is in category 3.
* If it is, the div is given the CSS class "post-category-three".
* Otherwise, the div is given the CSS class "post".
*/
if ( in_category( 3 ) ) : ?>
<div class="post-category-three">
<?php else : ?>
<div class="post">
<?php endif;
// Display the post's title.
the_title( '<h2>', ';</h2>' );
// Display a link to other posts by this posts author.
printf( __( 'Posted by %s', 'textdomain' ), get_the_author_posts_link() );
// Display the post's content in a div.
?>
<div class="entry">
<?php the_content() ?>
</div>
<?php
// Display a comma separated list of the post's categories.
_e( 'Posted in ', 'textdomain' ); the_category( ', ' );
// closes the first div box with the class of "post" or "post-cat-three"
?>
</div>
<?php
// Stop the Loop, but allow for a "if not posts" situation
endwhile;
else :
/*
* The very first "if" tested to see if there were any posts to
* display. This "else" part tells what do if there weren't any.
*/
_e( 'Sorry, no posts matched your criteria.', 'textdomain' );
// Completely stop the Loop.
endif;
?>
複数のループ
場合によっては、複数のループを使用する必要があります。例えば、ページの上部に目次リストで投稿のタイトルを表示し、その後ページの下部でコンテンツを表示したい場合があります。クエリが変更されないため、投稿を2回ループする必要があるときは、単にループを巻き戻す必要があります。そのために、rewind_posts() 関数を使用します。
rewind_postsの使用
rewind_posts()
を使用して、同じ クエリを2回ループすることができます。これは、ページの異なる場所で同じクエリを2回表示したい場合に便利です。
以下は rewind_posts()
の使用例です:
<?php
// Start the main loop
if ( have_posts() ) :
while ( have_posts() ) : the_post();
the_title();
endwhile;
endif;
// Use rewind_posts() to use the query a second time.
rewind_posts();
// Start a new loop
while ( have_posts() ) : the_post();
the_content();
endwhile;
?>
二次クエリとループの作成
同じクエリを使用して2つのループを使用するのは比較的簡単ですが、常に必要なわけではありません。代わりに、テンプレートで異なるコンテンツを表示するために二次クエリを作成したいことがよくあります。例えば、同じページに2つの投稿グループを表示したいが、それぞれのグループに異なる操作を行いたい場合があります。以下に示す一般的な例は、単一の投稿の下に同じカテゴリの投稿のリストを表示することです。
<?php
// The main query.
if ( have_posts() ) :
while ( have_posts() ) : the_post();
the_title();
the_content();
endwhile;
else :
// When no posts are found, output this text.
_e( 'Sorry, no posts matched your criteria.' );
endif;
wp_reset_postdata();
/*
* The secondary query. Note that you can use any category name here. In our example,
* we use "example-category".
*/
$secondary_query = new WP_Query( 'category_name=example-category' );
// The second loop.
if ( $secondary_query->have_posts() )
echo '<ul>';
while ( $secondary_query->have_posts() ) : $secondary_query->the_post();
the_title( '<li>', '</li>' );
endwhile;
echo '</ul>';
endif;
wp_reset_postdata();
?>
上記の例では、最初に通常のループを表示します。次に、WP_Query
を使用して特定のカテゴリをクエリする新しい変数を定義します。この場合、example-category
スラッグを選択しました。
上記の例の通常のループには1つの違いがあります: wp_reset_postdata()
を呼び出して投稿データをリセットします。二次ループを使用する前に、投稿データをリセットする必要があります。これを行う方法は2つあります:
複数のループのリセット
テンプレートで複数のループを使用する際は、それらをリセットすることが重要です。リセットしないと、グローバル $post
変数内でデータがどのように保存され、使用されるかによって予期しない結果が生じる可能性があります。呼び出し方によってループをリセットする主な方法は3つあります。
wp_reset_postdataの使用
wp_reset_postdata()
を使用して、WP_Query
でカスタムまたは複数のループを実行しているときに使用します。この関数は、グローバル $post
変数をメインクエリの現在の投稿に復元します。ベストプラクティスに従っている場合、これはループをリセットするために最も一般的に使用される関数です。
この関数を正しく使用するには、WP_Query
を使用したループの後に次のコードを配置します:
<?php wp_reset_postdata(); ?>
以下は、WP_Query
を使用してループを作成し、wp_reset_postdata()
でリセットされる例です。
<?php
// Example argument that defines three posts per page.
$args = array( 'posts_per_page' => 3 );
// Variable to call WP_Query.
$the_query = new WP_Query( $args );
if ( $the_query->have_posts() ) :
// Start the Loop
while ( $the_query->have_posts() ) : $the_query->the_post();
the_title();
the_excerpt();
// End the Loop
endwhile;
else:
// If no posts match this query, output this text.
_e( 'Sorry, no posts matched your criteria.', 'textdomain' );
endif;
wp_reset_postdata();
?>
wp_reset_queryの使用
wp_reset_query()
を使用すると、WP_Query とグローバル $post
データが元のメインクエリに復元されます。ループ内で query_posts()
を使用する場合は、この関数を使用してループをリセットする必要があります。カスタムループで WP_Query を使用した後に使用できます。なぜなら、実際に実行時に wp_reset_postdata()
を呼び出すからです。しかし、wp_reset_postdata()
を使用することがベストプラクティスです。query_posts()
はベストプラクティスではなく、可能な限り避けるべきです。したがって、wp_reset_query()
を使用する必要はあまりありません。
この関数を正しく使用するには、query_posts()
を使用したループの後に次のコードを配置します。
<?php wp_reset_query(); ?>