Code sample #7:

This adds the submit function, also referred to as a submit handler.

<?php
/**
 * Implements hook_menu().
 */
function my_module_menu() {
  $items = array();

  $items['my_module/form'] = array(
    'title' => t('My form'),
    'page callback' => 'drupal_get_form',
    'page arguments' => array('my_module_my_form'),
    'access arguments' => array('access content'),
    'description' => t('My form'),
    'type' => MENU_CALLBACK,
  );
  return $items;
}

/**
 * Returns the render array for the form.
 */
function my_module_my_form($form, &$form_state) {
  $form['name'] = array(
    '#type' => 'fieldset',
    '#title' => t('Name'),
    '#collapsible' => TRUE,
    '#collapsed' => FALSE,
  );

  $form['name']['first'] = array(
    '#type' => 'textfield',
    '#title' => t('First name'),
    '#required' => TRUE,
    '#default_value' => "First name",
    '#description' => "Please enter your first name.",
    '#size' => 20,
    '#maxlength' => 20,
  );

  $form['name']['last'] = array(
    '#type' => 'textfield',
    '#title' => t('Last name'),
    '#required' => TRUE,
  );

  $form['year_of_birth'] = array(
    '#type' => 'textfield',
    '#title' => t('Year of birth'),
    '#description' => 'Format is "YYYY"',
  );  

  $form['submit'] = array(
    '#type' => 'submit',
    '#value' => t('Submit'),
  );

  return $form;
}
/**
 * Validates the form.
 */
function my_module_my_form_validate($form, &$form_state) {
  $year_of_birth = $form_state['values']['year_of_birth'];
  if ($year_of_birth && ($year_of_birth < 1900 || $year_of_birth > 2000)) {
    form_set_error('year_of_birth', t('Enter a year between 1900 and 2000.'));
  }
}

/**
 * Add a submit handler/function to the form.
 *
 * This will add a completion message to the screen when the
 * form successfully processes
 */
function my_module_my_form_submit($form, &$form_state) {
  drupal_set_message(t('The form has been submitted.'));
}

Comments

drupalshrek’s picture

It only requires a small change to be able to call a View with arguments from the form. For example, imagine you have a View which takes two arguments, First name and Last name. The form could call this View based on the values the user has selected, e.g.

function my_module_my_form_submit($form, &$form_state) {
    $first_name = $form_state['values']['first']; 
    $last_name = $form_state['values']['last'];

    drupal_goto("/my_view/".$first_name."/".$last_name);
}

drupalshrek

xenophyle’s picture

Some documentation (http://drupal.org/node/222158) seems to say you would need to have a line in my_module_my_form

$form['#submit'][] = 'my_module_my_form_submit';

but it seems to work the same either way. Can someone explain? Is it only necessary when the form doesn't provide a submit button?

beanluc’s picture

xenophyle, that documentation says that it's necessary when you want to add additional submit handlers. The example specifies the default handler, but, you would add more handlers with the same syntax.

Actually, the reason they presented the example this way is that the example shows a form which does nothing but set var's on submit, which you don't even need a handler for (not as written, anyway). So the default handler is an "extra" handler in that case.

jacobson’s picture

$form['#submit'][] = 'my_module_my_form_additional_submit';

The default submit handler is always the name of the form function (e.g., my_module_my_form in the code example above) with "_submit" added. So, an additional submit handler is any submit handler function other than the default.

0xhiryuu’s picture

I've needed to add $form['#submit'][] = 'my_module_my_form_submit' to make this work.
Maybe its because I'm creating a CK2 module?

Maedi’s picture

Just to bridge the gap for people new to hook_form_alter. To find the appropriate variables for use in your submit handler function, insert dpm($form_state); inside your function, not in the main hook_form_alter in which you've declared the #submit attribute. The $form_state variable structure changes with each stage of the form. Now to see the variables you can work with in the Save stage, edit a form then submit, and the correct variables will be output on the next page.

amitcast’s picture

<?php
function my_module_menu() {
  $items = array();
  $items['my_module/form'] = array(
    'title' => t('My form'),
    'page callback' => 'my_module_form',
    'access arguments' => array('access content'),
    'description' => t('My form'),
    'type' => MENU_CALLBACK,
  );
  
  $items['admin/content/mymodule'] = array(
    'title' => t('My Form data'),
	'description' => t('My form data'),
    'page callback' => 'my_module_data',
    'access callback' => 'user_access',
	'access arguments' => array('access content'),
  );
  return $items;
}
/*
function my_module_data() {
$result = db_query('SELECT fname FROM {member}');
while ( $obj = db_fetch_object ($result) ) {
  $n1 = $obj->fname;
}
return $n1;
} */

function my_module_data() {
$result = db_query('SELECT * FROM {member}');
$items = array();
while ($row = db_fetch_object($result)) {
$items[] = "First name: ".$row->fname." | ". "Last name:".$row->lname." - ".$row->email. " - ".$row->pass;
}
return theme('item_list',$items);
}

function my_module_form() {
  return drupal_get_form('my_module_my_form');
}

function my_module_my_form($form_state) {
  $form['first'] = array(
    '#type' => 'textfield',
    '#title' => t('First Name'),
	'#required' => TRUE, // Added
	'#size' => 20, // added
    '#maxlength' => 20, // added
  );
  $form['last'] = array(
    '#type' => 'textfield',
    '#title' => t('Last Name'),
	'#required' => TRUE, // Added
  );
  $form['email'] = array(
    '#type' => 'textfield',
    '#title' => t('Email'),
	'#required' => TRUE, // Added
  );
  $form['pass'] = array(
    '#type' => 'password',
    '#title' => t('Password'),
	'#required' => TRUE, // Added
  );
   
    
  // Adds a simple submit button that refreshes the form and clears its contents -- this is the default behavior for forms.
  $form['submit'] = array(
    '#type' => 'submit',
    '#value' => 'Submit',
  );
  
  
  return $form;
}


// Adds a submit handler/function to our form to send a successful 
// completion message to the screen.


function my_module_my_form_submit($form, &$form_state) {

$fname = $form_state['values']['first'];
$lname = $form_state['values']['last'];
$email = $form_state['values']['email'];
$pass = $form_state['value']['pass'];


db_query("INSERT INTO {member} (fname, lname, email, pass) VALUES('%s', '%s', '%s', '%s')", $fname, $lname, $email, $pass);

    drupal_set_message(t('The form has been submitted.'));
	}

sridharpandu’s picture

I have encountered this issue. The function my_module_my_form_submit doesn't seem to get called. Is there a way out.

Acer Aspire 5745
[i5 430M, 3GB, 320GB]
Ubuntu 12.04 (Precise Pangolin)
Drupal 6.15, 7.x
DigitalOcean, Go Daddy, Rackspace,

strick’s picture

You have to add $form['#submit'][] = 'my_module_my_form_submit'; to my_module_my_form(). That made it work for me.

jalalkhan121’s picture

I had the same issue, the solution is that you need to enter valid values in email, pass etc while submitting the form.
I will start working...

steveturri’s picture

I used the example for drupal 7.x
I am not finding a way to modify the tab labels like you see on this page.
http://d7.drupalexamples.info/examples/form_example/tutorial

Any help would be much appreciated.

Steve

shafiul’s picture

Does it work for Drupal 7.x or what is the appropriate way for Drupal 7?

mchar’s picture

It does work for D7!

10kinds’s picture

Thought I'd drop this on here for those looking to call a function from a .inc file. I needed this today and had to locate a couple of pieces of information around the forums, etc.

I needed to pass the textfield value to a function in my .inc file, so this is how I did it:


/**
 * Custom form.
 */
function pagenode_form($form, &$form_state) {

  $form['pageid'] = array(
    '#type' => 'textfield',
    '#title' => t('Page ID')
  );

  $form['submit'] = array(
    '#type' => 'submit',
    '#value' => t('Import')
  );

  return $form;
}

function pagenode_form_submit($form, &$form_state) {
  // load the .inc file
  form_load_include($form_state, 'inc', 'pagenode','pagenode.extra');

  pagenode_addid($form['pageid']['#value']);

}

This is just the PoC for me, so it needs validation and direction on what to do once it returns, but this is the basis of the idea. (Also will make my titles more descriptive to the user, but you get the point)