Is there a way to use hook_form_alter to modify webform components? I'm especially interested in changing the weight of components, since this can't be done in the module's UI.

I tried this...

$form['#node']->webform['components'][5]['weight'] = '999';

It had no effect.

If not with hook_form_alter, is there some other way to programmatically alter webform components?

Thanks

Comments

quicksketch’s picture

I don't normally answer coding requests, but I just answered a question almost identical to this one a few days ago: #1298220: hook_form_alter fails to prepopulate the default value for a webform component before rendering the client_form.

webcomm’s picture

For what it's worth, the solution quicksketch proposed in the other thread doesn't work for this problem. Changes to component weight in hook_form_alter don't affect output in the webform module, regardless of how you reload the page. Opening the page in another browser confirms this.

webcomm’s picture

Looks like I won't need to alter the weights. There is a drag-and-drop interface for doing so, and I wasn't seeing it because of a problem in my own theme. If I switch to Garland, I see the drag-and-drop handles.

When I started doing searches for this issue, I found an "Arrange Fields" module that someone recommended for re-arranging webform components, so I got a bit off track. I take it the "Arrange Fields" module is no longer needed here.

I suppose it's conceivable someone might still need to programmatically alter the weights, but I have no need for that anymore.

webcomm’s picture

As luck would have it, I once again find myself needing to use hook_form_alter on a webform and it's not working. Here's a simple test. Do this in mymodule_form_alter:

if ('webform_client_form_86' == $form_id) { //change to suit your own form id 
  print $form['#node']->webform['components'][1]['name']; //sanity check
  $form['#node']->webform['components'][1]['name'] = 'test'; 
}

That will print out the name of the first component, thus confirming that you have targeted the right form and are dealing with the right part of the $form array. Now, try setting that value to something else, like 'test'. It will have no effect on the output in the form.

ps -- I'd mark this a duplicate of the issue quicksketch linked to, but that issue deals with 7x and I don't know how much webform has changed from 6x -> 7x.

quicksketch’s picture

Status: Active » Fixed

That will print out the name of the first component, thus confirming that you have targeted the right form and are dealing with the right part of the $form array.

You can't modify the $form['#node'] property, you need to modify the form element itself, such as $form['submitted']['my_element']['#title']. The #node property is a copy of the Webform $node object, it's not the form itself. Don't go blindly guessing at form keys, use devel.module's dsm() function to print out the whole array so you know what you're changing:

dsm($form);

As always, I feel that I need to state that I don't help with custom coding in the Webform issue queue. I'd suggest any number of options for learning how to properly code in Drupal, http://drupalize.me, http://drupalbook.com, http://www.lullabot.com/articles/modifying-forms-drupal-5-and-6, or just friggin' Google it.

Status: Fixed » Closed (fixed)

Automatically closed -- issue fixed for 2 weeks with no activity.

ressa’s picture

I just could not hook into my webform, even though everything looked right. But when I had copied the form ID from the form, I forgot to substitute dashes (-) with underscores (_) in the form name. So "webform-client-form-73" didn't work, but "webform_client_form_73" did :-)

You might also have to flush the caches to pick it up.

Does NOT work:

function MODULE_NAME_form_alter(&$form, &$form_state, $form_id) {
  if ($form_id == 'webform-client-form-73') {
    dsm($form);
  }
}

This is correct:

function MODULE_NAME_form_alter(&$form, &$form_state, $form_id) {
  if ($form_id == 'webform_client_form_73') {
    dsm($form);
  }
}
loominade’s picture

this will detect all webforms:

function  MODULE_NAME_form_alter(&$form, &$form_state, $form_id) {
  if ((isset($form['#node']) && $form['#node']->type == 'webform')) {
    // geeky stuff
  }
}

or

function  MODULE_NAME_form_alter(&$form, &$form_state, $form_id) {
  if (strpos($form_id, 'webform_client_form_') === 0) {
    // geeky stuff
  }
}
rajeevroy’s picture

Use $form['submitted']['field_key']. thanks

atikrant’s picture

Is it possible to override form id of a webform?

Is it right way,
/**
* Implement hook_from_alter
*
* @param type $form
* @param type $form_state
* @param type $form_id`enter code here`
*/
function MYMODULE_form_alter(&$form, &$form_state, $form_id) {
$form['#form_id'] = 'webform_en';
$form['#form_id'] = 'webform-en';
$form['form_id']['#value'] = 'webform_en';
$form['form_id']['#id'] = 'webform_en';
}