我正在使用一个小的快捷码输出一个按几十年排列的电影标题列表。decades
是我的自定义分类法,术语如下1930s
1940s
等
以下是我的短代码:
[fashionfilms type=fashionfilms tax=decades]
下面是如何解析该短代码:
add_shortcode(\'fashionfilms\', \'cw_output_fashion_films\');
function cw_output_fashion_films($atts){
$post_type = $atts[\'type\'];
$tax = $atts[\'tax\'];
$tax_terms = get_terms($tax);
if ($tax_terms) {
echo "<ul>";
foreach ($tax_terms as $tax_term) {
$args=array(
\'post_type\' => $post_type,
"$tax" => $tax_term->slug,
\'post_status\' => \'publish\',
\'posts_per_page\' => -1,
\'ignore_sticky_posts\'=> 1
);
$my_query = null;
$my_query = new WP_Query($args);
if( $my_query->have_posts() ) {
echo "<li class=\'letter\'>" . $tax_term->name . "</li>";
while ($my_query->have_posts()) : $my_query->the_post(); ?>
<li><a href="<?php the_permalink() ?>" rel="bookmark" title="Permanent Link to <?php the_title_attribute(); ?>"><?php the_title(); ?></a></li>
<?php
endwhile;
}
wp_reset_query();
} //end foreach loop
echo "</ul>";
}
}
问题是我的条目输出量增加了一倍。
要查看翻倍的内容,请查看我的实时链接here.
以下是我的页面模板代码:
<div class="span9">
<?php while ( have_posts() ) : the_post(); ?>
<div <?php post_class(); ?>>
<h1><?php the_title();?></h1>
<div class="content">
<?php the_content() ?>
</div>
</div><!-- /.post_class -->
<?php endwhile; ?>
<?php bootstrapwp_content_nav(\'nav-below\');?>
</div><!-- /.span9 -->
我做错了什么?我怎样才能解决这个问题?
最合适的回答,由SO网友:Tom J Nowell 整理而成
你用过wp_reset_query
, 但是,您应该使用wp_reset_postdata
.
wp_reset_query
获取当前查询对象,并将其替换为主查询。然而,这里的问题是,您使用的是WP\\u Query,它是一个单独的查询对象,主查询没有被触及,不需要保留。
这意味着我们不需要打电话wp_reset_query
, 因为查询从未更改。
我们确实打过电话$my_query->the_post
然而这意味着当前帖子数据来自您的自定义查询,需要重置,因此我们调用wp_reset_postdata
.
使命感wp_reset_query
当你不需要的时候,可能会产生意想不到的后果,在这种情况下,重复你的帖子
SO网友:Otto
虽然其他答案更具体,但您有一个更紧迫的问题:
Shortcodes should not create output.
我的意思是,您的shortcode处理程序函数永远不应该“回显”任何内容。它应该构建一个字符串并返回它。短代码处理代码将负责将其正确插入内容并为您回显。
如果你自己重复这些东西,那么你的短代码将与很多其他东西不兼容。短代码不仅在输出内容时才被处理,其他代码也可以处理它们。
在短代码(或过滤器)期间进行回音有时会导致输出两次或更多,因为短代码可以在同一页面加载上运行两次(或更多)。
更改函数以返回字符串,而不是回显您试图生成的内容。
更多信息:http://ottopress.com/2011/actions-and-filters-are-not-the-same-thing/
SO网友:Stephen Harris
问题不是wp_reset_query()
它本身。然而,正如@TomJNowell指出的,@hampusn最初建议的那样,您应该使用wp_reset_postdata()
由于您没有更改主查询,因此不需要重置它。
wp\\u reset\\u查询的作用
在呼叫顶部
wp_reset_postdata()
,
wp_reset_query()
只替换主查询
$wp_query
具有
$wp_the_query
(存储的副本)。这两者通过引用链接,因此应该是相同的。。。除非链接断开
$wp_query
更改人
query_posts()
(其中
wp_reset_query()
是有意的)。
当query_posts()
正在使用问题从这里开始。query_posts()
更改查询$wp_query
并破坏参考。这就是你循环的内容。让我们假设这个新循环中的第一篇帖子就是使用您的短代码的帖子。在您的呼叫回调中使用wp_reset_query()
.
$wp_query
现在设置回原始查询-这是我们刚刚打印的帖子的查询。因此,循环基本上重置为原始查询(在本文中,我对问题的评论有点错误*)。此循环打印帖子的内容,并到达末尾。
为什么使用wp_reset_postdata
\'解决它
如果使用
query_posts()
结果就是你想要的那篇文章——这会导致重复。
为什么不使用wp_reset_postdata
\'解决它
如果使用
query_posts()
结果包括其他帖子,然后第一次循环将包括这些其他帖子。
解决方案:
简而言之,使用
query_posts()
. 不要使用它。使用
wp_reset_postdata
, 虽然在这种情况下正确的做法是掩盖错误。
但我没有使用query_posts()
...
我不能确定是否有其他错误会导致您看到的内容。但是在“干净”的安装中,您不应该在上面的代码中看到它(我已经测试过)。
*如果$wp_query
和$wp_the_query
仍然通过引用链接,那么我的评论实际上是正确的