Here's an example I just ran into. I'm trying to put some HTML in the label of my field.

$form['field_feedback']['und']['#title'] <- has the title
$form['field_feedback']['und'][0]['#title'] <- has the title
$form['field_feedback']['und'][0]['value']['#title'] <- has the title. (Works)

Why are there three populated #title attributes with only one being used?

  • 1
    where this $form array is generated? as I know we have no $form with this structure in hook_form_alter Commented Apr 7, 2012 at 8:14
  • Thank you for this. I was pulling my hair out. The array structure is ridiculous.
    – JM01
    Commented Dec 12, 2014 at 17:14

1 Answer 1


What you're seeing is how Drupal represents fields in a form. It breaks down like this:

  • The children of the outer array, $form['field_back']['und'] ('und' for 'undefined'), are the different languages the field has been translated into. In Drupal, you are recommended to use LANGUAGE_NONE for 'und' in code.
  • The children inside each language array, e.g. $form['field_feedback']['und'][0], represent the different entries for the field. For example, if a field has unlimited cardinality, and there are several entries for that field, they will show as $form['field_feedback']['und'][0], $form['field_feedback']['und'][1], etc.
  • Finally you have the form input element(s), for the field values themselves, e.g. $form['field_feedback']['und'][0]['value']. In this case the column name is value, for a node reference field type it would be nid, and so on. If a field has multiple data columns associated with it you'll see more children as well. These are represented by a text field/select box/special widget, and will ultimately provide the value for the field.

The fact that titles have been added to the various elements throughout the hierarchy is incidental to be honest. Whether or not those titles are displayed on the form is down to the particular settings of the render array in which each #title is contained.

To change the title on the actual form widget, you only need to worry about the form element at the very bottom of the array: i.e. the actual input elements ($form['field_feedback']['und'][0]['value'], etc.).

It's probably worth noting that the element/widget used for a particular field may be quite complex. If you don't already have it, you should install the Devel module and use the dpm() function to inspect the $form array; that will show you exactly where in the array the elements you're trying to target are.

  • 3
    In short, adding #title to something that Drupal doesn't consider a form API array doesn't have any effect; even in that case, it is not said #title is taken in consideration, since it is not an attribute for all the form elements Drupal implements. The field API complicates the matters, as it adds a normal array to the form array, but that doesn't confuse Drupal that looks for #type, to recognise a form element.
    – apaderno
    Commented Jul 18, 2015 at 8:10

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.