Controles Personalizados com Theme Customizer

Controles Personalizados com Theme Customizer

O Theme Customizer do WordPress não se limita apenas aos controles do tipo text, textarea, code, html color, select e entre outros.

Como também, você pode criar seus próprios controles personalizados, de modo a adiciona-los dentro do Theme Customizer.

O procedimento é bem simples, você começa criando um controle e uma setting relacionada a ele, seguido de uma classe própria que iremos criar para gerenciar esse controle personalizado 🤓

Criando um controle de campo de texto

Neste primeiro exemplo, vamos aprender a criar um campo de texto do tipo 'text', ou seja, um simples <input type="text"> como este que estamos vendo na ilustração abaixo.

Criando a pasta de classes

Tudo começa com uma boa organização de arquivos, sendo assim, dentro da pasta raiz do seu tema, você vai precisar criar uma nova pasta chamada de classes:

Dentro dessa pasta, ficará armazenada todas as classes customizadas que iremos criar para o Theme Customizer 👏

Criando nossa classe customizada

Dentro da pasta classes, vamos precisar criar um novo arquivo que vai representar a nossa classe customizada.

Para isso, eu criei um novo arquivo chamado de micilini_custom_text.php:

Por hora, vamos deixar este arquivo vazio, somente com as tags php, como é mostrado no exemplo abaixo:

<?php

//Código da classe customizada

?>

Conectando nossa classe no functions.php

Já dentro do functions.php do seu tema, temos que inserir o arquivo que acabamos de criar no topo da página, da seguinte forma:

<?php

require get_template_directory() . '/classes/micilini_custom_text.php';
require get_template_directory().'/inc/micilini-customizer.php';

//....

Observe que adicionamos o comando que insere o arquivo micilini_custom_text.php, logo antes das funções do micilini-customizer.php que criamos em lições anteriores.

Fizemos isso, porque a classe que vai existir dentro do arquivo micilini_custom_text.php será chamada dentro da função micilini_customizer() que existe dentro do arquivo micilini-customizer.php.

Feito isso, chegou a hora de colocarmos a mão na massa e criamos a lógica da classe 😊

Conhecendo a classe WP_Customize_Control

Antes de criarmos a lógica do arquivo micilini_custom_text.php, devemos discursar um pouco sobre o funcionamento da classe WP_Customize_Control do WordPress.

Esta classe é fundamental no WordPress, onde é utilizada para criar controles personalizados no Customizer.

Ela é estendida por todas aquelas outras classes que conhecemos desde que começamos a falar sobre Theme Customizer, como:

  • WP_Customize_Color_Control,
  • WP_Customize_Image_Control,
  • etc...

Já utilizamos algumas dessas classes na lição anterior, você se lembra?

Pois bem, a classe WP_Customize_Control, deverá ser estendida da classe customizada que iremos criar, mas antes, é importante que você conheça alguns métodos principais dessa classe:

render_content(): é um método obrigatório que precisa ser implementado pela classe customizada. Ele é responsável por renderizar o conteúdo do controle no Customizer, e isso significa que é dentro dele que nós inserimos as tags HTML relacionadas ao nosso controle.

to_json(): não chega a ser um método obrigatório, a menos que você deseje criar um controle que interaja com o Javascript do Tema. Esse método é responsável por converter a instância da classe em JSON para que ela possa ser transmitida para o JavaScript no lado do cliente.

Além disso, a classe WP_Customize_Control conta com algumas propriedades principais:

'type': define o tipo de controle que será criado.

'label': é o título que será criado junto com o controle.

'description': é uma descrição adicional que será criada ao controle.

'section': é o identificador da seção ao qual o controle pertence.

'settings': é o identificador da setting relacionada a este controle.

Perfeito, agora que você já entende o funcionamento da classe WP_Customize_Control(), chegou a hora de criar a nossa classe customizada em definitivo!

Criando a lógica do arquivo micilini_custom_text.php 

Para que você entenda melhor o que estou fazendo aqui, vou criando separadamente bloco por bloco de código, ok?

Dentro do arquivo micilini_custom_text.php vamos começar validando se a classe WP_Customize_Control existe, e se ela está disponível para uso:

<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

}

?>

Essa estratégia é muito utilizada para evitar erros de compilação na plataforma do WordPress, isto é, caso algum dia eles resolvam alterar o nome dessa classe, o que faria com que seu controle gerasse um erro na plataforma.

Caso essa classe exista, precisamos criar nossa própria classe estendida da classe principal WP_Customize_Control, da seguinte forma:

<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{

 }

}

?>

Observe que criamos uma nova classe chamada de Micilini_Text_Control que estende da classe principal de WP_Customize_Control.

Agora chegou o momento de implementarmos os métodos e propriedades que a classe WP_Customize_Control nos pede:

<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{
 public $type = 'text';

 public function render_content() {
 
 }

 }

}

?>

Tudo começa com a propriedade $type que armazena inicialmente o valor 'text', que diz a classe WP_Customize_Control que o conteúdo será um campo de texto.

Em seguida declaramos o método render_content() que vai conter todo o código HTML necessário para mostrarmos esse campo de texto na tela.

E é isso que vamos fazer agora:

<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{
 public $type = 'text';

 public function render_content() {
 ?>
 <label>
 <span class="customize-control-title"><?php echo esc_html($this->label); ?></span>
 <input type="text" <?php $this->link(); ?> value="<?php echo esc_attr($this->value()); ?>" />
 </label>
 <?php
 }

 }

}

?>

Observe que fechamos e abrimos as tags do PHP, de modo a criar nossas estruturas HTML dentro da função render_content().

Ali dentro, criamos um <label> onde contém uma tag <span> que armazena o título, e um <input> do tipo text que armazena o campo em si.

Como você pode perceber, também estamos fazendo o uso de algumas tags PHP no meio dessas tags HTML, por exemplo:

$this->label: retorna o valor da chave 'label' que iremos declarar dentro do add_control().

$this->value(): retorna o valor da chave 'default' que iremos declarar dentro do add_control(). É importante ressaltar que se o usuário já tiver preenchido este campo, o valor a ser retornado será o que já está salvo no banco de dados.

$this->link(): é uma forma com que a classe WP_Customize_Control cria uma conexão entre o controle e a configuração associada no Customizer.

Lembra que em lições anteriores, eu expliquei que existe uma conexão entre o controle e a setting, de modo que todo valor digitado ou alterado no controle, surta efeito automaticamente em uma das telas do seu tema, em tempo real? O link faz justamente isso.

Como você pode perceber, ficaram faltando a implementação de três propriedades: 'description', 'section' e 'setting'.

Com relação as propriedades 'section' e 'setting', elas são usadas internamente pela classe WP_Customize_Control e não precisam ser trabalhadas dentro da nossa classe customizada.

Já a propriedade 'description' não foi adicionada propositalmente 🙂

Isso foi feito, para você entender que é possível adicionar quantos argumentos personalizados você desejar dentro do add_control().

Veremos como tudo isso funciona daqui a pouco rs

Criando o controle no Theme Customizer

Agora que já temos tudo configurado, basta abrir o arquivo micilini-customizer.php existente dentro da pasta inc.

E adicionarmos uma setting e um controle dentro da função micilini_customizer(), como vínhamos fazendo em lições passadas.

 $wp_customize->add_setting(
 'setting_micilini_text',
 array(
 'type' => 'theme_mod',
 'default' => '',
 'sanitize_callback' => 'sanitize_text_field'
 )
 );

 $wp_customize->add_control(
 new Micilini_Text_Control(
 $wp_customize,
 'setting_micilini_text',
 array(
 'label' => 'Controle Customizado',
 'section' => 'section_titulo',
 'settings' => 'setting_micilini_text'
 )
 )
 );

A única diferença que não vimos até agora, é que estamos fazendo o uso da classe Micilini_Text_Control() que acabamos de criar anteriormente.

Somente com essa configuração, você já será capaz de visualizar o seu novo controle personalizado dentro do painel do wordpress.

Conectando com o seu tema

Assim como vimos em lições anteriores, não há muito mistério quanto a conexão entre seu controle e os arquivos do seu tema.

$custom_control = wp_kses(get_theme_mod('setting_micilini_text', ''));

Passando novos argumentos no Add_Control()

Lembra que falei que o argumento 'description' era opcional, e que podemos passar quantos argumentos quisermos dentro do add_control()?

Observe abaixo que estou passando diversos argumentos novos dentro do add_control(), e recuperando cada um deles dentro das tags HTML da função render_content()

 $wp_customize->add_setting(
 'setting_micilini_text',
 array(
 'type' => 'theme_mod',
 'default' => '',
 'sanitize_callback' => 'sanitize_text_field'
 )
 );

 $wp_customize->add_control(
 new Micilini_Text_Control(
 $wp_customize,
 'setting_micilini_text',
 array(
 'label' => 'Controle Customizado',
 'section' => 'section_titulo',
 'settings' => 'setting_micilini_text',
 'description' => 'Essa é a descrição do campo',
 'micilini' => 'É DEZ!',
 'visivel' => true
 )
 )
 );
<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{
 public $type = 'text';
 public $micilini = null;
 public $visivel = null;

 public function render_content() {
 ?>
 <label>
 <span class="customize-control-title"><?php echo esc_html($this->label); ?></span>
 <span class="customize-control-title"><?php echo esc_html($this->description); ?></span>
 <span class="customize-control-title">O Micilini é: <?php echo esc_html($this->micilini); ?></span>
 <?php if($this->visivel){ ?>
 <input type="text" <?php $this->link(); ?> value="<?php echo esc_attr($this->value()); ?>" />
 <?php }else{ ?>
 <small style="color:red">Você não tem permissão para editar esse campo!</small>
 <?php } ?>
 </label>
 <?php
 }

 }

}

?>

Observação: Não se esqueça de declarar as propriedades da classe para cada novo argumento que você inserir.

Caso desejar, você pode criar um argumento chamado de custom_argument(ou qualquer outro nome), e dentro dele passar um array com outros argumentos:

 $wp_customize->add_setting(
 'setting_micilini_text',
 array(
 'type' => 'theme_mod',
 'default' => '',
 'sanitize_callback' => 'sanitize_text_field'
 )
 );

 $wp_customize->add_control(
 new Micilini_Text_Control(
 $wp_customize,
 'setting_micilini_text',
 array(
 'label' => 'Controle Customizado',
 'section' => 'section_titulo',
 'settings' => 'setting_micilini_text',
 'description' => 'Essa é a descrição do campo',
 'custom_argument' => array('micilini' => 'É DEZ!', 'visivel' => true),
 )
 )
 );
<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{
 public $type = 'text';
 public $custom_argument = null;

 public function render_content() {
 ?>
 <label>
 <span class="customize-control-title"><?php echo esc_html($this->label); ?></span>
 <span class="customize-control-title"><?php echo esc_html($this->description); ?></span>
 <span class="customize-control-title">O Micilini é: <?php echo esc_html($this->custom_argument['micilini']); ?></span>
 <?php if($this->custom_argument['visivel']){ ?>
 <input type="text" <?php $this->link(); ?> value="<?php echo esc_attr($this->value()); ?>" />
 <?php }else{ ?>
 <small style="color:red">Você não tem permissão para editar esse campo!</small>
 <?php } ?>
 </label>
 <?php
 }

 }

}

?>

Viu como é fácil? Veja como ficou o resultado final:

Falando um pouco mais sobre a propriedade $type, você pode fazer uma série de verificações dentro da classe de modo a carregar estruturas de HTML diferentes, por exemplo:

<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{
 public $type = 'text';
 public $micilini = null;
 public $visivel = null;

 public function render_content() {
 ?>
 
 <?php if ($this->type == 'text'){ ?>
 <!-- Carrega aqui o tipo texto -->
 <?php } ?>

 <?php if ($this->type == 'select'){ ?>
 <!-- Carrega aqui o tipo select -->
 <?php } ?>

 <?php if ($this->type == 'outro'){ ?>
 <!-- Carrega aqui o tipo outro -->
 <?php } ?>


 <?php
 }

 }

}

?>

Esta é uma boa estratégia quando temos uma única função customizada, que é capaz de entregar diversos tipos de controles diferentes.

Usando o WP_Query na classe customizada

Você sabia que também é possível usar a classe WP_Query de modo a deixar seu controle mais customizado?

Veja abaixo, um exemplo em que estou retornando dentro de um select os últimos posts:

$wp_customize->add_setting(
 'setting_micilini_select',
 array(
 'type' => 'theme_mod',
 'default' => '',
 'sanitize_callback' => 'sanitize_text_field'
 )
 );

 $wp_customize->add_control(
 new Micilini_Text_Control(
 $wp_customize,
 'setting_micilini_select',
 array(
 'label' => 'Controle Customizado',
 'section' => 'section_titulo',
 'settings' => 'setting_micilini_select',
 )
 )
 );
<?php

//Código da classe customizada

if (class_exists('WP_Customize_Control')) {

 class Micilini_Text_Control extends WP_Customize_Control{
 public $type = 'select';

 public function render_content() {

 $latest = new WP_Query( array(
 'post_type' => 'post',
 'post_status' => 'publish',
 'orderby' => 'date',
 'order' => 'DESC'
 ));

 ?>

 <label>
				<span class="customize-control-title"><?php echo esc_html( $this->label ); ?></span>
				<select <?php $this->link(); ?>>
					<?php
 echo "<option value='' selected disabled>Escolha uma opção</option>";
					while( $latest->have_posts() ) {
						$latest->the_post();
						echo "<option " . selected( $this->value(), get_the_ID() ) . " value='" . get_the_ID() . "'>" . the_title( '', '', false ) . "</option>";
					}
					?>
				</select>
			</label>
 
 <?php
 }

 }

}

?>

Veja como ficou o resultado final:

Como adicionar estilos diferentes em seus controles customizados?

Até o momento você aprendeu a criar controles que usam classes padronizadas do WordPress, mas talvez você esteja se perguntando: "Como eu adiciono meus próprios estilos em meus controles?".

Simples, basta que você crie novas classes CSS dentro do arquivo style.css, ou faça isso diretamente dentro da função render_content(), seja por meio da abertura das tags do CSS (<style></style>) ou diretamente na tag style="" do elemento HTML desejado.

<?php

//...

public function render_content() {
?>

<style>.meu-campo{ color:red; font-size:14px; }<style>
<input class="meu-campo" type="text" <?php $this->link(); ?> value="<?php echo esc_attr($this->value()); ?>" />

<label styçe="color:green; margin-top:30px;">Um texto...</label>

<?php
}
//...

?>

Conclusão

Nesta lição você aprendeu um assunto bastante interessante sobre como criar controles personalizados no Theme Customizer.

Acredito que agora você atingiu um marco super importante na criação de temas do WordPress, está apto a criar um tema de sucesso, e totalmente personalizado para seu usuário 😎

Parabéns, e até a próxima lição.