各位WordPress探险家们,欢迎来到今天的“解剖小工具”讲座! 今天我们要一起深入WordPress的 add_dashboard_widget() 函数,把它扒个精光,看看它到底是怎么把那些花花绿绿的仪表盘小工具变出来的。 别害怕,虽然我们要看代码,但我保证尽量说人话,让大家听得懂,看得明白,还能举一反三。
开场白:仪表盘上的“小玩具”
WordPress后台仪表盘,咱们每天都要光顾的地方,上面那些“站点概览”、“快速草稿”、“WordPress新闻”等等,都是仪表盘小工具。 这些小工具可以让你快速了解网站的各种信息,或者执行一些常用操作。 而 add_dashboard_widget() 函数,就是创建和注册这些小工具的关键。
add_dashboard_widget():它的庐山真面目
首先,我们来认识一下 add_dashboard_widget() 函数的基本结构:
<?php
/**
* Adds a new dashboard widget.
*
* @since 2.7.0
*
* @param string $widget_id Required. The widget slug.
* @param string $widget_name Required. The widget title.
* @param callable $callback Required. Function that fills the widget with the desired content. The function should echo its output.
* @param callable $control_callback Optional. Function that outputs controls for the widget.
* @param array $callback_args Optional. Array of extra arguments to pass to the callback functions.
*/
function add_dashboard_widget( string $widget_id, string $widget_name, callable $callback, callable $control_callback = null, array $callback_args = null ) {
global $wp_meta_boxes;
$id_attr = sanitize_html_class( $widget_id );
$wp_meta_boxes['dashboard'][$id_attr]['normal']['core'][$widget_id] = array(
'id' => $widget_id,
'title' => $widget_name,
'callback' => $callback,
'args' => $callback_args,
'control_callback' => $control_callback,
);
return true;
}
看起来有点吓人? 别怕,我们来逐个击破:
$widget_id(string, 必需): 小工具的唯一ID,就像你的身份证号一样,不能重复。 建议使用插件或主题的slug作为前缀,避免冲突。 例如:my_plugin_custom_widget。$widget_name(string, 必需): 小工具的标题,显示在仪表盘上,给人看的。 例如:"我的自定义小工具"。$callback(callable, 必需): 这是个大人物!它是一个函数,负责生成小工具的内容,也就是你希望在小工具里显示什么东西。 记住,这个函数应该echo输出内容,而不是return。$control_callback(callable, 可选): 另一个函数,负责生成小工具的设置选项。 如果你的小工具需要用户自定义一些东西,比如显示多少条数据,就可以用它来添加设置界面。$callback_args(array, 可选): 一个数组,用来传递额外参数给$callback和$control_callback函数。 就像给函数喂零食一样,让它们吃饱了好好干活。
add_dashboard_widget() 的工作原理:幕后推手
add_dashboard_widget() 函数本质上做的事情很简单:它把你的小工具信息(ID、标题、回调函数等等)放进一个全局变量 $wp_meta_boxes 里面。 这个 $wp_meta_boxes 就像一个巨大的仓库,WordPress会在显示仪表盘的时候,从这个仓库里取出所有的小工具信息,然后调用相应的回调函数,把小工具渲染出来。
具体来说,它把小工具的信息存放在如下的数组结构中:
$wp_meta_boxes['dashboard'][$id_attr]['normal']['core'][$widget_id]
dashboard: 表示这个小工具是用于仪表盘的。$id_attr: 这是经过sanitize_html_class()函数处理过的$widget_id,确保它是有效的HTML class name。normal: 表示小工具的位置,normal表示在正常区域(通常是左侧),还有side表示侧边栏。core: 表示小工具的优先级,core表示核心小工具。 你可以自定义优先级,例如high或low,来控制小工具的显示顺序。$widget_id: 小工具的ID。
这个多维数组就像一个复杂的地址,WordPress可以通过这个地址找到你的小工具的所有信息。
实战演练:创建一个简单的仪表盘小工具
光说不练假把式,现在我们就来创建一个简单的仪表盘小工具,显示一句问候语。
<?php
/**
* 添加一个自定义的仪表盘小工具.
*/
function my_custom_dashboard_widget() {
add_dashboard_widget(
'my_greeting_widget', // 小工具ID
'我的问候语小工具', // 小工具标题
'my_greeting_widget_content' // 内容生成函数
);
}
add_action( 'wp_dashboard_setup', 'my_custom_dashboard_widget' );
/**
* 生成小工具的内容.
*/
function my_greeting_widget_content() {
$current_hour = date('G'); // 获取当前小时 (0-23)
if ($current_hour >= 6 && $current_hour < 12) {
$greeting = '早上好!';
} elseif ($current_hour >= 12 && $current_hour < 18) {
$greeting = '下午好!';
} else {
$greeting = '晚上好!';
}
echo '<p>' . $greeting . '</p>';
}
这段代码做了什么?
my_custom_dashboard_widget()函数:- 它使用
add_dashboard_widget()函数注册了一个新的仪表盘小工具。 $widget_id是'my_greeting_widget'。$widget_name是'我的问候语小工具'。$callback是'my_greeting_widget_content',指定了内容生成函数。
- 它使用
add_action( 'wp_dashboard_setup', 'my_custom_dashboard_widget' ):- 这行代码非常重要! 它告诉WordPress,在
wp_dashboard_setup这个动作发生时,执行my_custom_dashboard_widget()函数。wp_dashboard_setup动作会在仪表盘加载时触发,所以我们的函数就能在这个时候注册小工具。
- 这行代码非常重要! 它告诉WordPress,在
my_greeting_widget_content()函数:- 这个函数负责生成小工具的内容。
- 它根据当前时间,选择合适的问候语。
- 最后,使用
echo输出问候语。
把这段代码放到你的主题的 functions.php 文件或者一个自定义插件里,登录WordPress后台,你就能看到一个新的小工具出现在仪表盘上,显示着根据当前时间生成的问候语。
进阶技巧:添加设置选项
如果你的小工具需要用户自定义一些东西,比如显示多少条最新的文章,你可以使用 $control_callback 参数来添加设置选项。
<?php
/**
* 添加一个带有设置选项的仪表盘小工具.
*/
function my_custom_dashboard_widget_with_settings() {
add_dashboard_widget(
'my_posts_widget', // 小工具ID
'我的最新文章小工具', // 小工具标题
'my_posts_widget_content', // 内容生成函数
'my_posts_widget_control' // 设置选项生成函数
);
}
add_action( 'wp_dashboard_setup', 'my_custom_dashboard_widget_with_settings' );
/**
* 生成小工具的内容.
*/
function my_posts_widget_content() {
$num_posts = get_option( 'my_posts_widget_num_posts', 5 ); // 获取用户设置的文章数量,默认为5
$args = array(
'posts_per_page' => $num_posts,
'orderby' => 'date',
'order' => 'DESC',
);
$posts = get_posts( $args );
if ( $posts ) {
echo '<ul>';
foreach ( $posts as $post ) {
echo '<li><a href="' . get_permalink( $post->ID ) . '">' . esc_html( $post->post_title ) . '</a></li>';
}
echo '</ul>';
} else {
echo '<p>还没有文章。</p>';
}
}
/**
* 生成设置选项.
*/
function my_posts_widget_control() {
$num_posts = get_option( 'my_posts_widget_num_posts', 5 ); // 获取用户设置的文章数量,默认为5
?>
<p>
<label for="my_posts_widget_num_posts">显示文章数量:</label>
<input type="number" id="my_posts_widget_num_posts" name="my_posts_widget_num_posts" value="<?php echo esc_attr( $num_posts ); ?>" min="1" max="20">
</p>
<button type="button" class="button button-primary" id="my_posts_widget_save_button">保存</button>
<script type="text/javascript">
jQuery(document).ready(function($) {
$('#my_posts_widget_save_button').click(function() {
var num_posts = $('#my_posts_widget_num_posts').val();
$.post(ajaxurl, {
action: 'my_posts_widget_save_settings',
num_posts: num_posts,
security: '<?php echo wp_create_nonce('my_posts_widget_save_settings'); ?>' // 添加nonce以确保安全性
}, function(response) {
if (response == 'success') {
alert('设置已保存!');
} else {
alert('保存失败!');
}
});
});
});
</script>
<?php
}
/**
* 处理AJAX请求,保存设置.
*/
add_action( 'wp_ajax_my_posts_widget_save_settings', 'my_posts_widget_save_settings' );
function my_posts_widget_save_settings() {
check_ajax_referer( 'my_posts_widget_save_settings', 'security' ); // 验证nonce
$num_posts = intval( $_POST['num_posts'] ); // 获取用户输入的文章数量
if ( $num_posts >= 1 && $num_posts <= 20 ) {
update_option( 'my_posts_widget_num_posts', $num_posts ); // 保存设置
echo 'success';
} else {
echo 'error';
}
wp_die(); // 结束AJAX请求
}
这段代码比之前的复杂了一些,我们来一步步分析:
my_custom_dashboard_widget_with_settings()函数:- 与之前的例子类似,它使用
add_dashboard_widget()函数注册了一个新的仪表盘小工具。 - 但是,这次它还指定了
$control_callback为'my_posts_widget_control'。
- 与之前的例子类似,它使用
my_posts_widget_content()函数:- 这个函数负责生成小工具的内容,显示最新的文章。
- 它使用
get_option( 'my_posts_widget_num_posts', 5 )函数获取用户设置的文章数量。 如果用户没有设置,则默认为5。 - 然后,它使用
get_posts()函数获取指定数量的最新文章,并显示出来。
my_posts_widget_control()函数:- 这个函数负责生成设置选项的界面。
- 它创建了一个输入框,让用户可以输入要显示的文章数量。
- 它还添加了一个保存按钮,当用户点击这个按钮时,会通过AJAX请求保存设置。
- 安全性: 代码中使用了
wp_create_nonce()和check_ajax_referer()函数来确保AJAX请求的安全性,防止跨站请求伪造(CSRF)攻击。
my_posts_widget_save_settings()函数:- 这个函数负责处理AJAX请求,保存用户设置的文章数量。
- 它首先使用
check_ajax_referer()函数验证nonce,确保请求的合法性。 - 然后,它使用
update_option()函数保存用户设置的文章数量。
需要注意的几个点:
- CSS样式: 仪表盘小工具的样式是WordPress提供的,你不需要自己写太多的CSS代码。 但是,如果你需要自定义样式,可以添加自己的CSS代码。
- JavaScript: 如果你需要在小工具中使用JavaScript,可以使用
wp_enqueue_scripts()函数加载你的JavaScript文件。 记得要在wp_dashboard_setup动作中加载JavaScript文件,确保它们在仪表盘加载时可用。 - 数据缓存: 如果你的小工具需要从数据库或者外部API获取数据,建议使用WordPress的缓存机制(Transient API)来缓存数据,提高性能。
- 权限控制: 如果你的小工具只能让特定用户访问,可以使用
current_user_can()函数检查用户的权限。
$wp_meta_boxes 的更多可能性
$wp_meta_boxes 这个全局变量不仅仅用于仪表盘小工具,它还用于定义文章编辑页面上的自定义字段(Meta Boxes)。 实际上,add_meta_box() 函数最终也是把信息存放到 $wp_meta_boxes 里面。
remove_dashboard_widget(): 移除已注册的小工具。
function remove_dashboard_widget( string $widget_id, string $context = 'normal', string $priority = 'core' ): bool {
global $wp_meta_boxes;
$id_attr = sanitize_html_class( $widget_id );
unset( $wp_meta_boxes['dashboard'][ $id_attr ][ $context ][ $priority ][ $widget_id ] );
return true;
}
$widget_id(string, 必需): 要移除的小工具的ID。$context(string, 可选): 小工具所在的区域,默认为'normal'。 可以是'normal'或'side'。$priority(string, 可选): 小工具的优先级,默认为'core'。 可以是'high','core','default'或'low'。
表格总结:
| 参数 | 类型 | 必需 | 描述 |
|---|---|---|---|
$widget_id |
string | 是 | 小工具的唯一ID。 |
$widget_name |
string | 是 | 小工具的标题。 |
$callback |
callable | 是 | 用于生成小工具内容的函数。 |
$control_callback |
callable | 否 | 用于生成小工具设置选项的函数。 |
$callback_args |
array | 否 | 传递给 $callback 和 $control_callback 函数的额外参数。 |
| 函数 | 描述 |
|---|---|
add_dashboard_widget() |
注册一个新的仪表盘小工具。 |
remove_dashboard_widget() |
移除已注册的仪表盘小工具。 |
wp_create_nonce() |
创建一个nonce,用于验证AJAX请求的安全性。 |
check_ajax_referer() |
验证nonce,确保AJAX请求的合法性。 |
get_option() |
获取WordPress选项。 |
update_option() |
更新WordPress选项。 |
get_posts() |
获取文章列表。 |
wp_enqueue_scripts() |
加载JavaScript文件。 |
current_user_can() |
检查当前用户是否有指定权限。 |
结束语:小工具,大世界
add_dashboard_widget() 函数只是WordPress众多强大函数中的一个,但它却能让你轻松地扩展WordPress的功能,让你的仪表盘更加个性化。 掌握了它,你就可以为自己和你的用户创建各种各样的小工具,提高工作效率,更好地管理网站。
希望今天的讲座对大家有所帮助。 记住,编程就像探险,勇敢地去尝试,去探索,你会发现一个充满惊喜的世界。 祝大家编程愉快!