I'm trying to add more textfields to a bean form using an "Add More" button with an ajax callback to keep adding textfields to the fieldset.

Watching the ajax response in Chrome's Network tab, it doesn't contain the markup to replace the contents of fieldset-add-more-wrapper. I'm wondering if this is even possible with a bean form?

<?php

class ExampleBean extends BeanPlugin {
  /**
   * Declares default block settings.
   */
  public function values() {
    $values = array(
      'fieldset_add_more' => array(
        'text'    => array('value' => ''),
      ),
    );

    return array_merge(parent::values(), $values);
  }

  /**
   * Builds extra settings for the block edit form.
   */
  public function form($bean, $form, &$form_state) {
    $form = array();

    /*  Fieldset Add More Settings */
    $form['fieldset_add_more'] = array(
      '#type'               => 'fieldset',
      '#tree'               => 1,
      '#title'              => t('Fieldset Add More'),
      // Set up the wrapper so that AJAX will be able to replace the fieldset.
      '#prefix' => '<div id="fieldset-add-more-wrapper">',
      '#suffix' => '</div>',
    );

    // Build the fieldset with the proper number of textfields. 
    // We'll use $form_state['num_items'] to determine the number of textfields to build.
    if (empty($form_state['num_items'])) {
      $form_state['num_items'] = 1;
    }
    for ($i = 0; $i < $form_state['num_items']; $i++) {
      $form['fieldset_add_more']['text'][$i] = array(
        '#type'               => 'textfield',
        '#title'              => t('Textfield '.$i.' Title'),
        '#description'        => t('Adding textfield '.$i),
      );
    }

    $form['add_more_button'] = array(
      '#type' => 'submit',
      '#value' => t('Add one more'),
      '#submit' => array('example_ajax_add_more_add_one'),
      
      // See the examples in ajax_example.module for more details on the
      // properties of #ajax.
      '#ajax' => array(
        'callback' => 'example_ajax_add_more_callback',
        'wrapper' => 'fieldset-add-more-wrapper',
      ),
    );

    return $form;
  }

  public function example_ajax_add_more_add_one($form, &$form_state) {
    $form_state['num_items']++;
    $form_state['rebuild'] = TRUE;
  }

  public function example_ajax_add_more_callback($form, $form_state) {
    return $form['fieldset_add_more'];
  }

  /**
   * Displays the bean.
   */
  public function view($bean, $content, $view_mode = 'default', $langcode = NULL) {
    $content['block']['#markup'] = theme('example_bean', array('form' => drupal_get_form('example_form', array('config' => $config)), 'bean' => $bean));
    return $content;
  }
}
?>

Comments

wesleymusgrove created an issue. See original summary.

wesleymusgrove’s picture

Status: Active » Closed (fixed)

I forgot to enable the permissions to allow viewing and administrative editing for this new bean type.

I also moved the ajax callback functions into the module itself and out of the bean plugin include file.

kienan91’s picture

hi ! Did your code working ? I build ajax add more field in Bean but not work !

wesleymusgrove’s picture

Yes my code is working and being used in production after I made the changes mentioned in https://www.drupal.org/node/2575023#comment-10388307.

kienan91’s picture

hi @wesleymusgrove ! I tried repair my code , the ajax loaded but not appear more field new ! I tried copy handle code ajax simple in module examples for test . But ajax still not add more field !

wesleymusgrove’s picture

Can you confirm the ajax wrapper callback is correct and matches the <div id="fieldset-add-more-wrapper"> prefix of the element your ajax is trying to replace?

Also the num_items incrementer used by the for loop when the form rebuilds is crucial. Otherwise it won't know how many form items to add to the current form when the ajax returns and rebuilds everything inside the callback wrapper container.

Can you post your complete code so I can see what the issue might be?