1

I have a custom module which invokes the hook_theme_registry_alter() to modify the presentation of some input fields.

However, I've discovered that the overridden styling is affecting ALL input fields on my entire site.

This is not good!

How to I make it so that my implementation of the hook_theme_registry_alter() is only seen on my module's pages?

Here is my function, and it is applying the theming functions to ALL radio and form elements on our site.

function MY_MODULE_theme_registry_alter(&$theme_registry) {
  if (isset($theme_registry['radio'])) {
    $theme_registry['radios']['function'] = "MY_MODULE_radios";
    $theme_registry['radio']['function'] = "MY_MODULE_radio";
    $theme_registry['form_element']['function'] = "MY_MODULE_element";
  }
}

2 Answers 2

1

For simple alterations, instead of implementing hook_elements(), you could simply implement hook_form_alter() or it's cousin hook_form_FORM_ID_alter(). Both of these functions will effectively allow you to (as their name suggests) alter a form's input elements, and they are much easier to implement than hook_elements(). The former gets called for every function in the website, while the later only gets called for the FORM_ID that you specified in your hook implementation.

If the ID of the form you wish to modify is my_form, then hook_form_FORM_ID_alter() would be written as hook_form_my_form_alter(). If you want a more thorough explanation of these two hooks, I highly recommend reading Lullabot's writeup on modifying Drupal 6 Forms.

0

Instead of implementing hook_theme_registry_alter() that changes the theme implementations for every module, you could define new form fields using hook_elements(). In this way you can implement a new radio field that is used only from your module, and that render a radio field in a customized way.
The default field definitions implemented by Drupal are contained in system_elements(), which defines the form fields you are interested to using the following arrays:

  $type['radios'] = array(
    '#input' => TRUE,
    '#process' => array('expand_radios'),
  );
  $type['radio'] = array(
    '#input' => TRUE,
    '#default_value' => NULL,
    '#process' => array('form_expand_ahah'),
  );

Using your form fields, you would just replace code similar to the first snippet with code similar to the second snippet.

$form['posting_settings']['comment_preview'] = array(
  '#type' => 'radios', 
  '#title' => t('Preview comment'), 
  '#default_value' => variable_get('comment_preview', 1), 
  '#options' => array(t('Optional'), t('Required')),
);
$form['posting_settings']['comment_preview'] = array(
  '#type' => 'mymodule_radios', 
  '#title' => t('Preview comment'), 
  '#default_value' => variable_get('comment_preview', 1), 
  '#options' => array(t('Optional'), t('Required')),
);

As only your module would use the "mymodule_radios" form field type, only your module would render the "radios" form field in a different way.

In Drupal 7, the hook has been renamed to hook_element_info().

For more information, see Creating Custom Elements Using Drupal 6.x.

7
  • The only way I can get this to work is if in the custom mymodule_radios function I pass the $element array through the theme(form_element) function. Which means I have to customize that as well. That works, but I don't have any of my radio buttons. How do I tell it to build the radios and ALSO to theme the RADIO elements inside with a custom function?
    – oranges13
    Sep 21, 2011 at 13:10
  • "Creating Custom Elements Using Drupal 6.x" reports the following sentence: "If you use hook_elements() to define an element type, there is an implicit assumption that there will be a theme function with the same name as the element type used to render HTML of its instances."
    – apaderno
    Sep 21, 2011 at 13:28
  • I have created the theme functions too. My issue comes that it's rendering the radios element just fine, but not the CHILDREN inside it. So I get a radio element formatted the way I want with no actual button choices.
    – oranges13
    Sep 21, 2011 at 13:48
  • theme_radios() uses the following code: theme('form_element', $element, $element['#children']);. Even if you use a different theme function, you should still theme the child elements.
    – apaderno
    Sep 21, 2011 at 13:56
  • When I use that, I don't GET any children, though. I get the theme'd radios element with no children. I have a seperate theme_mymodule_radio function but that doesn't seem to get called at all.
    – oranges13
    Sep 21, 2011 at 14:28

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.