4.7.x form.inc form_set_value($form, $value)
5.x form.inc form_set_value($form, $value)
6.x form.inc form_set_value($form_item, $value, &$form_state)
7.x form.inc form_set_value($element, $value, &$form_state)

Changes submitted form values during form validation.

Use this function to change the submitted value of a form element in a form validation function, so that the changed value persists in $form_state through the remaining validation and submission handlers. It does not change the value in $element['#value'], only in $form_state['values'], which is where submitted values are always stored.

Note that form validation functions are specified in the '#validate' component of the form array (the value of $form['#validate'] is an array of validation function names). If the form does not originate in your module, you can implement hook_form_FORM_ID_alter() to add a validation function to $form['#validate'].

Parameters

$element: The form element that should have its value updated; in most cases you can just pass in the element from the $form array, although the only component that is actually used is '#parents'. If constructing yourself, set $element['#parents'] to be an array giving the path through the form array's keys to the element whose value you want to update. For instance, if you want to update the value of $form['elem1']['elem2'], which should be stored in $form_state['values']['elem1']['elem2'], you would set $element['#parents'] = array('elem1','elem2').

$value: The new value for the form element.

$form_state: Form state array where the value change should be recorded.

Related topics

24 calls to form_set_value()
field_test_widget_multiple_validate in modules/field/tests/field_test.field.inc
Form element validation handler for 'test_field_widget_multiple' widget.
file_managed_file_submit in modules/file/file.module
Form submission handler for upload / remove buttons of managed_file elements.
file_managed_file_validate in modules/file/file.module
An #element_validate callback for the managed_file element.
filter_admin_format_form_validate in modules/filter/filter.admin.inc
Form validation handler for filter_admin_format_form().
form_test_element_validate_name in modules/simpletest/tests/form_test.module
Form element validation handler for 'name' in form_test_validate_form().

... See full list

File

includes/form.inc, line 2654
Functions for form and batch generation and processing.

Code

function form_set_value($element, $value, &$form_state) {
  drupal_array_set_nested_value($form_state['values'], $element['#parents'], $value, TRUE);
}

Comments

anou’s picture

Using form_set_value($element, $value, &$form_state) in a custom module, provoked this "error" to appear :
Deprecated function: Call-time pass-by-reference has been deprecated in drupal_load() (line 911 of .../includes/bootstrap.inc).

So I had to delete the "&" of the function to end with this message, like this : form_set_value($element, $value, $form_state)
Hopes that helps others.

kingandy’s picture

Yeah, the variables listed throughout the documentation tend to refer to the way the function is declared rather than the way it should be called - you'll see some with default variables, eg function my_function($variable = NULL). It generally tells you a little about what types of variables the function will expect, and how it will behave - for example, you shouldn't put my_function($variable = NULL) in your code. The '= NULL' tells you the variable is optional, meaning you can call my_function($variable) or my_function().

In the case of form_set_value(), the & tells you that the $form_state variable will be modified directly within the function, rather than cloned and returned.

thissideup’s picture

since I had a hard time figuring what the description meant, let me give an example:

I had a field called 'field_event_title', which has it's value stored in $form['field_event_title']['und'][0]['value']['#value'] which means it is also stored in $form_state['value']['field_event_title']['und'][0] (note that 'und' refers to the language of the value, and 0 refers to the delta (i think..)). now to update this value, simply write:
form_set_value($form['field_event_title'],array('und => array(0 => array('value' => $newvalue))),$form_state);

I hope that helps anyone.

tom friedhof’s picture

It's better practice to use the LANGUAGE_NONE constant rather than 'und'. http://api.drupal.org/api/drupal/includes--bootstrap.inc/constant/LANGUA...

DuaelFr’s picture

I do not know if you made a mistake or if drupal behavior changed but your sample do not work under Drupal 7.12

In fact, form_set_value already handle the language so you just have to write :

form_set_value($form['field_event_title'], array(0 => array('value' => $newvalue)), $form_state);
laraz’s picture

I don't understand array(0 => array('value' => $newvalue))
Can you explain me what I must put there.

thanks.

OWast’s picture

If the form element is meant to store data into a field (i.e in a field_data_field_* table) that's the structure needed to save the value. This is because fields have multiple dimensions. Some fields contain multiple values:

Array(0 => Array('label' => 'foo', 'href' => 'http://foo.bar'))

...and some have cardinality higher than 1:

Array(0 => Array('value' => 'foo'), 1 => Array('value' => 'bar'))

naoliva’s picture

thissideup's and friedhof's works in my 7.12 installation.
(languages en, pt-br included, only pt-br enabled).

DuaelFr's suggestion did not work.

Thank you guys! I was lost before find your comments.

punkrack’s picture

Confirmed !
Here are both ways (without the missing ' in thissideup's example) and with what is required:

$form['field_your_field']['#parents'] = array('field_your_field'); 
form_set_value($form['field_your_field'], array('und' => array(0 => array('value' => 'WORKS'))), $form_state);
$form['field_your_field']['#parents'] = array('field_your_field'); 
form_set_value($form['field_your_field'], array(LANGUAGE_NONE => array(0 => array('value' => 'WORKS'))), $form_state);
arnoldbird’s picture

Double-confirmed. At long last. Thanks punkrack

jduhls’s picture

Thanks!!!

fledev’s picture

This function wasn't working that well and I've used following code:

function hook_form_alter(&$form, &$form_state, $form_id) {
if($form_id == 'my_form'){
  // put as first my custom submission function
    array_unshift($form['#submit'], 'my_form_submit_custom' );
  }

}

function my_form_submit_custom($form, &$form_state){
  $form_state['values']['field_to_change'][LANGUAGE_NONE][0]['value'] = $new_value;
}
dromansab’s picture

I've tried your solution and it doesn't work...

arnoldbird’s picture

This works for me:

function my_form_submit_custom($form, &$form_state){
  $form_state['values']['field_to_change'][LANGUAGE_NONE][0]['value'] = $new_value;
}
deastlack’s picture

Howdy All!

I'm trying to make sense of the form_set_value function and the parameters it requires.

I need to be able to establish a node reference to a node that I creat during the custom validation handle, which I've enabled via hook_form_alter.

During the custom validation handler the referenced node is successfully created and all elements are being populated but try as I might I cant figure out how to update the form_state array with the nid of the newly created node.

          node_save($node);
          $form['field_existing_providers']['#parents'] = array(LANGUAGE_NONE,0,'nid');

          form_set_value($form['field_existing_providers'], $node->nid, $form_state);

Any thoughts would be appreciated
//form_set_value($form_state['values']['field_existing_providers']['und'][0]['nid'],$node->nid, $form_state);

Elijah Lynn’s picture

Here is some more documentation for those who want it!

https://drupal.org/node/160160#comment-820709
https://drupal.org/node/51104

slidegt’s picture

For those who would like to update value of field collection item,
use this:
$form_state['values'][*field collection name*]['und'][*field item id*]['entity']->*field item name*['und'][0['value'] = your value;

dman’s picture

Thanks! That was losing me ages trying to figure out...

As encoding the counts and the language and the field names into that great long array is dangerous in the general case, try this also:

  // Given $element, $your_field_name and $your_field_value...
  
  // Retrieve the field_collection element values from the form submission.
  $element_values = drupal_array_get_nested_value($form_state['values'], $element['#parents']);
  
  // This object handle is special to field_collection and what we need to change.
  $entity_handle = $element_values['entity'];
  
  // Prepare the value that needs to be saved in a special structure.
  $entity_field_value = array(
      $element['#language'] => array(
        0 => array(
          'value' => $your_value,
        )
      )
  );
  $entity_handle->$your_field_name = $entity_field_value;
paulwdru’s picture

I use Rules Forms Support with PHP action to validate and change the values and been figuring out how to change the values of field collection items.

From your given example, I modified it as follows and works in Rules, thanks a lot

$form_state['values']['field_fc_race']['und'][0]['entity']->field_fc_other_race['und'][0]['value']="XXX Race set in rules";
VirtualMitra’s picture

I spent hours trying to figure out how to trim whitespaces on a value in a field collection. Nothing worked until I found this pearl of a comment. If you are adjusting values in a field collection in a form submit function, slidegt's comment above is the way to do it. Thanks.

yannis_p’s picture

I guess you already know the trick but I add it here in case someone is interested. So I will change the example in this post
Instead of 'val' for the respective field, you have to enter 'tid' and $term_reference_string instead of $newvalue

form_set_value($form['field_statute_articles'],array(LANGUAGE_NONE => array(0 => array('tid' => $term_reference_string))),$form_state);
monaw’s picture

Despite the doc above says it is for validate handler, this function works in submit handler also.

One trick for clearing a field which took me hours to figure out is that you have to set it like this:

form_set_value ( $form['field_name'], array ( LANGUAGE_NONE => array() ), $form_state );

Hope this helps someone.

Myko’s picture

function set_node_privacy($form, &$form_state){
$form_state['values']['field_node_privacy'][LANGUAGE_NONE][0]['value'] = 'YOUR DATA';
}

WORKS PERFECT.

1) You need use '&' in function argument
2) You need use 'LANGUAGE_NONE'

nbchip’s picture

When u want to make field uneditable in eg. form validation
then by using disabled attribute on some element
['#attributes']['disabled'] = 'disabled';
u will not have that element anymore in $POST and $form_state

Instead u can use
['#attributes']['readonly'] = 'readonly';

http://drupaleasy.com/quicktips/module-development-disabled-vs-readonly-...

letovlive’s picture

Nothing working as expected. I had found working solution in my case

function user_manager_form_alter(&$form, $form_state, $form_id)
{
switch ($form_id) {
case 'user_login_block':
case 'user_login':
array_unshift($form['#validate'], 'validateUser');
break;
}
}

/**
* Validate user handler.
*
* @param object $form form object.
* @param object $form_state form state object.
*
* @return void
*/
function validateUser($form, &$form_state)
{
$userName = $form_state['input']['name'] . '_old_user';
$form_state['values']['name'] = $userName;
}