| Versions | |
|---|---|
| 4.7 – 5 | form_builder($form_id, $form) |
| 6 | form_builder($form_id, |
| 7 | form_builder($form_id, &$element, &$form_state) |
Adds some required properties to each form element, which are used internally in the form api. This function also automatically assigns the value property from the $edit array, provided the element doesn't already have an assigned value.
$form_id A unique string identifying the form. Allows each form to be themed.
$form An associative array containing the structure of the form.
includes/
<?php
function form_builder($form_id, $form) {
global $form_values, $form_submitted, $form_button_counter;
// Initialize as unprocessed.
$form['#processed'] = FALSE;
/* Use element defaults */
if ((!empty($form['#type'])) && ($info = _element_info($form['#type']))) {
// overlay $info onto $form, retaining preexisting keys in $form
$form += $info;
}
if (isset($form['#input']) && $form['#input']) {
if (!isset($form['#name'])) {
$form['#name'] = 'edit[' . implode('][', $form['#parents']) . ']';
}
if (!isset($form['#id'])) {
$form['#id'] = 'edit-' . implode('-', $form['#parents']);
}
$posted = (isset($_POST['edit']) && ($_POST['edit']['form_id'] == $form_id));
$edit = $posted ? $_POST['edit'] : array();
foreach ($form['#parents'] as $parent) {
$edit = isset($edit[$parent]) ? $edit[$parent] : NULL;
}
if (!isset($form['#value']) && !array_key_exists('#value', $form)) {
if ($posted) {
switch ($form['#type']) {
case 'checkbox':
$form['#value'] = !empty($edit) ? $form['#return_value'] : 0;
break;
case 'select':
if (isset($form['#multiple']) && $form['#multiple']) {
if (isset($edit) && is_array($edit)) {
$form['#value'] = drupal_map_assoc($edit);
}
else {
$form['#value'] = array();
}
}
elseif (isset($edit)) {
$form['#value'] = $edit;
}
break;
case 'textfield':
if (isset($edit)) {
// Equate $edit to the form value to ensure it's marked for validation
$edit = str_replace(array("\r", "\n"), '', $edit);
$form['#value'] = $edit;
}
break;
case 'token':
$form['#value'] = (string) $edit;
break;
default:
if (isset($edit)) {
$form['#value'] = $edit;
}
}
// Mark all posted values for validation
if ((isset($form['#value']) && $form['#value'] === $edit) || (isset($form['#required']) && $form['#required'])) {
$form['#needs_validation'] = TRUE;
}
}
if (!isset($form['#value'])) {
$function = $form['#type'] . '_value';
if (function_exists($function)) {
$function($form);
}
else {
$form['#value'] = $form['#default_value'];
}
}
}
if (isset($form['#executes_submit_callback'])) {
// Count submit and non-submit buttons
$form_button_counter[$form['#executes_submit_callback']]++;
// See if a submit button was pressed
if (isset($_POST[$form['#name']]) && $_POST[$form['#name']] == $form['#value']) {
$form_submitted = $form_submitted || $form['#executes_submit_callback'];
}
}
}
// Allow for elements to expand to multiple elements, e.g. radios, checkboxes and files.
if (isset($form['#process']) && !$form['#processed']) {
foreach ($form['#process'] as $process => $args) {
if (function_exists($process)) {
$args = array_merge(array($form), $args);
$form = call_user_func_array($process, $args);
}
}
$form['#processed'] = TRUE;
}
// Set the $form_values key that gets passed to validate and submit.
// We call this after #process gets called so that #process has a
// chance to update #value if desired.
if (isset($form['#input']) && $form['#input']) {
form_set_value($form, $form['#value']);
}
// Recurse through all child elements.
$count = 0;
foreach (element_children($form) as $key) {
// don't squash an existing tree value
if (!isset($form[$key]['#tree'])) {
$form[$key]['#tree'] = $form['#tree'];
}
// don't squash existing parents value
if (!isset($form[$key]['#parents'])) {
// Check to see if a tree of child elements is present. If so, continue down the tree if required.
$form[$key]['#parents'] = $form[$key]['#tree'] && $form['#tree'] ? array_merge($form['#parents'], array($key)) : array($key);
}
# Assign a decimal placeholder weight to preserve original array order
if (!isset($form[$key]['#weight'])) {
$form[$key]['#weight'] = $count / 1000;
}
$form[$key] = form_builder($form_id, $form[$key]);
$count++;
}
if (isset($form['#after_build']) && !isset($form['#after_build_done'])) {
foreach ($form['#after_build'] as $function) {
if (function_exists($function)) {
$form = $function($form, $form_values);
}
}
$form['#after_build_done'] = TRUE;
}
return $form;
}
?>