וורדפרס עושה עבודה מצויינת בכדי לעקוב אחר מה שקורה עם הלולאה, אך כאשר אתם מתחילים לשנות פרמטרים ולהגדיר לולאות מרובות, נכון יהיה לאפס את אותן לולאות באמצעות אחת מתוך שלושת הפונקציות שוורדפרס מספקת לנו.
בפוסט זה נסביר על שלוש טכניקות המאפשרות לאפס את הלולאה של וורדפרס בכדי להבין טוב יותר מתי וכיצד להשתמש בהם בתבניות וורדפרס. שלושת הפונקציות המדוברות הינן:
הפונקציה wp_reset_postdata
הפונקציה הראשונה הינה wp_reset_postdata
, המשחזרת את המשתנה הגלובאלי ($post
) לפוסט הנוכחי בלולאה הראשית. הפונקציה שימושית כאשר אתם משתמשים ב WP_Query על מנת לשנות לולאות או ליצור לולאות מרובות באותו עמוד. היא נראית כך:
<?php wp_reset_postdata(); ?>
הפונקציה פשוטה – היא אינה מקבלת שום פרמטר ואינה מחזירה שום ערך. היא פשוט מחזירה, או מאפסת לצורך העניין את המידע (של האובייקט) חזרה לפוסט הנוכחי לאחר שימוש בלולאה חדשה שיצרתם. אז לדוגמה, נאמר שיש לנו לולאת WP_Query בקובץ header.php
של התבנית שלנו, משהו בסגנון הבא:
<?php
$random_post = new WP_query();
$random_post->query('cat=3&showposts=1&orderby=rand');
while ($random_post->have_posts()) : $random_post->the_post(); ?>
<a href="<?php the_permalink() ?>" title="<?php the_title(); ?>">
<img src="<?php echo get_post_meta($random_post->ID, 'featured', true); ?>">
</a>
<?php
endwhile;
זאת תציג פוסט רנדומלי ב Header, אך היא גם תשנה את האובייקט של הלולאה הראשית. ללא המידע המקורי של הלולאה, הפוסטים שיוצגו לדוגמה ב index.php
הנטען לאחר header.php
כנראה ויציגו תוצאות בלתי צפויות.
לשמחתינו אנו יכולים להשתמש ב wp_reset_postdata
על מנת לשחזר את האובייקט למצבו המקורי. בכדי להשתמש ב wp_reset_postdata
פשוט הוסיפו אותו לאחר הלולאה המותאמת שלכם.
הנה הדוגמה הקודמת שהצגנו יחד עם wp_reset_postdata
המאפס האובייקט המדובר:
<?php
$random_post = new WP_query();
$random_post->query('cat=3&showposts=1&orderby=rand');
while ($random_post->have_posts()) : $random_post->the_post(); ?>
<a href="<?php the_permalink() ?>" title="<?php the_title(); ?>">
<img src="<?php echo get_post_meta($random_post->ID, 'featured', true); ?>">
</a>
<?php
endwhile;
wp_reset_postdata();
מתי להשתמש? עדיף להשתמש לאחר לולאה מותאמת או מספר לולאות שנוצרו באמצעות WP_Query.
הפונקציה wp_reset_query
לאחר מכן ישנה הפונקציה wp_reset_query
המאפסת את Query בשימוש בלולאות מרובות. היא גם כן אינה מקבלת שום פרמטר ואינה מחזירה שום ערך ונראית כך:
<?php wp_reset_query(); ?>
הפונקציה הזו נוצרה ספציפית בכדי למנוע בעיות עם השימוש ב query_posts
כפי שמתואר בפונקציה עצמה הנמצאית בקובץ wp-includes/query.php
:
/**
* Destroys the previous query and sets up a new query.
*
* This should be used after query_posts() and before another query_posts().
* This will remove obscure bugs that occur when the previous WP_Query object
* is not destroyed properly before another is set up.
*
* @since 2.3.0
*
* @global WP_Query $wp_query Global WP_Query instance.
* @global WP_Query $wp_the_query Copy of the global WP_Query instance created during wp_reset_query().
*/
function wp_reset_query() {
$GLOBALS['wp_query'] = $GLOBALS['wp_the_query'];
wp_reset_postdata();
}
אם תתנו מבט בפונקציה wp_reset_query
, תגלו שהיא משתמש בפונקציה הקודמת wp_reset_postdata בכדי לשחזר את משתנה ה $post
הגלובאלי לפוסט הנוכחי בשאילתא הראשית (Main Query):
<?php
// destroy and reset the query
function wp_reset_query() {
unset($GLOBALS['wp_query']);
$GLOBALS['wp_query'] =& $GLOBALS['wp_the_query'];
wp_reset_postdata(); // <-- RESET QUERY
}
// restore the query
function wp_reset_postdata() {
global $wp_query;
if ( !empty($wp_query->post) ) {
$GLOBALS['post'] = $wp_query->post;
setup_postdata($wp_query->post);
}
}
אז שתי הפונקציות wp_reset_query
ו wp_reset_postdata
מאפסות את האובייקט על ידי שחזור המשתנה הגלובלי $post
אך הפונקציה wp_reset_query
לוקחת זאת צעד אחד קדימה ואף הורסת את השאילתא הקודמת (את ה Query שיצרתם) לפני שמאפסת את האובייקט.
יכול להיות שההסבר על חלק זה דורש ניסוח שונה… עובד על זה 🙂
פעולה זו חשובה כאשר משתמשים ב query_posts
כפי שתראו בדוגמה הבאה:
<?php query_posts('posts_per_page=3');
if (have_posts()) : while (have_posts()) : the_post(); ?>
<h1><a href="<?php the_permalink(); ?>"><?php the_title(); ?></a></h1>
<?php endwhile; endif; ?>
<?php wp_reset_query(); ?>
מתי להשתמש? לאחר לולאת
query_posts
בכדי לאפס את העניינים לאחר שימוש ב Custom Query.
הפונקציה rewind_posts
אחרונה חביבה היא הפונקציה rewind_posts()
וכשמה כן היא, מחזירה את הלולאה בכדי שתוכלו להשתמש באותה שאילתא (Query). גם כן אינה מקבלת פרמטרים, אינה מחזירה שום ערך ונראית בצורה הבאה:
<?php rewind_posts(); ?>
אז בכדי להבין מתי להשתמש ב rewind_posts()
, בואו נאמר שאנו מעוניינים באותו Query בשתי מקומות שונים באותו עמוד. בלולאה הראשונה בכדי להציג אך ורק את שמות הפוסטים ובלולאה שנייה בכדי להציג את התוכן של אותם פוסטים. בכדי לעשות שימוש נוסף באותה לולאה אנו מוסיפים את rewind_posts
לאחר הלולאה הראשונה כבדוגמה הבאה:
<?php if (have_posts()) : while (have_posts()) : the_post(); ?>
<h1><a href="<?php the_permalink(); ?>"><?php the_title(); ?></a></h1>
<?php endwhile; endif; ?>
<?php rewind_posts(); ?>
<?php while (have_posts()) : the_post(); ?>
<?php the_content(); ?>
<?php endwhile; ?>
אז כאשר wp_reset_query
ו wp_reset_postdata
מאפסות את האובייקט לגמרי, הפונקציה rewind_posts
פשוט מאפסת את המספור כפי שניתן לראות בקובץ wp-includes/query.php
:
<?php
// rewind the posts and reset post index
function rewind_posts() {
$this->current_post = -1;
if ( $this->post_count > 0 ) {
$this->post = $this->posts[0];
}
}
מתי להשתמש? כאשר את עושים שימוש נוסף בלולאה באותו עמוד.
לסיכום
ראינו שלוש דוגמאות המציגות כיצד ניתן לאפס הלולאה בוורדפרס. אם נאמר את ההבדל בינהן בצורה מעט שונה, אז יש להשתמש ב wp_reset_query
בכדי לוודא כי השאילתא הראשית (Main Query) מתאפסת לשאילתא הראשית המקורית. ויש להשתמש ב wp_reset_postdata
בכדי לוודא כי המשתנה הגלובלי $post
משוחזר חזרה לפוסט הנוכחי השאילתא הראשית.
זאת אומרת שיש להשתמש ב wp_reset_query
רק כאשר משתמשים בפונקציה query_posts
אך חשוב לדעת כי אין עליכם להשתמש ב query_posts
לעולם כפי שתראו בהסבר הבא.
הפונקציה rewind_posts
די ברורה אני חושב. בכל מקרה אני מקווה שהצלחתי לעשות מעט סדר בדברים ולא לבלבל. זה לא פשוט לתת הסברים טכניים מסוג זה בעברית אך עשיתי כמיטב יכולתי. אם טעיתי או שישנן השגות לגבי הנאמר אשמח אם תתקנו אותי בתגובות וכולנו נלמד….
Thanks to DigWP.
תודה רבה על איסוף הפונקציות האלה ביחד! מאוד שימושי. אני חושבת שלא הכרתי את הפונקציה rewind_posts, והיא נראית אחלה , אז תודה.
ומעולה שהוספת בסוף את האזהרה להשתדל להימנע משימוש ב – query_posts.
על לא דבר 🙂