这不再是使用主题选项的推荐方式。建议使用Customizer API,以便为用户提供更多控制和灵活性。
主题作者可能需要提供一个设置界面,以便用户可以自定义其主题的使用或工作方式。最好的方法是创建一个管理菜单项,该菜单项允许用户从所有管理界面访问该设置界面。
函数参考
菜单页面
子菜单页面
WordPress管理菜单
- add_dashboard_page()
- add_posts_page()
- add_media_page()
- add_links_page()
- add_pages_page()
- add_comments_page()
- add_theme_page()
- add_plugins_page()
- add_users_page()
- add_management_page()
- add_options_page()
每个情节都需要一个钩子
要添加管理菜单,您需要做三件事:
- 创建一个包含菜单构建代码的函数。
- 如果要为网络添加菜单,请使用
admin_menu
动作挂钩-或network_admin_menu
注册上述函数 。 - 创建界面的HTML输出,单击菜单项时显示该界面。
大多数开发人员忽略了此列表中的第二步。您不能简单地调用菜单代码。您需要将其放在一个函数中,然后注册该函数。
这是描述的这三个步骤的简单示例。这将在“设置”顶级菜单下添加一个子菜单项。选择后,该菜单项将显示一个非常基本的界面。
<?php
/** Step 2 (from text above). */
add_action( 'admin_menu', 'my_menu' );
/** Step 1. */
function my_menu() {
add_options_page(
'My Options',
'My Menu',
'manage_options',
'my-unique-identifier',
'my_options'
);
}
/** Step 3. */
function my_options() {
if ( !current_user_can( 'manage_options' ) ) {
wp_die( __( 'You do not have sufficient permissions to access this page.' ) );
}
echo 'Here is where I output the HTML for my screen.';
echo '</div><pre>';
}
?>
在此示例中,函数my_menu()
通过函数 add_options_page()
将新项目添加到“设置”管理菜单。
注意:请注意,步骤2 中的add_action()
调用将my_menu()
函数注册在admin_menu挂钩下。否则,add_action()
调用将引发未定义函数的PHP错误。最后,add_options_page()
调用的my_options()
包含某人单击菜单项时要显示的实际页面(以及要处理的PHP代码)的函数。
在下面的章节中将更详细地描述这些步骤。请记住将菜单和页面的创建包含在函数中,并使用该admin_menu
挂钩在正确的时间启动整个过程。
确定新菜单位置
在创建新菜单之前,首先确定该菜单是顶级菜单还是子菜单项。顶级菜单在管理菜单中显示为新部分,并包含子级菜单项。这意味着子级菜单项是现有顶级菜单的成员。
很少有主题需要创建一个新的顶层菜单。如果主题为WordPress引入了一个全新的概念并且需要很多界面来实现,则该主题可能需要一个新的等级菜单。仅当您确实需要多个相关界面以使WordPress执行其最初设计无法完成的操作时,才应考虑添加顶级菜单。新的顶级菜单的示例可能包括作业管理或会议( conference )管理。请注意,通过内置的文章类型注册,WordPress会自动创建顶级菜单来管理此类功能。
如果不需要创建顶级菜单,则需要决定在哪个顶级菜单下放置新的子级菜单项。
可以根据WordPress顶级菜单的位置来确定子菜单项的正确位置:
- 仪表板–您站点的信息中心,包括用于更新WordPress核心、插件和主题的“更新”选项。
- 文章–显示用于撰写文章的工具。
- 媒体–上传和管理您的图片、视频和音频。
- 链接–管理对其他博客和感兴趣站点的引用。(已弃用)
- 页面–显示用于编写称为页面的静态内容的工具。
- 评论–控制和规范读者对文章的回应。
- 外观–显示用于控制主题/样式文件、侧边栏等控件。
- 插件–显示有关插件管理的控件,而不是插件本身的配置选项。
- 用户–显示用于用户管理的控件。
- 工具–管理博客数据的导出,导入,甚至备份。
- 设置–显示只有管理员才能查看的插件选项。
- 网络管理员–显示在多站点网络上设置选项。对于注册网络菜单,不要用
admin_menu
,应该使用network_admin_menu
(另请参阅创建网络)
顶级菜单
如果您确定主题需要全新的顶级菜单,则要做的第一件事就是使用该函数add_menu_page()
创建一个菜单。注意:如果不需要顶级菜单,请跳至“ 子菜单”。
参数值:
page_title
–选择菜单后在页面标题标签中显示的文本。menu_title
–菜单的界面名称文本。capability
–向用户显示此菜单所需的用户权限。使用设置API处理表单时,应在此处使用manage_options
,因为如果没有表单,用户将无法保存选项。用户级别已弃用,在此不应该使用。menu_slug
–引用此菜单所依据的子名称(此菜单应唯一)。在3.0版之前,这称为文件(或句柄)参数。如果省略function
参数,menu_slug
则应为处理菜单页面内容显示的PHP文件。function
–显示菜单页面内容的函数。icon_url
–此菜单使用的图标的位置。此参数是可选的。position
–该菜单应在菜单顺序中出现的位置。默认情况下,如果省略此参数,则菜单将出现在菜单结构的底部。要查看当前菜单位置, 请在菜单加载后使用print_r( $GLOBALS[ 'menu' ] )
。- 子菜单–定义了顶层菜单或选择使用现有的WordPress顶级菜单后,即可使用该
add_submenu_page()
函数定义一个或多个子级菜单项。
子菜单
如果您希望新菜单项作为子菜单项,则可以使用add_submenu_page()
函数来创建它。
参数值:
parent_slug
–父级菜单的slug别名,或提供要在其中插入子菜单的顶级菜单的标准WordPress管理文件的文件名,如果此子菜单进入自定义顶级菜单。例子:- 仪表板 –
add_submenu_page('index.php', ...)
- 文章–
add_submenu_page('edit.php', ...)
- 媒体–
add_submenu_page('upload.php', ...)
- 链接–
add_submenu_page('link-manager.php', ...)
- 页面–
add_submenu_page('edit.php?post_type=page', ...)
- 评论 –
add_submenu_page('edit-comments.php', ...)
- 自定义文章类型–
add_submenu_page('edit.php?post_type=your_post_type', ...)
- 外观–
add_submenu_page('themes.php', ...)
- 插件–
add_submenu_page('plugins.php', ...)
- 用户–
add_submenu_page('users.php', ...)
- 工具–
add_submenu_page('tools.php', ...)
- 设置–
add_submenu_page('options-general.php', ...)
- 仪表板 –
page_title
–子菜单页面标题的文本。menu_title
–选择菜单后在页面标题标签中显示的文本。capability
–向用户显示此菜单所需的用户权限。用户级别已弃用,在此不应该使用。menu_slug
–对于现有的WordPress菜单,该PHP文件用于处理菜单页面内容的显示。对于自定义顶级菜单的子菜单,是此子菜单页面的唯一标识符。function
–显示菜单页面内容的函数。从技术上讲,就像在add_menu_page
函数中一样,function
参数是可选的,但是如果未提供该参数,则WordPress将默认认为该PHP文件将生成管理界面,而无需调用函数。
使用包装函数
由于大多数子菜单都位于“设置”、“工具”或“外观”菜单下,因此WordPress提供了包装函数,这些函数使将子菜单项添加到这些顶级菜单变得更加容易。请注意,函数名称可能与在管理界面中看到的名称不匹配,因为它们随着时间的推移而发生了变化:
仪表板
<?php add_dashboard_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
文章
<?php add_posts_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
媒体
<?php add_media_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
链接
<?php add_links_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
页面
<?php add_pages_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
评论
<?php add_comments_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
外观
<?php add_theme_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
插件
<?php add_plugins_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
用户
<?php add_users_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
工具
<?php add_management_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
设置
<?php add_options_page( $page_title, $menu_title, $capability, $menu_slug, $function); ?>
另请参阅主题选项,以了解当前推荐的通过Customizer API创建选项的方式。
示例
这是一个快速示例,说明了如何插入顶级菜单页面和子菜单页面,其中子菜单页面上的标题与顶级页面不同。在此示例中,register_my_theme_more_settings_menu
是显示第一个子菜单页面的函数的名称:
function register_my_theme_settings_menu() {
add_menu_page(
"My Theme's Settings",
"My Theme",
"manage_options",
"my-theme-settings-menu"
);
}
function register_my_theme_more_settings_menu() {
add_submenu_page(
"my-themes-settings-menu",
"More Settings for My Theme",
"More Settings",
"manage_options",
"my-theme-more-settings-menu"
);
}
add_action( "admin_menu", "register_my_theme_settings_menu");
add_action( "admin_menu", "register_my_theme_more_settings_menu");
插入页面
这是一个如何在多个位置插入多个菜单的示例:
<?php
// 添加管理菜单的钩子
add_action('admin_menu', 'mt_add_pages');
// 挂载到上面钩子的函数
function mt_add_pages() {
// 在设置下添加子菜单
add_options_page(__('Test Settings','menu-test'), __('Test Settings','menu-test'), 'manage_options', 'testsettings', 'mt_settings_page');
// 在工具下添加子菜单
add_management_page( __('Test Tools','menu-test'), __('Test Tools','menu-test'), 'manage_options', 'testtools', 'mt_tools_page');
// 添加顶级菜单
add_menu_page(__('Test Toplevel','menu-test'), __('Test Top-level','menu-test'), 'manage_options', 'mt-top-level-handle', 'mt_toplevel_page' );
//添加子菜单到自定义的顶级菜单
add_submenu_page('mt-top-level-handle', __('Test Sub-Level','menu-test'), __('Test Sub-Level','menu-test'), 'manage_options', 'sub-page', 'mt_sublevel_page');
// 添加第二个子菜单到自定义的顶级菜单
add_submenu_page('mt-top-level-handle', __('Test Sub-Level 2','menu-test'), __('Test Sub-Level 2','menu-test'), 'manage_options', 'sub-page2', 'mt_sublevel_page2');
}
// mt_settings_page() 显示设置下子菜单页面的内容
function mt_settings_page() {
echo "</pre>
<h2>" . __( 'Test Settings', 'menu-test' ) . "</h2>
<pre>
";
}
// mt_tools_page() 显示工具下子菜单的内容
function mt_tools_page() {
echo "</pre>
<h2>" . __( 'Test Tools', 'menu-test' ) . "</h2>
<pre>
";
}
// mt_toplevel_page() 显示自定义顶级菜单的内容
function mt_toplevel_page() {
echo "</pre>
<h2>" . __( 'Test Top-Level', 'menu-test' ) . "</h2>
<pre>
";
}
// mt_sublevel_page() 显示第一个子菜单的内容
// of the custom Test Toplevel menu
function mt_sublevel_page() {
echo "</pre>
<h2>" . __( 'Test Sub-Level', 'menu-test' ) . "</h2>
<pre>
";
}
// mt_sublevel_page2() 显示第二个子菜单的内容
// of the custom Test Top-Level menu
function mt_sublevel_page2() {
echo "</pre>
<h2>" . __( 'Test Sub-Level 2', 'menu-test' ) . "</h2>
<pre>
";
}
?>
菜单页示例
注意:有关创建设置页面的信息,请参见Settings API。
前面的示例包含几个虚拟函数,例如mt_settings_page()
,作为实际页面内容的占位符。让我们扩展它们。如果您想创建一个名为mt_favorite_color
的选项,该选项使站点所有者可以通过“设置”页面键入自己喜欢的颜色怎么办?mt_options_page()
函数将需要在界面上输出数据输入表单,并处理输入的数据。
这是执行此操作的函数:
// mt_settings_page() 显示设置下子菜单的页面
function mt_settings_page() {
//必须检查当前用户是否有对应的权限
if (!current_user_can('manage_options'))
{
wp_die( __('您没有足够的权限访问该页面。') );
}
// 字段和选项名称变量
$opt_name = 'mt_favorite_color';
$hidden_field_name = 'mt_submit_hidden';
$data_field_name = 'mt_favorite_color';
// 从数据库中读取现有的选项值
$opt_val = get_option( $opt_name );
// 查看用户是否向我们提交了一些信息
// 如果他们这样做了,则此隐藏字段将设置为“Y”
if( isset($_POST[ $hidden_field_name ]) && $_POST[ $hidden_field_name ] == 'Y' ) {
// 获取所提交的信息
$opt_val = $_POST[ $data_field_name ];
// 保存所提交的信息到数据库
update_option( $opt_name, $opt_val );
// 在屏幕上显示“设置已更新”消息
?>
<div class="updated"></div>
<div class="wrap">
<?php
// Header
echo "<h2>" . __( 'Menu Test Settings', 'menu-test' ) . "</h2>";
// 设置表单
?>
<form action="" method="post" name="form1"></form>
<?php _e("Favorite Color:", 'menu-test' ); ?>
<hr />
</div>
<?php } ?>
一些注意事项:
- WordPress函数(例如
add_menu_page()
和)add_submenu_page()
具有将用于确定显示顶级菜单还是子菜单的功能。 - 连接到处理页面输出的函数必须检查用户是否也具有所需的权限。
- WordPress管理函数负责验证用户登录名,因此您不必在函数中担心它。
- 上面的功能示例已国际化- 有关更多详细信息,请参见WordPress开发人员的I18n。
- 该函数在将数据输入表单显示在屏幕上之前会处理所有输入的数据,以便新的值可以在该表单显示(而不是数据库中的值)。
- 您不必担心第一次工作,因为WordPress
update_option
函数会自动将选项添加到数据库(如果尚不存在)。 - 每次您导航到Admin中的页面时,都会解析这些管理菜单的添加过程。因此,如果您编写的主题没有选项页面,但是以后添加了,则可以按照上述说明添加主题选项,然后重新上传,然后进行调整,直到满意为止。换句话说,激活主题后,菜单不会“永久添加”或放入数据库中。它们是动态解析的,因此您可以随意添加或减去菜单项,重新上传,更改将立即反映出来。
页面钩子后缀
增加管理菜单每一个函数:add_menu_page()
、add_submenu_page()
都有其专有的版本,如add_options_page()
-返回称为页面钩子后缀的特殊值。以后可以将它用作一个钩子,可以将仅在该特定页面上调用的操作注册到该钩子。
这样的动作挂钩之一是load-{page_hook}
,其中{page_hook}
就是这些add_*_page()
函数返回的值。加载特定页面时将调用此钩子。在以下示例中,它用于在除插件选项页面之外的所有管理页面上显示“未配置主题”通知:
<?php
add_action('admin_menu', 'my_menu');
// 您可以在此处检查是否已配置插件(例如,检查是否设置了某些选项)。如果没有,请添加新的钩子。
// 在此示例中,始终添加钩子。
add_action( 'admin_notices', 'my_admin_notices' );
function my_menu() {
// 添加新的管理菜单和页面并保存返回的钩子后缀
$hook_suffix = add_options_page('My Options', 'My Theme', 'manage_options', 'my-unique-identifier', 'my_options');
// 使用钩子后缀组成钩子,并注册加载插件的选项页面时执行的操作
add_action( 'load-' . $hook_suffix , 'my_load_function' );
}
function my_load_function() {
// 当前管理页面是我们插件的选项页面,因此不显示通知
// (删除对此负责的操作)
remove_action( 'admin_notices', 'my_admin_notices' );
}
function my_admin_notices() {
echo '<pre>
<div class="updated fade" id="notice">
My Plugin is not configured yet. Please do it now.</div>
</pre>';
}
function my_options() {
if (!current_user_can('manage_options')) {
wp_die( __('You do not have sufficient permissions to access this page.') );
}
echo '</pre>
<div class="wrap">';
echo 'Here is where the form would go if I actually had options.';
echo '</div>
<pre>
';
}
?>