1. Code
  2. WordPress
  3. Theme Development

La API de ajustes de WordPress, Parte 5: Navegación mediante pestañas para los ajustes

LLegados a este punto de la serie, ya hemos echado un vistazo de cerca a la API de ajustes y a lo que nos ofrece. Incluso hemos comenzado a crear nuestro propio tema para ayudar a demostrar todo lo que hemos estado aprendiendo. Hemos cubierto las secciones, los campos, los ajustes, los menús, las páginas y mucho más.
Scroll to top
This post is part of a series called The Complete Guide to the WordPress Settings API.
The WordPress Settings API, Part 4: On Theme Options
The WordPress Settings API, Part 6: Menu Pages

Spanish (Español) translation by Eva Collados Pascual (you can also view the original English article)

LLegados a este punto de la serie, ya hemos echado un vistazo de cerca a la API de ajustes y a lo que nos ofrece. Incluso hemos comenzado a crear nuestro propio tema para ayudar a demostrar todo lo que hemos estado aprendiendo. Hemos cubierto las secciones, los campos, los ajustes, los menús, las páginas y mucho más.

Si nos has estado siguiendo desde el principio, es probable que hayas notado que estos artículos son largos y con gran cantidad de código. Hemos llegado a los puntos principales de la API de ajustes, por lo que, para los restantes artículos, vamos a adoptar un enfoque más breve y centrado en el resto de los temas. Esto reducirá la longitud de nuestros artículos y la cantidad de código que estamos escribiendo y, con suerte, hará que algunas de las ideas sean un poco más fáciles de digerir.

La última vez, lo dejamos en medio del desarrollo: hemos creado con éxito nuestra propia página de opciones e introducido algunas nuevas, pero dejamos el proyecto en un estado que impedía que todas nuestras opciones se guardasen correctamente. En este artículo, vamos a echar un vistazo a la razón por la cual no podemos guardar nuestras opciones y a lo que podemos hacer para solucionarlo.

Antes de empezar: en este artículo se supone que ya estás familiarizado con la API de ajustes y las opciones de tema. Si eres un desarrollador de WordPress principiante o incluso intermedio, te recomiendo que te pongas al día con el resto de la serie antes de sumergirte en este artículo.


¿Por qué no se guardan mis opciones?

Si has estado siguiendo esta serie, tu página de opciones debería tener un aspecto similar al siguiente:

Theme OptionsTheme OptionsTheme Options

Todo se ve bien, pero hay un problema con esta configuración, los valores de las opciones sociales, "Social Options", se guardarán correctamente, pero las opciones de visualización, "Display Options", no. Antes de ir más lejos, es importante entender por qué somos capaces de renderizar nuestras opciones en una sola página, pero no podemos guardar ambas.

Recuerda que anteriormente en la serie, definimos dos conjuntos de ajustes para nuestro tema: "Display Options" y "Social Options". Mediante el uso de la API de ajustes, le estamos indicando a WordPress que cree entradas en la base de datos para cada grupo de ajustes. Dado que hemos definido dos grupos de ajustes, se crean dos filas en la base de datos. A continuación, la API de ajustes representa las opciones en el panel mediante elementos de formulario. A partir de ahí, WordPress toma los valores del formulario y los guarda en la base de datos.

Con el fin de proporcionar un mayor nivel de seguridad, WordPress asigna a cada grupo de ajustes un valor único conocido como nonce que protege contra ataques maliciosos. Dado que se aplica un valor nonce a cada grupo de ajustes, actualmente estamos representando un único formulario con dos nonces. Cuando envías el formulario al servidor, WordPress solo verá (y, por lo tanto, utilizará) el valor nonce "más reciente". En nuestro caso, este corresponderá a "Social Options". Como tal, solo se serializan esas opciones: las opciones de visualización, "Display Options", son ignoradas por completo.

Esto no es muy avanzado, de hecho, en realidad se pueden ver los dos valores nonce para cada una de nuestras secciones cuando se observa el código fuente de la página. Aquí está el nonce para "Display Options":

Theme OptionsTheme OptionsTheme Options

Y aquí está el nonce para "Social Options":

Theme OptionsTheme OptionsTheme Options

Los valores reales serán diferentes, pero el elemento de entrada existirá.

Una forma de evitar que este problema tenga lugar consiste en crear una página independiente para cada grupo de ajustes. Esta no es una mala solución, pero si solo estás trabajando en un grupo con una o dos opciones, crear una página completa nueva podría ser un poco exagerado.

Por suerte, WordPress es compatible con un término medio, todavía puedes mantener todos tus ajustes en una sola página, pero asegúrate de que los usuarios sean capaces de guardar todos sus ajustes y todavía tengan una experiencia de usuario agradable.


Introducir navegación mediante pestañas

Sin duda has visto en alguna ocasión una navegación con pestañas en el panel de WordPress. Basta con echar un vistazo a la página "Temas":

ThemesThemesThemes

La navegación con pestañas proporciona una buena alternativa para agrupar conjuntos de opciones relacionadas en una sola página sin sacrificar la experiencia general del usuario. Esto es lo que implementaremos en el tema Sandbox.

Antes de escribir cualquier código, siempre es una buena práctica enumerar exactamente lo que vamos a hacer durante el desarrollo.

  • Introducir dos pestañas: una para las opciones de visualización y otra para las opciones sociales
  • Establece "Display Options" como pestaña predeterminada cuando se cargue la página
  • Asegúrate de que la misma pestaña esté marcada como activa después de guardar una página de opciones concreta
  • Comprueba que se muestra el mensaje de actualización cuando se guarden los ajustes

Añadir pestañas individuales

En functions.php, localiza sandbox_theme_display. Esta es la función que estamos usando realmente para representar la página de opciones. A partir de ahora, debería tener este aspecto:

1
function sandbox_theme_display() {
2
?>
3
	<!-- Create a header in the default WordPress 'wrap' container -->
4
	<div class="wrap">
5
	
6
		<div id="icon-themes" class="icon32"></div>
7
		<h2>Sandbox Theme Options</h2>
8
		<?php settings_errors(); ?>
9
		
10
		<form method="post" action="options.php">
11
12
			<?php settings_fields( 'sandbox_theme_display_options' ); ?>
13
			<?php do_settings_sections( 'sandbox_theme_display_options' ); ?>	
14
			
15
			<?php settings_fields( 'sandbox_theme_social_options' ); ?>
16
			<?php do_settings_sections( 'sandbox_theme_social_options' ); ?>	
17
		
18
			<?php submit_button(); ?>
19
			
20
		</form>
21
		
22
	</div><!-- /.wrap -->
23
<?php
24
} // end sandbox_theme_display

Primero, vamos a presentar nuestras dos pestañas. Esto es relativamente sencillo, ya que vamos a aprovechar las clases CSS que ya proporciona WordPress, a saber, nav-tab-wrapper y nav-tab. En la función sandbox_theme_display, suelta el siguiente bloque de HTML justo bajo la llamada a settings_errors():

1
	<h2 class="nav-tab-wrapper">
2
		<a href="#" class="nav-tab">Display Options</a>
3
		<a href="#" class="nav-tab">Social Options</a>
4
	</h2>

Obviamente, esto es muy básico, pero acabamos de introducir dos pestañas con estilo que vamos a utilizar en el resto del tutorial. En este punto, el código debería tener este aspecto:

1
function sandbox_theme_display() {
2
?>
3
	<!-- Create a header in the default WordPress 'wrap' container -->
4
	<div class="wrap">
5
	
6
		<div id="icon-themes" class="icon32"></div>
7
		<h2>Sandbox Theme Options</h2>
8
		<?php settings_errors(); ?>
9
		
10
		<h2 class="nav-tab-wrapper">
11
			<a href="#" class="nav-tab">Display Options</a>
12
			<a href="#" class="nav-tab">Social Options</a>
13
		</h2>
14
		
15
		<form method="post" action="options.php">
16
17
			<?php settings_fields( 'sandbox_theme_display_options' ); ?>
18
			<?php do_settings_sections( 'sandbox_theme_display_options' ); ?>	
19
			
20
			<?php settings_fields( 'sandbox_theme_social_options' ); ?>
21
			<?php do_settings_sections( 'sandbox_theme_social_options' ); ?>	
22
		
23
			<?php submit_button(); ?>
24
			
25
		</form>
26
		
27
	</div><!-- /.wrap -->
28
<?php
29
} // end sandbox_theme_display

Y tu página de ajustes debe tener este aspecto:

Initial Settings TabsInitial Settings TabsInitial Settings Tabs

Dar vida a las pestañas

Para comenzar a alternar nuestras páginas de opciones, vamos a tener que proporcionar algún tipo de señal para indicar qué opciones queremos representar. Esto se puede hacer usando una variable de cadena de consulta que identifica sobre qué pestaña se hizo clic y que, a su vez, puede ser leída usando PHP.

Así que vamos a hacer lo anterior y a dar a cada ancla que hemos creamos anteriormente una señal única que indique qué pestaña estamos tratando de cargar. Actualiza tu marcado para que tenga el siguiente aspecto:

1
	<h2 class="nav-tab-wrapper">
2
		<a href="?page=sandbox_theme_options&tab=display_options" class="nav-tab">Display Options</a>
3
		<a href="?page=sandbox_theme_options&tab=social_options" class="nav-tab">Social Options</a>
4
	</h2>

Presta aquí mucha atención para no perderte esto: hemos proporcionado dos variables de cadena de consulta en cada enlace, el valor de la página y el valor de la pestaña. El valor de la página es necesario porque es generado por WordPress a través de la API de ajustes y se utiliza para indicar a la aplicación qué página de opciones cargar. El segundo valor es un valor arbitrario que hemos utilizado para indicar en qué pestaña estamos. Si has hecho esto correctamente, observa si la barra de direcciones de tu navegador refleja los valores al hacer clic en cada pestaña como debería.

A continuación, tenemos que escribir un poco de PHP que lea el nuevo valor de cadena de consulta. En última instancia, este código es lo que nos permitirá alternar nuestra página de opciones, pero vamos a ver esto paso a paso. Por lo tanto, empecemos escribiendo una condicional para comprobar si se establece el valor de la cadena de consulta y, si es así, almacenarlo en una variable. Esto puede colocarse directamente por encima de nuestro nav-tab-wrapper que definimos anteriormente.

1
<?php
2
if( isset( $_GET[ 'tab' ] ) ) {
3
	$active_tab = $_GET[ 'tab' ];
4
} // end if

5
?>

WordPress proporciona una clase llamada nav-tab-active que podemos aplicar a nuestras pestañas de anclaje para aplicarles estilo cuando estén activas. Por tanto, nuestro siguiente paso consistirá en comparar el valor de la variable $active_tab con la variable de la cadena de consulta de la pestaña y, a continuación, aplicar ese nombre de clase a la pestaña correspondiente.

Para ello, actualiza el código de manera que tenga este aspecto:

1
	<h2 class="nav-tab-wrapper">
2
		<a href="?page=sandbox_theme_options&tab=display_options" class="nav-tab <?php echo $active_tab == 'display_options' ? 'nav-tab-active' : ''; ?>">Display Options</a>
3
		<a href="?page=sandbox_theme_options&tab=social_options" class="nav-tab <?php echo $active_tab == 'social_options' ? 'nav-tab-active' : ''; ?>">Social Options</a>
4
	</h2>

Observe como aquí hemos escrito alguno de PHP en línea en el atributo de clase de cada ancla. En esencia, el código dice "Si el valor de la variable de la pestaña activa es 'display_options', a continuación, se hace eco de la palabra clave nav-tab-active; de lo contrario, no se hace eco de nada". Bastante fácil, ¿verdad? Pruébalo un par de veces: deberías ver cada una de tus pestañas alternando de un estado a otro.

En este punto, la función debería tener este aspecto:

1
function sandbox_theme_display() {
2
?>
3
	<!-- Create a header in the default WordPress 'wrap' container -->
4
	<div class="wrap">
5
	
6
		<div id="icon-themes" class="icon32"></div>
7
		<h2>Sandbox Theme Options</h2>
8
		<?php settings_errors(); ?>
9
		
10
		<?php
11
			if( isset( $_GET[ 'tab' ] ) ) {
12
				$active_tab = $_GET[ 'tab' ];
13
			} // end if

14
		?>
15
		
16
		<h2 class="nav-tab-wrapper">
17
			<a href="?page=sandbox_theme_options&tab=display_options" class="nav-tab <?php echo $active_tab == 'display_options' ? 'nav-tab-active' : ''; ?>">Display Options</a>
18
			<a href="?page=sandbox_theme_options&tab=social_options" class="nav-tab <?php echo $active_tab == 'social_options' ? 'nav-tab-active' : ''; ?>">Social Options</a>
19
		</h2>
20
		
21
		<form method="post" action="options.php">
22
23
			<?php settings_fields( 'sandbox_theme_display_options' ); ?>
24
			<?php do_settings_sections( 'sandbox_theme_display_options' ); ?>	
25
			
26
			<?php settings_fields( 'sandbox_theme_social_options' ); ?>
27
			<?php do_settings_sections( 'sandbox_theme_social_options' ); ?>	
28
		
29
			<?php submit_button(); ?>
30
			
31
		</form>
32
		
33
	</div><!-- /.wrap -->
34
<?php
35
} // end sandbox_theme_display

Pero espera, ¡en este código hay un sutil error! Recuerda que cuando un usuario aterriza en la página de ajustes por primera vez, no existirá ningún valor para tab en la cadena de consulta. Como tal, necesitamos establecer uno como el valor predeterminado. Para ello, vamos a actualizar el condicional que comprueba la presencia de la variable de cadena de consulta. Mientras estamos en ello, vamos a consolidarlo usando el operador ternario:

1
	$active_tab = isset( $_GET[ 'tab' ] ) ? $_GET[ 'tab' ] : 'display_options';

Esto dice "si la cadena de consulta contiene un valor para 'tab', se asigna a la variable de la pestaña activa; de lo contrario, se asigna el valor de 'display_options'". Exactamente así es como establecemos la pestaña de visualización como activa. Una vez más, comprueba tus pestañas.

Alternar nuestra página de ajustes

¡Ya casi terminamos! Lo último que tenemos que hacer es alternar nuestra página de ajustes en función de qué pestaña está activa. En concreto, solo queremos mostrar las opciones de visualización cuando la pestaña de visualización esté seleccionada (y lo mismo para nuestras opciones sociales).

Dado que tenemos todo almacenado en la variable active_tab, deberíamos ser capaces de envolver nuestras llamadas a la API de ajustes en un condicional y ya lo tendríamos listo. Por lo tanto, primero, busca en tu tema el siguiente bloque de código:

1
	<form method="post" action="options.php">
2
		
3
		<?php settings_fields( 'sandbox_theme_display_options' ); ?>
4
		<?php do_settings_sections( 'sandbox_theme_display_options' ); ?>
5
		
6
		<?php settings_fields( 'sandbox_theme_social_options' ); ?>
7
		<?php do_settings_sections( 'sandbox_theme_social_options' ); ?>
8
		
9
		<?php submit_button(); ?>
10
		
11
	</form>

Ten en cuenta que tenemos dos llamadas a settings_fields y do_settings_section. Básicamente, solo queremos representar un único grupo cuando se selecciona una pestaña determinada. Para ello, simplemente escribimos un condicional que comprueba el valor de $active_tab y, a continuación, ejecuta la sección adecuada:

1
	<form method="post" action="options.php">
2
		<?php

3
			

4
			if( $active_tab == 'display_options' ) {

5
				settings_fields( 'sandbox_theme_display_options' );

6
				do_settings_sections( 'sandbox_theme_display_options' );

7
			} else {

8
				settings_fields( 'sandbox_theme_social_options' );

9
				do_settings_sections( 'sandbox_theme_social_options' );

10
			} // end if/else

11
			

12
			submit_button();

13
			

14
		?>
15
	</form>

Actualiza la página de opciones, si has hecho todo correctamente, cada grupo de ajustes debe alternar en función del campo y todas las opciones deben guardarse correctamente.


Conclusión

La navegación mediante pestañas es un sencillo método para agrupar opciones relacionadas entre sí y ofrecer a los usuarios una experiencia de usuario sólida al no abrumarlos con opciones. Es relativamente fácil de implementar y logra integrar con perfecta solidez tus opciones usando el aspecto nativo de WordPress.

En el siguiente artículo, continuaremos construyendo sobre esto mediante la exposición de un menú de nivel superior que hará que tus opciones de tema estén accesibles a través del menú del escritorio de WordPress.