1 views_handler_filter.inc views_handler_filter::build_group_form(&$form, &$form_state)

Build the form to let users create the group of exposed filters. This form is displayed when users click on button 'Build group'

File

core/modules/views/handlers/views_handler_filter.inc, line 812
@todo.

Class

views_handler_filter
Base class for filters.

Code

function build_group_form(&$form, &$form_state) {
  if (empty($this->options['exposed']) || empty($this->options['is_grouped'])) {
    return;
  }
  $form['#theme'] = 'views_ui_build_group_filter_form';

  // #flatten will move everything from $form['group_info'][$key] to $form[$key]
  // prior to rendering. That's why the pre_render for it needs to run first,
  // so that when the next pre_render (the one for fieldsets) runs, it gets
  // the flattened data.
  array_unshift($form['#pre_render'], 'views_ui_pre_render_flatten_data');
  $form['group_info']['#flatten'] = TRUE;

  if (!empty($this->options['group_info']['identifier'])) {
    $identifier = $this->options['group_info']['identifier'];
  }
  else {
    $identifier = 'group_' . $this->options['expose']['identifier'];
  }
  $form['group_info']['identifier'] = array(
    '#type' => 'textfield',
    '#default_value' => $identifier,
    '#title' => t('Filter identifier'),
    '#size' => 40,
    '#description' => t('This will appear in the URL after the ? to identify this filter. Cannot be blank.'),
    '#fieldset' => 'more',
  );
  $form['group_info']['label'] = array(
    '#type' => 'textfield',
    '#default_value' => $this->options['group_info']['label'],
    '#title' => t('Label'),
    '#size' => 40,
  );

  $form['group_info']['optional'] = array(
    '#type' => 'checkbox',
    '#title' => t('Optional'),
    '#description' => t('This exposed filter is optional and will have added options to allow it not to be set.'),
    '#default_value' => $this->options['group_info']['optional'],
  );
  $form['group_info']['multiple'] = array(
    '#type' => 'checkbox',
    '#title' => t('Allow multiple selections'),
    '#description' => t('Enable to allow users to select multiple items.'),
    '#default_value' => $this->options['group_info']['multiple'],
  );
  $form['group_info']['widget'] = array(
    '#type' => 'radios',
    '#default_value' => $this->options['group_info']['widget'],
    '#title' => t('Widget type'),
    '#options' => array(
      'radios' => t('Radios'),
      'select' => t('Select'),
    ),
    '#description' => t('Select which kind of widget will be used to render the group of filters'),
  );
  $form['group_info']['remember'] = array(
    '#type' => 'checkbox',
    '#title' => t('Remember'),
    '#description' => t('Remember the last setting the user gave this filter.'),
    '#default_value' => $this->options['group_info']['remember'],
  );

  if (!empty($this->options['group_info']['identifier'])) {
    $identifier = $this->options['group_info']['identifier'];
  }
  else {
    $identifier = 'group_' . $this->options['expose']['identifier'];
  }
  $form['group_info']['identifier'] = array(
    '#type' => 'textfield',
    '#default_value' => $identifier,
    '#title' => t('Filter identifier'),
    '#size' => 40,
    '#description' => t('This will appear in the URL after the ? to identify this filter. Cannot be blank.'),
    '#fieldset' => 'more',
  );
  $form['group_info']['label'] = array(
    '#type' => 'textfield',
    '#default_value' => $this->options['group_info']['label'],
    '#title' => t('Label'),
    '#size' => 40,
  );
  $form['group_info']['description'] = array(
    '#type' => 'textfield',
    '#default_value' => $this->options['group_info']['description'],
    '#title' => t('Description'),
    '#size' => 60,
  );
  $form['group_info']['optional'] = array(
    '#type' => 'checkbox',
    '#title' => t('Optional'),
    '#description' => t('This exposed filter is optional and will have added options to allow it not to be set.'),
    '#default_value' => $this->options['group_info']['optional'],
  );
  $form['group_info']['widget'] = array(
    '#type' => 'radios',
    '#default_value' => $this->options['group_info']['widget'],
    '#title' => t('Widget type'),
    '#options' => array(
      'radios' => t('Radios'),
      'select' => t('Select'),
    ),
    '#description' => t('Select which kind of widget will be used to render the group of filters'),
  );
  $form['group_info']['remember'] = array(
    '#type' => 'checkbox',
    '#title' => t('Remember'),
    '#description' => t('Remember the last setting the user gave this filter.'),
    '#default_value' => $this->options['group_info']['remember'],
  );

  $groups = array('All' => '- Any -'); // The string '- Any -' will not be rendered see @theme_views_ui_build_group_filter_form

  // Provide 3 options to start when we are in a new group.
  if (count($this->options['group_info']['group_items']) == 0) {
    $this->options['group_info']['group_items'] = array_fill(1, 3, array());
  }

  // After the general settings, comes a table with all the existent groups.
  $default_weight = 0;
  foreach ($this->options['group_info']['group_items'] as $item_id => $item) {
    if (!empty($form_state['values']['options']['group_info']['group_items'][$item_id]['remove'])) {
      continue;
    }
    // Each rows contains three widgets:
    // a) The title, where users define how they identify a pair of operator | value
    // b) The operator
    // c) The value (or values) to use in the filter with the selected operator

    // In each row, we have to display the operator form and the value from
    // $row acts as a fake form to render each widget in a row.
    $row = array();
    $groups[$item_id] = '';
    $this->operator_form($row, $form_state);
    // Force the operator form to be a select box. Some handlers uses
    // radios and they occupy a lot of space in a table row.
    $row['operator']['#type'] = 'select';
    $row['operator']['#title'] = '';
    $this->value_form($row, $form_state);

    // Fix the dependencies to update value forms when operators
    // changes. This is needed because forms are inside a new form and
    // their ids changes. Dependencies are used when operator changes
    // from to 'Between', 'Not Between', etc, and two or more widgets
    // are displayed.
    $without_children = TRUE;
    foreach (element_children($row['value']) as $children) {
      $has_state = FALSE;
      $states = array();
      foreach ($row['value'][$children]['#states']['visible'] as $key => $state) {
        if (isset($state[':input[name="options[operator]"]'])) {
          $has_state = TRUE;
          $states[$key] = $state[':input[name="options[operator]"]']['value'];
        }
      }
      if ($has_state) {
        foreach ($states as $key => $state) {
          $row['value'][$children]['#states']['visible'][$key] = array(
            ':input[name="options[group_info][group_items][' . $item_id . '][operator]"]' => array('value' => $state),
          );
        }

        $row['value'][$children]['#title_display'] = 'invisible';
        $row['value'][$children]['#placeholder'] = $row['value'][$children]['#title'];

        if (!empty($this->options['group_info']['group_items'][$item_id]['value'][$children])) {
          $row['value'][$children]['#default_value'] = $this->options['group_info']['group_items'][$item_id]['value'][$children];
        }
      }
      $without_children = FALSE;
    }

    if ($without_children) {
      if (!empty($this->options['group_info']['group_items'][$item_id]['value'])) {
        $row['value']['#default_value'] = $this->options['group_info']['group_items'][$item_id]['value'];
      }
    }

    if (!empty($this->options['group_info']['group_items'][$item_id]['operator'])) {
      $row['operator']['#default_value'] = $this->options['group_info']['group_items'][$item_id]['operator'];
    }

    $default_title = '';
    if (!empty($this->options['group_info']['group_items'][$item_id]['title'])) {
      $default_title = $this->options['group_info']['group_items'][$item_id]['title'];
    }

    // Per item group, we have a title that identifies it.
    $form['group_info']['group_items'][$item_id] = array(
      'title' => array(
        '#type' => 'textfield',
        '#size' => 20,
        '#default_value' => $default_title,
      ),
      'operator' => $row['operator'],
      'value' => $row['value'],
      'remove' => array(
        '#type' => 'checkbox',
        '#id' => 'views-removed-' . $item_id,
        '#attributes' => array('class' => array('views-remove-checkbox')),
        '#default_value' => 0,
      ),
      'weight' => array(
        '#type' => 'weight',
        '#delta' => 10,
        '#default_value' => $default_weight++,
        '#attributes' => array('class' => array('weight')),
      ),
    );
  }
  // From all groups, let chose which is the default.
  $form['group_info']['default_group'] = array(
    '#type' => 'radios',
    '#options' => $groups,
    '#default_value' => $this->options['group_info']['default_group'],
    '#required' => TRUE,
    '#attributes' => array(
      'class' => array('default-radios'),
    )
  );
  // From all groups, let chose which is the default.
  $form['group_info']['default_group_multiple'] = array(
    '#type' => 'checkboxes',
    '#options' => $groups,
    '#default_value' => $this->options['group_info']['default_group_multiple'],
    '#attributes' => array(
      'class' => array('default-checkboxes'),
    )
  );

  $form['group_info']['add_group'] = array(
    '#prefix' => '<div class="views-build-group clear-block">',
    '#suffix' => '</div>',
    '#type' => 'submit',
    '#value' => t('Add another item'),
    '#submit' => array('views_ui_config_item_form_add_group'),
    '#attributes' => array(
      'class' => array('use-ajax-submit'),
    ),
  );

  $js = array();
  $js['tableDrag']['views-filter-groups']['weight'][0] = array(
    'target' => 'weight',
    'source' => NULL,
    'relationship' => 'sibling',
    'action' => 'order',
    'hidden' => TRUE,
    'limit' => 0,
  );
  if (!empty($form_state['js settings']) && is_array($js)) {
    $form_state['js settings'] = array_merge($form_state['js settings'], $js);
  }
  else {
    $form_state['js settings'] = $js;
  }
}