You are here

function abjs_test_form in A/B Test JS 7

Generates a form for adding and editing tests.

Arg $tid will be NULL when adding a test, and will be a number when editing tests. $tid is checked throughout the function for determining if this is an add form or edit form.

1 string reference to 'abjs_test_form'
abjs_menu in ./abjs.module
Implements hook_menu().

File

./abjs.admin.inc, line 122
Admin forms to view/add/edit/delete tests, conditions, experiences.

Code

function abjs_test_form($form, &$form_state, $tid = NULL) {
  $form = array();
  $test_name_default = "";
  $test_active_default = 0;
  if (!empty($tid)) {

    // Retrieve the test to prefill the edit form.
    $test_result = db_query('SELECT name, active FROM {abjs_test} WHERE tid = :tid', array(
      ':tid' => $tid,
    ));
    if (empty($test_result)) {
      drupal_set_message(t('The requested test does not exist.'), 'error');
      return $form;
    }
    $test = $test_result
      ->fetchObject();
    $test_name_default = $test->name;
    $test_active_default = $test->active;
    $form['tid'] = array(
      '#type' => 'value',
      '#value' => $tid,
    );
  }

  // Because we have many fields with the same values, we have to set
  // #tree to be able to access them.
  $form['#tree'] = TRUE;
  $form['name'] = array(
    '#type' => 'textfield',
    '#title' => t('Test Name'),
    '#default_value' => $test_name_default,
    '#size' => 30,
    '#maxlength' => 50,
    '#required' => TRUE,
  );

  // Make select list of conditions.
  $conditions = db_query("SELECT cid, name FROM {abjs_condition} ORDER BY cid ASC, created DESC");
  $options_array = array(
    0 => t('Select Condition'),
  );
  foreach ($conditions as $condition) {
    $options_array[$condition->cid] = $condition->name . ' (c_' . $condition->cid . ')';
  }

  // Group conditions together, and allow for adding and removing conditions
  // via AJAX incide this fieldset.
  $form['conditions_fieldset'] = array(
    '#type' => 'fieldset',
    '#title' => t('Conditions'),
    // Set up the wrapper so that AJAX will be able to replace the fieldset.
    '#prefix' => '<div id="conditions-fieldset-wrapper">',
    '#suffix' => '</div>',
    '#description' => t('Select Conditions for which the test will apply. All conditions must must be satisfied for the test to apply'),
  );
  $existing_conditions_count = 0;
  if (empty($form_state['num_conditions'])) {

    // On initial load, get the number of condition select fields (1 for add
    // form, query the number for edit form).
    $form_state['num_conditions'] = 1;
    if (!empty($tid)) {
      $existing_conditions = db_query("SELECT cid FROM {abjs_test_condition} WHERE tid = :tid", array(
        ':tid' => $tid,
      ));
      if (!empty($existing_conditions)) {
        $existing_conditions_count = $existing_conditions
          ->rowCount();
        $form_state['num_conditions'] = $existing_conditions_count;
      }
    }
  }

  // Prefill all the condition select fields that exist.
  for ($i = 0; $i < $existing_conditions_count; $i++) {
    $existing_condition = $existing_conditions
      ->fetchObject();
    $form['conditions_fieldset']['conditions'][$i] = array(
      '#type' => 'select',
      '#title' => t('Select Condition'),
      '#options' => $options_array,
      '#default_value' => $existing_condition->cid,
      '#required' => TRUE,
    );
  }

  // Add number of sesgment fields determined by use of Ajax Add and
  // remove buttons.
  for ($i = $existing_conditions_count; $i < $form_state['num_conditions']; $i++) {
    $form['conditions_fieldset']['conditions'][$i] = array(
      '#type' => 'select',
      '#title' => t('Select Condition'),
      '#options' => $options_array,
      '#default_value' => 0,
      '#required' => TRUE,
    );
  }

  // Ajax add button.
  $form['conditions_fieldset']['add_condition'] = array(
    '#type' => 'submit',
    '#value' => t('Add'),
    '#name' => 'add-condition',
    '#submit' => array(
      'abjs_ajax_add_condition',
    ),
    '#ajax' => array(
      'callback' => 'abjs_ajax_conditions_callback',
      'wrapper' => 'conditions-fieldset-wrapper',
    ),
    '#limit_validation_errors' => array(),
  );

  // Ajax Remove button.
  if ($form_state['num_conditions'] > 1) {
    $form['conditions_fieldset']['remove_condition'] = array(
      '#type' => 'submit',
      '#value' => t('Remove'),
      '#name' => 'remove-condition',
      '#submit' => array(
        'abjs_ajax_remove_condition',
      ),
      '#ajax' => array(
        'callback' => 'abjs_ajax_conditions_callback',
        'wrapper' => 'conditions-fieldset-wrapper',
      ),
      '#limit_validation_errors' => array(),
    );
  }

  // Now do the same for experiences.
  // Make select list of experiences.
  $experiences = db_query("SELECT eid, name FROM {abjs_experience} ORDER BY changed DESC, created DESC");
  $options_array = array(
    0 => t('Select Experience'),
  );
  foreach ($experiences as $experience) {
    $options_array[$experience->eid] = $experience->name . ' (e_' . $experience->eid . ')';
  }

  // Group experiences together, and allow for adding and removing experiences
  // via AJAX incide this fieldset.
  $form['experiences_fieldset'] = array(
    '#type' => 'fieldset',
    '#title' => t('Experiences'),
    // Set up the wrapper so that AJAX will be able to replace the fieldset.
    '#prefix' => '<div id="experiences-fieldset-wrapper">',
    '#suffix' => '</div>',
    '#description' => t('Select one or more Experiences for the test, and assign fractions to each Experience (e.g. 1/2, 1/3, 0, 1, 0.5, .95, etc...). You cannot use the same Experience ID twice in the same test, so you must duplicate an Experience to use it twice.'),
  );
  $existing_experiences_count = 0;
  if (empty($form_state['num_experiences'])) {

    // On initial load, get the number of experience select fields (1 for add
    // form, query the number for edit form).
    $form_state['num_experiences'] = 1;
    if (!empty($tid)) {
      $existing_experiences = db_query("SELECT eid, fraction FROM {abjs_test_experience} WHERE tid = :tid", array(
        ':tid' => $tid,
      ));
      if (!empty($existing_experiences)) {
        $existing_experiences_count = $existing_experiences
          ->rowCount();
        $form_state['num_experiences'] = $existing_experiences_count;
      }
    }
  }

  // Prefill all the experience select fields that exist, including fractions
  // for each experience.
  for ($i = 0; $i < $existing_experiences_count; $i++) {
    $existing_experience = $existing_experiences
      ->fetchObject();
    $form['experiences_fieldset'][$i]['experience'] = array(
      '#type' => 'select',
      '#title' => t('Experience %i', array(
        '%i' => $i + 1,
      )),
      '#options' => $options_array,
      '#default_value' => $existing_experience->eid,
      '#required' => TRUE,
    );
    $form['experiences_fieldset'][$i]['experience_fraction'] = array(
      '#type' => 'textfield',
      '#title' => t('Experience %i Fraction', array(
        '%i' => $i + 1,
      )),
      '#default_value' => $existing_experience->fraction,
      '#size' => 5,
      '#maxlength' => 10,
      '#required' => TRUE,
    );
  }

  // Add number of experience fields determined by use of Ajax Add and remove
  // buttons.
  for ($i = $existing_experiences_count; $i < $form_state['num_experiences']; $i++) {
    $form['experiences_fieldset'][$i]['experience'] = array(
      '#type' => 'select',
      '#title' => t('Experience %i', array(
        '%i' => $i + 1,
      )),
      '#options' => $options_array,
      '#default_value' => 0,
      '#required' => TRUE,
    );
    $form['experiences_fieldset'][$i]['experience_fraction'] = array(
      '#type' => 'textfield',
      '#title' => t('Experience %i Fraction', array(
        '%i' => $i + 1,
      )),
      '#default_value' => '',
      '#size' => 5,
      '#maxlength' => 10,
      '#required' => TRUE,
    );
  }

  // Ajax add button.
  $form['experiences_fieldset']['add_experience'] = array(
    '#type' => 'submit',
    '#value' => t('Add'),
    '#name' => 'add-experience',
    '#submit' => array(
      'abjs_ajax_add_experience',
    ),
    '#ajax' => array(
      'callback' => 'abjs_ajax_experiences_callback',
      'wrapper' => 'experiences-fieldset-wrapper',
    ),
    '#limit_validation_errors' => array(),
  );

  // Ajax Remove button.
  if ($form_state['num_experiences'] > 1) {
    $form['experiences_fieldset']['remove_experience'] = array(
      '#type' => 'submit',
      '#value' => t('Remove'),
      '#name' => 'remove-experience',
      '#submit' => array(
        'abjs_ajax_remove_experience',
      ),
      '#ajax' => array(
        'callback' => 'abjs_ajax_experiences_callback',
        'wrapper' => 'experiences-fieldset-wrapper',
      ),
      '#limit_validation_errors' => array(),
    );
  }

  // Add selector for activating/deactivating test.
  $form['active'] = array(
    '#type' => 'select',
    '#title' => t('Status'),
    '#options' => array(
      0 => t('Inactive'),
      1 => t('Active'),
    ),
    '#default_value' => $test_active_default,
  );

  // Save test.
  $form['actions']['save'] = array(
    '#type' => 'submit',
    '#value' => t('Save'),
    '#weight' => 5,
    '#validate' => array(
      'abjs_test_form_save_validate',
    ),
    '#submit' => array(
      'abjs_test_form_save_submit',
    ),
  );

  // Cancel test and return to admin tests page.
  $form['actions']['cancel'] = array(
    '#type' => 'submit',
    '#value' => t('Cancel'),
    '#weight' => 10,
    '#submit' => array(
      'abjs_test_form_cancel_submit',
    ),
    '#limit_validation_errors' => array(),
  );

  // Delete test.
  if (!empty($tid)) {
    $form['actions']['delete'] = array(
      '#type' => 'submit',
      '#value' => t('Delete'),
      '#weight' => 15,
      '#submit' => array(
        'abjs_test_form_delete_submit',
      ),
    );
  }
  return $form;
}