diff --git css/views-admin.css css/views-admin.css
index 93e895a..c5bd2b0 100644
--- css/views-admin.css
+++ css/views-admin.css
@@ -305,17 +305,28 @@ html.js #views-ajax-pad {
 }
 
 .views-override,
+.views-build-group,
 .views-expose {
   padding: 0.5em 1em 0em 1em;
 }
 
+.views-build-group .form-submit {
+  margin: 0.5em !important;
+}
+
+table.views-filter-groups {
+  margin-bottom: 0px;
+}
+
 #views-ajax-pad .views-override .form-submit,
+#views-ajax-pad .views-build-group .form-submit,
 #views-ajax-pad .views-expose .form-submit {
   float: right;
   margin: 0 .5em 0 1em;
 }
 
 #views-ajax-pad .views-expose .description,
+#views-ajax-pad .views-build-group .description,
 #views-ajax-pad .views-override .description {
   margin-bottom: .25em;
 }
@@ -705,6 +716,7 @@ tr.group-message {
 }
 
 .group-message .form-submit,
+#edit-options-add-group,
 #views-add-group {
   float: right;
   clear: both;
diff --git handlers/views_handler_filter.inc handlers/views_handler_filter.inc
index 246d405..85ee56d 100644
--- handlers/views_handler_filter.inc
+++ handlers/views_handler_filter.inc
@@ -15,6 +15,7 @@
  * Base class for filters.
  */
 class views_handler_filter extends views_handler {
+
   /**
    * Provide some extra help to get the operator/value easier to use.
    *
@@ -26,6 +27,7 @@ class views_handler_filter extends views_handler {
 
     $this->operator = $this->options['operator'];
     $this->value = $this->options['value'];
+    $this->group_info = $this->options['group_info']['default_group'];
 
     // Compatibility: Set use_operator to true if the old way of using
     // the operator is set and use_operator is NULL (was never set).
@@ -60,7 +62,18 @@ class views_handler_filter extends views_handler {
         'single' => array('default' => 1),
       ),
     );
-
+    $options['build_group'] = array('default' => FALSE);
+    $options['group_info'] = array(
+      'contains' => array(
+        'label' => array('default' => '', 'translatable' => TRUE),
+        'identifier' => array('default' => ''),
+        'optional' => array('default' => TRUE),
+        'widget' => array('default' => 'select'),
+        'remember' => array('default' => 0),
+        'default_group' => array('default' => 'All'),
+        'group_items' => array('default' => array(0, array(), array())),
+      ),
+    );
     return $options;
   }
 
@@ -77,6 +90,13 @@ class views_handler_filter extends views_handler {
   function can_expose() { return TRUE; }
 
   /**
+   * Determine if a filter can be exposed into a group.
+   */
+  function can_expose_groups() {
+    return (bool) count($this->operator_options());
+  }
+
+  /**
    * Provide the basic form which calls through to subforms.
    * If overridden, it is best to call through to the parent,
    * or to at least make sure all of the functions in this form
@@ -85,6 +105,9 @@ class views_handler_filter extends views_handler {
   function options_form(&$form, &$form_state) {
     if ($this->can_expose()) {
       $this->show_expose_button($form, $form_state);
+      if ($this->options['exposed'] && $this->can_expose_groups()) {
+        $this->show_build_group_button($form, $form_state);
+      }
     }
     $form['op_val_start'] = array('#value' => '<div class="clear-block">');
     $this->show_operator_form($form, $form_state);
@@ -92,6 +115,9 @@ class views_handler_filter extends views_handler {
     $form['op_val_end'] = array('#value' => '</div>');
     if ($this->can_expose()) {
       $this->show_expose_form($form, $form_state);
+      if ($this->options['exposed'] && $this->can_expose_groups()) {
+        $this->show_build_group_form($form, $form_state);
+      }
     }
   }
 
@@ -116,6 +142,7 @@ class views_handler_filter extends views_handler {
     $this->value_submit($form, $form_state);
     if (!empty($this->options['exposed'])) {
       $this->expose_submit($form, $form_state);
+      $this->group_submit($form, $form_state);
     }
   }
 
@@ -164,6 +191,45 @@ class views_handler_filter extends views_handler {
   function operator_submit($form, &$form_state) { }
 
   /**
+   * Build a form containing a group of filters to apply as a single filter.
+   */
+  function group_form(&$form, &$form_state) {
+    if (!empty($this->options['group_info']['optional'])) {
+      $any_label = variable_get('views_exposed_filter_any_label', 'old_any') == 'old_any' ? '<Any>' : t('- Any -');
+      $groups = array('All' => $any_label);
+    }
+    foreach ($this->options['group_info']['group_items'] as $id => $group) {
+      if (!empty($group['title'])) {
+        $groups[$id] = t($group['title']);
+      }
+    }
+
+    if (count($groups)) {
+      $form['build_group'] = array(
+        '#title' => t($this->options['group_info']['label']),
+        '#type' => $this->options['group_info']['widget'],
+        '#default_value' => $this->group_info,
+        '#options' => $groups,
+      );
+      $this->options['expose']['label'] = '';
+    }
+  }
+
+  /**
+   * Filters out groups without a title.
+   */
+  function group_submit(&$form, &$form_state) {
+    if (!empty($form_state['values']['options']['group_info']['group_items'])) {
+      foreach ($form_state['values']['options']['group_info']['group_items'] as $item_id => $item) {
+        // Allow "0" as a possible title.
+        if (trim($item['title']) === '') {
+          unset($form_state['values']['options']['group_info']['group_items'][$item_id]);
+        }
+      }
+    }
+  }
+
+  /**
    * Shortcut to display the value form.
    */
   function show_value_form(&$form, &$form_state) {
@@ -174,6 +240,41 @@ class views_handler_filter extends views_handler {
     }
   }
 
+  function show_build_group_form(&$form, &$form_state) {
+    if (empty($this->options['build_group'])) {
+      return;
+    }
+
+    $form['op_val_start']['#value'] = '<div class="group-populated">' . $form['op_val_start']['#value'];
+    $form['op_val_end']['#value'] .= '</div>';
+    $form['expose']['#prefix'] = '<div class="group-populated">' . $form['expose']['#prefix'];
+    $form['expose']['#suffix'] .= '</div>';
+    $form['expose']['use_operator']['#default_value'] = TRUE;
+
+    $form['build_group'] = array(
+      '#prefix' => '<div class="views-expose-options clear-block">',
+      '#suffix' => '</div>',
+    );
+    $this->build_group_form($form, $form_state);
+
+    // When we click the expose button, we add new gadgets to the form but they
+    // have no data in $_POST so their defaults get wiped out. This prevents
+    // these defaults from getting wiped out. This setting will only be TRUE
+    // during a 2nd pass rerender.
+    if (!empty($form_state['force_expose_options'])) {
+      foreach (element_children($form['expose']) as $id) {
+        if (isset($form['expose'][$id]['#default_value']) && !isset($form['expose'][$id]['#value'])) {
+          $form['expose'][$id]['#value'] = $form['expose'][$id]['#default_value'];
+        }
+      }
+      foreach (element_children($form['group_info']) as $id) {
+        if (isset($form['group_info'][$id]['#default_value']) && !isset($form['group_info'][$id]['#value'])) {
+          $form['group_info'][$id]['#value'] = $form['group_info'][$id]['#default_value'];
+        }
+      }
+    }
+  }
+
   /**
    * Provide a form for setting options.
    *
@@ -308,6 +409,18 @@ class views_handler_filter extends views_handler {
       return;
     }
 
+    // If this filter use a group of operator | values
+    if (!empty($this->options['build_group'])) {
+      $value = $this->options['group_info']['identifier'];
+      $this->group_form($form, $form_state);
+      $form[$value] = $form['build_group'];
+
+      if ($value != 'build_group') {
+        unset($form['build_group']);
+      }
+      return;
+    }
+
     // Build the exposed form, when its based on an operator.
     if (!empty($this->options['expose']['use_operator']) && !empty($this->options['expose']['operator'])) {
       $operator = $this->options['expose']['operator'];
@@ -349,6 +462,132 @@ class views_handler_filter extends views_handler {
     }
   }
 
+  function build_group_form(&$form, &$form_state) {
+    if (empty($this->options['build_group'])) {
+      return;
+    }
+
+    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('Group identifier'),
+      '#size' => 40,
+      '#description' => t('This will appear in the URL after the ? to identify this filter. Cannot be blank.'),
+    );
+    $label = !empty($this->options['group_info']['label']) ? $this->options['group_info']['label'] : $this->options['expose']['label'];
+    $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']['widget'] = array(
+      '#type' => 'radios',
+      '#default_value' => $this->options['group_info']['widget'],
+      '#title' => t('Widget'),
+      '#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'],
+    );
+
+    $any_label = variable_get('views_exposed_filter_any_label', 'old_any') == 'old_any' ? '<Any>' : t('- Any -');
+    $groups = array('All' => $any_label);
+
+    foreach ($this->options['group_info']['group_items'] as $item_id => $item) {
+      if (!empty($form_state['values']['options']['group_info']['group_items'][$item_id]['removed'])) {
+        continue;
+      }
+      $row = array();
+      $groups[$item_id] = '';
+      $this->operator_form($row, $form_state);
+      $row['operator']['#type'] = 'select';
+      $row['operator']['#title'] = '';
+      $this->value_form($row, $form_state);
+      foreach (element_children($row['value']) as $children) {
+        if (isset($row['value'][$children]['#dependency']['edit-options-operator'])) {
+          $row['value'][$children]['#dependency']["edit-options-group-info-group-items-$item_id-operator"] = $row['value'][$children]['#dependency']['edit-options-operator'];
+          unset($row['value'][$children]['#dependency']['edit-options-operator']);
+          $row['value'][$children]['#title'] = '';
+          $row['value'][$children]['#default_value'] = $this->options['group_info']['group_items'][$item_id]['value'][$children];
+        }
+      }
+      $row['operator']['#default_value'] = $this->options['group_info']['group_items'][$item_id]['operator'];
+
+      $form['group_info']['group_items'][$item_id] = array(
+        'title' => array(
+          '#type' => 'textfield',
+          '#size' => 20,
+          '#default_value' => $this->options['group_info']['group_items'][$item_id]['title'],
+        ),
+        'operator' => $row['operator'],
+        'value' => $row['value'],
+        'removed' => array(
+          '#type' => 'checkbox',
+          '#id' => 'views-removed-' . $item_id,
+          '#attributes' => array('class' => 'views-remove-checkbox'),
+          '#default_value' => 0,
+        ),
+        'weight' => array(
+          '#type' => 'weight',
+          '#delta' => 10,
+          '#default_value' => $this->options['group_info']['group_items'][$item_id]['weight'],
+          '#attributes' => array('class' => 'weight'),
+        ),
+      );
+    }
+
+    $form['group_info']['default_group'] = array(
+      '#type' => 'radios',
+      '#options' => $groups,
+      '#default_value' => $this->options['group_info']['default_group'],
+    );
+    $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'),
+    );
+    $form['group_info']['#theme'] = 'views_ui_build_group_table';
+
+    $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;
+    }
+  }
+
   /**
    * Make some translations to a form item to make it more suitable to
    * exposing.
@@ -413,6 +652,18 @@ class views_handler_filter extends views_handler {
       return TRUE;
     }
 
+    if (!empty($this->options['build_group'])) {
+      $selected_group = $input[$this->options['group_info']['identifier']];
+      if (isset($selected_group) && isset($this->options['group_info']['group_items'][$selected_group])) {
+        $input[$this->options['expose']['operator']] = $this->options['group_info']['group_items'][$selected_group]['operator'];
+        $input[$this->options['expose']['identifier']] = $this->options['group_info']['group_items'][$selected_group]['value'];
+        $this->options['expose']['use_operator'] = TRUE;
+        $this->group_info = $input[$this->options['group_info']['identifier']];
+      }
+      else {
+        return FALSE;
+      }
+    }
 
     if (!empty($this->options['expose']['use_operator']) && !empty($this->options['expose']['operator']) && isset($input[$this->options['expose']['operator']])) {
       $this->operator = $input[$this->options['expose']['operator']];
@@ -459,7 +710,7 @@ class views_handler_filter extends views_handler {
       return TRUE;
     }
 
-    if (empty($this->options['expose']['remember'])) {
+    if (empty($this->options['expose']['remember']) && empty($this->options['group_info']['remember'])) {
       return;
     }
 
@@ -481,6 +732,10 @@ class views_handler_filter extends views_handler {
       if (isset($session[$this->options['expose']['identifier']])) {
         unset($session[$this->options['expose']['identifier']]);
       }
+
+      if (isset($session[$this->options['group_info']['identifier']])) {
+        unset($session[$this->options['group_info']['identifier']]);
+      }
     }
 
     if ($status) {
@@ -495,6 +750,10 @@ class views_handler_filter extends views_handler {
       }
 
       $session[$this->options['expose']['identifier']] = $input[$this->options['expose']['identifier']];
+
+      if (!empty($this->options['build_group']) && isset($input[$this->options['group_info']['identifier']])) {
+        $session[$this->options['group_info']['identifier']] = $input[$this->options['group_info']['identifier']];
+      }
     }
   }
 
@@ -521,6 +780,38 @@ class views_handler_filter extends views_handler {
    function can_group() {
      return TRUE;
    }
+
+  function show_build_group_button(&$form, &$form_state) {
+    $form['build_group_button'] = array(
+      '#prefix' => '<div class="views-build-group clear-block">',
+      '#suffix' => '</div>',
+    );
+    if (empty($this->options['build_group'])) {
+      $form['build_group_button']['button'] = array(
+        '#type' => 'submit',
+        '#value' => t('Build a group'),
+        '#submit' => array('views_ui_config_item_form_build_group'),
+      );
+      $form['build_group_button']['markup'] = array(
+        '#prefix' => '<div class="description">',
+        '#value' => t('This item is currently using a single filter. If you <strong>build a group</strong>, users will see a list of items that represents a pair of operator values.'),
+        '#suffix' => '</div>',
+      );
+    }
+    else {
+      $form['build_group_button']['button'] = array(
+        '#type' => 'submit',
+        '#value' => t('Use single filter'),
+        '#submit' => array('views_ui_config_item_form_build_group'),
+      );
+      $form['build_group_button']['markup'] = array(
+        '#prefix' => '<div class="description">',
+        '#value' => t('This item is currently using a group. If you choose <strong>use single filter</strong>, users will see the usual exposed filter.'),
+        '#suffix' => '</div>',
+      );
+    }
+  }
+
 }
 
 
diff --git includes/admin.inc includes/admin.inc
index e0edd4b..3da917b 100644
--- includes/admin.inc
+++ includes/admin.inc
@@ -370,6 +370,40 @@ function theme_views_ui_list_views_form($form) {
   return drupal_render($form);
 }
 
+function theme_views_ui_build_group_table($form) {
+  $header = array(
+    t('Default'),
+    t('Weight'),
+    t('Title'),
+    t('Operator'),
+    t('Value'),
+    '',
+  );
+  $rows[] = array(
+    drupal_render($form['default_group']['All']),
+    '',
+    array(
+      'data' => t('- Any -'),
+      'colspan' => 4,
+    ),
+  );
+  foreach (element_children($form['group_items']) as $group_id) {
+    $output = array(
+      'default' => drupal_render($form['default_group'][$group_id]),
+      'weight' => drupal_render($form['group_items'][$group_id]['weight']),
+      'title' => drupal_render($form['group_items'][$group_id]['title']),
+      'operator' => drupal_render($form['group_items'][$group_id]['operator']),
+      'value' => drupal_render($form['group_items'][$group_id]['value']),
+      'removed' => drupal_render($form['group_items'][$group_id]['removed']) . l('<span>' . t('Remove') . '</span>', 'javascript:void()', array('attributes' => array('id' => 'views-remove-link-' . $group_id, 'class' => 'views-hidden views-button-remove views-remove-link', 'alt' => t('Remove this item'), 'title' => t('Remove this item')), 'html' => true)),
+    );
+    $rows[] = array('data' => $output, 'id' => 'views-row-' . $group_id, 'class' => 'draggable');
+  }
+  $table = theme_table($header, $rows, array('class' => 'views-filter-groups', 'id' => 'views-filter-groups')) . drupal_render($form['add_group']);
+  drupal_add_tabledrag('views-filter-groups', 'order', 'sibling', 'weight');
+  $render_form = drupal_render($form);
+  return $render_form . $table;
+}
+
 /**
  * Page callback for the live preview.
  *
@@ -3340,6 +3374,46 @@ function views_ui_config_item_form_expose($form, &$form_state) {
   $form_state['force_expose_options'] = TRUE;
 }
 
+
+/**
+ * Override handler for views_ui_edit_display_form
+ */
+function views_ui_config_item_form_build_group($form, &$form_state) {
+  $item =& $form_state['handler']->options;
+  // flip
+  $item['build_group'] = empty($item['build_group']);
+
+  // If necessary, set new defaults:
+  if ($item['build_group']) {
+    $form_state['handler']->expose_options();
+  }
+
+  $form_state['view']->set_item($form_state['display_id'], $form_state['type'], $form_state['id'], $item);
+
+  views_ui_cache_set($form_state['view']);
+  $form_state['rerender'] = TRUE;
+  $form_state['rebuild'] = TRUE;
+  $form_state['force_expose_options'] = TRUE;
+}
+
+/**
+ * Add a new group to the exposed filter groups.
+ */
+function views_ui_config_item_form_add_group($form, &$form_state) {
+  $item =& $form_state['handler']->options;
+
+  // Add a new row.
+  $item['group_info']['group_items'][] = array();
+
+  $form_state['view']->set_item($form_state['display_id'], $form_state['type'], $form_state['id'], $item);
+
+  views_ui_cache_set($form_state['view']);
+  $form_state['rerender'] = TRUE;
+  $form_state['rebuild'] = TRUE;
+  $form_state['force_expose_options'] = TRUE;
+}
+
+
 /**
  * Form to config_item items in the views UI.
  */
diff --git views_ui.module views_ui.module
index b0854f2..b6feb2d 100644
--- views_ui.module
+++ views_ui.module
@@ -232,6 +232,12 @@ function views_ui_theme() {
       'arguments' => array('form' => NULL),
       'file' => 'includes/admin.inc',
     ),
+
+    // Group of filters
+    'views_ui_build_group_table' => array(
+      'arguments' => array('form' => NULL),
+      'file' => 'includes/admin.inc',
+    ),
   );
 }
 
