web-dev-qa-db-fra.com

Définir un modèle de page personnalisé sans son propre fichier .php

Existe-t-il un moyen de définir un modèle de page à partir d'une fonction/d'un filtre/d'un hook sans qu'un fichier .php ne contienne le commentaire en haut de la page pour déclarer le nom du modèle?


Par exemple, au lieu de faire ceci:

some-custom-page-template.php

/**
* Template Name: Some Custom Page Template
*/

autre-custom-page-template.php

/**
* Template Name: Another Custom Page Template
*/

Je me demande si je peux faire quelque chose comme:

functions.php

wp_some_function_to_define_templates( 'Some Custom Page Template' );
wp_some_function_to_define_templates( 'Another Custom Page Template' );

EDIT: j'écris un complex et un genre de expérimental WP theme - C'est comme objet- Orienté comme suit: WP, j'ai les classes de contrôleur pour décider de ce qu'il faut afficher dans chaque page, les classes DAO pour récupérer les données de la base de données, les modèles Twig pour générer les vues, etc.

J'ai tellement répandu le code que mes modèles de page sont devenus juste une ligne de code où j'appelle un contrôleur et le laisse faire le travail, pour finalement rendre un modèle Twig. J'ai donc décidé de déplacer cet appel vers le contrôleur, vers l'intérieur du filtre template_include, afin que je n'ai même pas besoin de mettre de code dans les modèles de page ...

Je peux me débarrasser des modèles de page, mais il me faut tout de même leur groupe group pages pour leur permettre de définir des groupes de champs personnalisés avancés, etc.

Je me suis donc retrouvé avec environ 15 PHP fichiers ne contenant qu'un commentaire en haut avec un nom de modèle, ce que j'aimerais éviter en définissant ces modèles à partir d'une fonction ...

Est-ce que j'essaie de réinventer la roue ? Peut-être dans un sens, mais je pense que cela devient vraiment un thème cool , très maintenable et modifiable ...

6
MikO

WordPress a lu les modèles à partir des en-têtes de fichier, puis les a placés dans le cache. using wp_cache_set() nad une clé dérivée du dossier md5 de la feuille de style.

Donc, en ignorant ce cache, nous pouvons afficher les modèles que nous voulons. Pour remplacer ce cache, nous devons appeler wp_cache_set() en utilisant la même clé.

Tout d’abord, écrivons une fonction qui récupère les modèles que nous voulons afficher. Il existe de nombreuses manières de définir des modèles: option, fichier de configuration, filtre ou combinaison de ceux-ci:

function get_custom_page_templates() {
  $templates = array();
  // maybe by options? --> $templates = get_option( 'custom_page_templates' );
  // maybe by conf file? --> $templates = include 'custom_page_templates.php';
  return apply_filters( 'custom_page_templates', $templates );
}

Après cela, nous devons récupérer les modèles dans l'édition de page, juste après que WordPress ait enregistré le cache. De plus, nous devons les récupérer à nouveau lorsque le formulaire de modification est publié pour permettre la sauvegarde.

Nous pouvons utiliser 'edit_form_after_editor' hook pour la première portée, 'load-post.php' et 'load-post.new' pour la seconde:

add_action( 'edit_form_after_editor', 'custom_page_templates_init' );
add_action( 'load-post.php', 'custom_page_templates_init_post' );
add_action( 'load-post-new.php', 'custom_page_templates_init_post' );

function custom_page_templates_init() {
  remove_action( current_filter(), __FUNCTION__ );
  if ( is_admin() && get_current_screen()->post_type === 'page' ) {
    $templates = get_custom_page_templates(); // the function above
    if ( ! empty( $templates ) )  {
      set_custom_page_templates( $templates );
    }
  }
}

function custom_page_templates_init_post() {
  remove_action( current_filter(), __FUNCTION__ );
  $method = filter_input( INPUT_SERVER, 'REQUEST_METHOD', FILTER_SANITIZE_STRING );
  if ( empty( $method ) || strtoupper( $method ) !== 'POST' ) return;
  if ( get_current_screen()->post_type === 'page' ) {
    custom_page_templates_init();
  }
}

Dernière chose à faire, écrivez la fonction set_custom_page_templates() qui édite le cache pour inclure nos modèles, en veillant à fusionner tous les modèles définis par les en-têtes de fichiers:

function set_custom_page_templates( $templates = array() ) {
  if ( ! is_array( $templates ) || empty( $templates ) ) return;
  $core = array_flip( (array) get_page_templates() ); // templates defined by file
  $data = array_filter( array_merge( $core, $templates ) );
  ksort( $data );
  $stylesheet = get_stylesheet();
  $hash = md5( get_theme_root( $stylesheet ) . '/' . $stylesheet );
  $persistently = apply_filters( 'wp_cache_themes_persistently', false, 'WP_Theme' );
  $exp = is_int( $persistently ) ? $persistently : 1800;
  wp_cache_set( 'page_templates-' . $hash, $data, 'themes', $exp );
}

Après avoir exécuté ce code, vous pouvez configurer des modèles personnalisés en utilisant simplement la méthode que vous avez utilisée dans la fonction get_custom_page_templates(); ici, j'utilise le filtre:

add_filter( 'custom_page_templates', function( $now_templates ) {

  $templates = array(
    'some-custom-page-template' => 'Some Custom Page Template',
    'another-custom-page-template' => 'Another Custom Page Template' ,
  );

  return array_merge( $now_templates, $templates );

} );

Et tu as fini.

6
gmazzap

Si je vous comprends bien, vous pouvez le faire avec le template_include hook. Par exemple:

add_filter( 'template_include', 'phpless_template');
function phpless_template( $template ) {  
  get_header();
  // some php
  get_footer();
  die;
}
2
s_ha_dum

Je vous suggère une solution de contournement plus simple:

  1. Dans votre fichier de configuration/functions/index, définissez une variable de configuration $config_template = false; (*)
  2. Créez un dossier "include" (vous en avez probablement déjà un)
  3. Mettez-y les fichiers some-custom-page-template.php et another-custom-page-template.php
  4. Dans ces fichiers, attribuez simplement une valeur à $ config_template puis demandez à la page que vous utilisez de rendre la boucle - par exemple: $config_template = 'some-custom-page'; require( "../index.php" );
  5. Dans ce fichier (index.php) vous pouvez faire ce que vous voulez en fonction de la valeur de $ config_template

En utilisant cette méthode, vous ne forcez pas le flux de travail normal de WP (ce n'est jamais une bonne idée), mais vous maintenez votre projet suffisamment propre.

(*) Vous utilisez probablement déjà une propriété d'objet pour gérer vos configurations. Vous allez mettre la variable $ config_template à cet endroit.

0
Marco Panichi