有一个长期存在的WordPress核心bug(#16373) 其中,如果在查询字符串中注册并存在自定义查询变量,则不会设置查询is_front_page()
是的,即使\'page\' == get_option( \'show_on_front\' )
. 完整的详细信息在trac票证中,但最终结果是首页返回无效页面,而不是get_option( \'page_on_front\' )
.
我有一个特定的用例,在这个用例中,我需要将自定义查询变量传递给首页上的查询字符串(使用表单传递已注册的查询变量,这些查询变量反过来又用于过滤主题选项-前端主题选项演示)。上述trac票证因无效而关闭,因此我需要解决问题。
我可以很容易地强制使用首页模板,如下所示:
function themeslug_force_front_page_template( $template ) {
if ( \'\' != get_query_var( \'foobar\' ) ) { // Registered custom query var
return get_front_page_template();
}
return $template;
}
add_filter( \'template_include\', \'themeslug_force_front_page_template\' );
但是,基础查询条件不受影响。因此,任何代码都依赖于
is_front_page()
存在
true
(例如,仅显示在站点首页上的滑块)仍然无法正确渲染。
我已尝试修改$query
在pre_get_posts
, 但这似乎不起作用:
function themeslug_force_static_front_page( $query ) {
if ( $query->is_main_query() ) {
if ( \'page\' == get_option( \'show_on_front\' ) ) {
if ( \'\' != get_query_var( \'foobar\' ) ) { // Registered custom query var
$query->set( \'page_id\', get_option( \'page_on_front\' ) );
$query->set( \'is_home\', false );
$query->set( \'is_page\', true );
$query->set( \'is_front_page\', true );
}
}
}
}
add_action( \'pre_get_posts\', \'themeslug_force_static_front_page\' );
不会修改查询条件。我是否在回拨中尝试错误?是否有其他/更好的方法来强制查询条件,尤其是
is_front_page()
?
编辑请注意,设置page_id
does 在中工作pre_get_posts
回调:
$query->set( \'page_id\', get_option( \'page_on_front\' ) );
如果我省略
template_include
过滤器,显示的页面实际上是分配给首页的页面;然而
get_page_template()
使用,而不是
get_front_page_template()
. 所以,设置
page_id
在
pre_get_posts
确实导致
is_page()
是真的。但是前面提到的bug阻止了
is_front_page()
从设置为
true
.
根据@toscho的请求编辑2,这里是一些查询变量代码,用于上下文。
注册查询变量:
/**
* Add options-related query variables
*/
function themslug_add_theme_demo_query_vars( $qvars ) {
$qvars[] = \'demo_foo\';
$qvars[] = \'demo_bar\';
$qvars[] = \'demo_baz\';
return $qvars;
}
add_filter( \'query_vars\', \'themeslug_add_theme_demo_query_vars\' );
(其中
foo
,
bar
, 和
baz
是主题选项-背景、各种颜色等)
它们的使用方法只是向主题选项添加一个过滤器——这部分超出了问题的范围,所以我将在这里省略它。
它们通过自定义小部件在前端输出。小部件输出只是一个表单。以下是其中一个表单字段的示例:
<h3>Foo</h3>
<input name="demo_foo" id="demo_foo" class="pickcolor" type="text" value="<?php echo $foo_setting; ?>" data-default-color="<?php echo $foo_setting; ?>" />
提交时生成的查询字符串:
www.example.com/?foo=some_value
最合适的回答,由SO网友:s1lv3r 整理而成
你检查过is_front_page() 是否导致返回false?
我可以通过跟踪trac记录单的设置来重现该问题。在我的例子中,在这个函数中is_page() 正在返回false
.
我想这是因为$wp_query->set()
对于page_id
和is_page
只会导致query_vars
要更改,您不需要更改“查询状态”本身。
我可以通过在代码中附加这两行代码来创建一个解决方案:
$query->is_page = true;
$query->queried_object = get_post(get_option(\'page_on_front\') );
这导致(在我的设置中)页面正确显示在frontpage上(尽管URL中存在query\\u var),并且
is_front_page()
正在返回
true
.
我希望这对你有进一步的帮助。
如果你看看WP_Query 类,您将看到有一个变量$query_vars
还有一个变量$is_page
.
这个set
您使用的函数($query->set( \'is_page\', true );
) 只设置了query var:
function set($query_var, $value) {
$this->query_vars[$query_var] = $value;
}
它不会更改保存在中的状态信息
$query->is_page = true
, 相反,它设置查询变量
$query->query_vars[\'is_page\'] = true
.
如果您来自OOP方法并理解WP_Query::set()
作为一个经典的类setter函数,事实并非如此。