Community

Replacement for _phptemplate_callback()?

This summer my boss decided we're upgrading from Drupal 4.7.2 to Drupal 6.2. We've got some heavy customizations requiring custom .tpl.php files. For example, we've got one called access_links.tpl.php. It's loaded like this (substantially simplified):

<?php
function _phptemplate_variables($hook, $vars = array()){
    switch(
$hook){

       
// Stuff to do when we're loading a whole page.
       
case "page":
           
// Load the access links into $access_links, with access to the variables.
           
$vars["access_links"] = phptemplate_access_links($vars);
        break;
    }
    return
$vars;
}

function
phptemplate_access_links($vars = array()){
  return
_phptemplate_callback('access_links', $vars);
}
?>

I've figured out how to use phptemplate_preprocess_page() (and related functions) to manipulate variables. That part's fine. But I have no idea how to coax Drupal into loading my template file without _phptemplate_callback(). The theming guide says its functionality has been rolled into theme(). But I've read the source code for theme() in the 6.x branch, and I still have no idea how to make it do what I want. I found a Drupal Dojo screencast on theme template files for Drupal 6, which was almost but not quite helpful. It covered overriding existing template files from modules in great detail, but that's not what I'm trying to do. I'm trying to create my own template file with its own name, and the screencast doesn't go into that.

I've got a sandbox installation of Drupal 6, and have been playing with it. Nothing I've tried has yielded any results. I can set new variables, but I can't load my custom template files. I'm aware of registry clearing, and have placed a call to drupal_rebuild_theme_registry() at the top of my template.php to simplify development and debugging, so I don't think it's a registry issue.

I guess it boils down to:

How do I do

<?php
return _phptemplate_callback('whatever', $vars);
?>
in Drupal 6?

Any help would be greatly appreciated.

Comments

I have a similar problem to.

I have a similar problem to. I have a module where I want a hook for a header / footer....and these templates to be stored in the module directory.

My solution was this

return theme_render_template(drupal_get_path('module', 'directory') .'/directory_header.tpl.php', array());

The array is essentially $vars. I don't know if their is a better way of doing this????

For your problem you could try

return theme_render_template(drupal_get_path('theme', 'theme_name') .'/access_links.tpl.php', array());

Adam
CTISN

Nice

I gave that a shot, and it did the trick. I passed $vars as the second argument for theme_render_template(), and it worked just fine for making the standard theme-type variables available to the template file.

You're right, it feels like there ought to be a better way to do this. But it works, so I'm not going to complain too hard. Thanks!

migration 5 to 6

Hi,

Is this correct ? in fact i don't understand if i have to change my_theme ==> the name of the directory of the theme ? I tried both without succeding...i've also tried with array() ....

// $items[] = _phptemplate_callback('views-list-mentions_view', $vars);
theme_render_template(drupal_get_path('theme', 'my_theme'). './views-list-mentions_view.tpl.php', $vars);

theme_render_template(drupal_get_path('theme', 'garland2'). './views-list-mentions_view.tpl.php', $vars);

What did you do with the fonction : _phptemplate_variables??

thanks for your help!

sam

Use preprocess functions and hook_theme

The _phptemplate_variables() function was replaced with a variety of "preprocess" functions, which are used for manipulating the PHP variables for various parts of the theme. For example, if you wish to create a new variable and make it available to page.tpl.php, then you would put the following in your template.php file:

<?php
function phptemplate_preprocess_page ($vars) {
 
$vars['new_variable'] = 'Hi!';
}
?>

Then, in page.tpl.php, you can do a simple <?php print $new_variable; ?> and it will print it out. There are similar preprocess functions available for other template files, e.g. phptemplate_preprocess_block(), phptemplate_preprocess_node(), and so on. Read more about that on the preprocess functions page in the Theming Guide.

You can then add custom template files using hook_theme(). The theme hook is used mostly by module developers, but can also be used from your theme's template.php file. The theme hook lets you register new template files and theming functions. Thus:

<?php
function THEMENAME_theme () {
  return array(
   
'THEMENAME_views_list_mentions_view' => array(
     
'template' => 'views-list-mentions_view', // The template file name, without .tpl.php
      
'arguments' => array(
       
'variable1' => null,
       
'variable2' => null, // Declare as many variables as you like here, setting them all to null
     
),
    )
  );
}
?>

Replace "THEMENAME" with the name of your theme. For example, if you're using Garland the function would be named garland_theme(). I'm not sure if you can use "phptemplate" in preference to your theme name with hook_theme, but it'll definitely work using your theme name. You can read the API entry about hook_theme if you'd like. Make sure the views-list-mentions_view.tpl.php file is located in your theme directory.

Once you've written a hook_theme() function for your theme, you'll need to clear the theme registry; your new template won't be found until you do. On the "Administer > Site configuration > Performance" page, click on the "Clear cached data" button. That will do the trick. Alternatively, if you're going to be doing a lot of this, look into the Devel module. It has a block containing a very handy "Empty cache" link, as well as a whole bunch of other useful functions (particularly the "theme developer" module is extremely useful for identifying potential template names).

The last step, once you've registered a theme hook, is to actually call it from a preprocess function using the theme() function. So the final

<?php
function phptemplate_preprocess_page ($vars) {
 
$whatever = 'foo';
 
$whenever = 'bar';
 
$vars['new_variable'] = theme('THEMENAME_views_list_mentions_view', $whatever, $whenever);
}

function
THEMENAME_theme () {
  return array(
   
'THEMENAME_views_list_mentions_view' => array(
     
'template' => 'views-list-mentions_view', // The template file name, without .tpl.php
      
'arguments' => array(
       
'variable1' => null,
       
'variable2' => null, // Declare as many variables as you like here, setting them all to null
     
),
    )
  );
}
?>

I presume you've found this already, but just in case you haven't, there's a guide to converting themes from 5.x to 6.x available.

Hope this helps.

Hi wdmartin, Thank you very

Hi wdmartin,

Thank you very much for your help. I really appreciate your help, because the switch D5 to D6 isn't as easy i hope :-) I had to review my tpl.php.

Unfortunately, i still have got the problem.

I've got a view (type node). It's a dynamique view with 3 sort of datas. That's why i've declared il my preprocess_node some variable. For each list there is an output specefic.

Here is my code :

function phptemplate_preprocess_node(&$vars) {
    ....
  if ($vars['type'] == 'filiere') {
  $vars['liste_des_metiers'] = phptemplate_node_filiere_liste_metiers($vars['field_filiere_metiers_links']);
  $vars['liste_des_videos'] = phptemplate_liste_videos($vars['field_filiere_videos']);
  }
...
}

function phptemplate_node_filiere_liste_metiers($links) {
if (is_array($links)) {
$items = array();
foreach ($links as $i => $link) {
$link_node = node_load($link[nid]);
if ($link_node && ($link_node->status == 1)) {
$link_node = node_build_content($link_node, FALSE, FALSE);
$vars = array();
$vars['node'] = $link_node;
foreach ($link_node as $field_name => $field_content) {
if (substr($field_name, 0, 6) == 'field_') {
$vars[$field_name.'_value'] = $field_content[0]['value'];
$vars[$field_name.'_view'] = $field_content[0]['view'];
}
}
$items[] = garland2_theme('list-liste_metiers', $vars);
}
}
if (count($items) > 0) {
$item_list = theme('link_item_list', $items);
$vars = array();
$vars['item_list'] = $item_list;
$output = garland2_theme('zone-liste_metiers', $vars);

return $output;
}
}
return;
}

the same for the function phptemplate_liste_videos

And then i've got :

function garland2_theme () {
  return array(
    'garland2_list-liste_metiers' => array(
      'template' => 'list-liste_metiers', // The template file name, without .tpl.php
       'arguments' => array(
        'variable1' => NULL,
      ),
    ),
     'garland2_zone-liste_videos' => array(
      'template' => 'zone-liste_videos', // The template file name, without .tpl.php
       'arguments' => array(
        'variable1' => NULL,
      ),
    ),
        'garland2_list-liste_videos' => array(
      'template' => 'list-liste_videos', // The template file name, without .tpl.php
       'arguments' => array(
        'variable1' => NULL,
      ),
    ),
        'garland2_zone-liste_metiers' => array(
      'template' => 'zone-liste_metiers', // The template file name, without .tpl.php
       'arguments' => array(
        'variable1' => NULL,
      ),
    ),
  );
}

In my directory theme i've got zone-liste_metiers.tpl.php and list-liste_metiers.tpl.php but they are never called...i've got also node-view-filieres_view.tpl.php to put all my variables. Maybe i can't use this way the templates? they aren't attached to a view.

Thank you for your help!

Sam