Add custom fields to image field I have a case where I need to add three custom fields to each image in an image field to hold data.  The content of these fields will not be displayed, but will only be indexed into Solr so they can be used in a custom image search. The logical place for these fields is in the same place that the Alt and Title fields are displayed (when enabled in the field settings), so that they can be entered in when the image is attached. Considering all the field API goodness in D7, it seemed like this would be pretty straightforward. However, it's not turning out that way.

One suggestion was to use the File Entity module, so I can add custom fields.  This seems to work great, in that it allows me to add fields through the UI to the file entity.  However, the problem is that these fields are not available when actually attaching the image to a node - they are only available when you add an image at /file/add.

After looking at the code in image.module, I noticed that the Alt and Title fields are added in the #process callback, which in turn is added in the hook_field_widget_form() imeplentation (image_field_widget_form()).  Since there is an alter hook (hook_field_widget_form_alter()), I implemented it and added my own #process callback:

function nb_alters_field_widget_form_alter(&amp;$element, &amp;$form_state, $context) {
  if ($element['#field_name'] == 'field_images') {
    // Add a custom #process function to add the fields.
    $element['#process'][] = 'nb_alters_image_process';
  }
}


and then added my callback (using code suggestion found here:

function nb_alters_image_process($element, &amp;$form_state, $form) {
  if (isset($element['#type']) &amp;&amp; ($info = element_info($element['#type'])) &amp;&amp; isset($info['#process'])) {
    foreach ($info['#process'] as $process) {
      $process($element, $form_state);
    }
  }

  // Add the additional Person, and Organization fields.
  $element['person'] = array(
    '#title' =&gt; t('Person'),
    '#type' =&gt; 'textfield',
    //'#default_value' =&gt; isset($item['person']) ? $item['person'] : '',
    '#default_value' =&gt; t('Default Person text'),
    '#description' =&gt; t('The person'),
    // @see http://www.gawds.org/show.php?contentid=28
    '#maxlength' =&gt; 255,
    '#weight' =&gt; -2,
    //'#access' =&gt; (bool) $item['fid'] &amp;&amp; $settings['alt_field'],
    '#access' =&gt; TRUE,
  );
  $element['organization'] = array(
    '#type' =&gt; 'textfield',
    '#title' =&gt; t('Organization'),
    //'#default_value' =&gt; isset($item['title']) ? $item['title'] : '',
    '#default_value' =&gt; t('Default Organization text'),
    '#description' =&gt; t('The organization the person in the image belongs to.'),
    '#maxlength' =&gt; 255,
    '#weight' =&gt; -1,
    //'#access' =&gt; (bool) $item['fid'] &amp;&amp; $settings['title_field'],
    '#access' =&gt; TRUE,
  );

  return $element;
}


However, this doesn't work as expected. Instead of the fields being added to each image, they are added separately below the last uploaded image.

What do I need to do differently to get my fields to show up for each image? Am I on the right track?

Thanks.
This question got me scratching my head also for a couple of hours, until I found File Entity Inline module.

Basically this module provides the functionality the OP wanted. You just create the field in the file entity you need to and then when creating the file/image field you have an additional box in the editing window where you can select the fields you want to be displayed next to each file.