Drupal 6: Inserting a form in a lightbox window and submitting it with AJAX
The purpose of this code snippet is to show you how you can use the lightmodal functionality in the Lightbox2 module to embed a form in a fancy css popup window. But why would you want to do this? Because it looks great and it improves usability.
The first thing you’ll need to do is register a menu item for the page callback that you’d like to appear in the lightbox window.
<?php
function MYMODULE_menu() {
$items[] = array();
$items['MY/URL'] = array(
'page callback' => 'drupal_get_form',
'page arguments' => array('MYCALLBACK_form'),
'type' => MENU_CALLBACK,
'title' => t('MY TITLE')
);
return $items;
}
?>
Next define a function to create the form:
<?php
function MYCALLBACK_form($form_state) {
$form = array();
// add your form elements here. for example:
$form['MYTEXTFIELD'] = array(
'#type' => 'textfield',
'#title' => t('MY TEXT FIELD'),
);
// add submit button
$form['submit'] = array(
'#value' => 'Submit',
'#type' => 'button'
);
// add cancel button
// NOTE: the cancel button simply closes the lightbox window
$form['cancel'] = array(
'#value' => 'Cancel',
'#type' => 'button',
'#attributes' => array(
'onClick' => "Lightbox.end('forceClose'); return false;"
)
);
return $form;
}
?>
Next add a link to your page content to open up the lightbox window with your new form in it. By adding the rel=lightmodal property onto an A tag, you’ll automatically load the contents of the href in a fancy lightbox window.
<?php
// NOTE: you should use the l() function here to properly generate your A tag
$page_contents .= '<a href="/MY/URL" rel="lightmodal">MY LINK TEXT</a>';
?>
I made my lightbox form more usable by using ajax to submit the form to another page callback. First I had to add an onSubmit javascript event handler to my form to prevent it from submitting.
<?php
function MYCALLBACK_form($form_state) {
// ...code...
$form['#attributes'] = array(
'onsubmit' => 'return my_js_submit_function(this);'
);
// ...code...
}
?>
Now define a javascript function to validate and submit the form using AJAX.
function my_js_submit_function(whichThis) {
// validate your form here
// define arguments to pass to ajax page callback
// you'll actually want to collect the user submitted form data here
var args = {
myArg1: 'blah',
myArg2: 'blah',
};
// submit the data using jQuery
// in this case, I'm using the getJSON function which uses GET and expects a JSON object in return
$.getJSON('/MY/URL/SUBMIT', args,
function(json){
// check for a return status, show a message, close the lightbox window, etc
alert(json.message);
if (json.status == true) {
Lightbox.end('forceClose');
}
}
);
}
You’ll need a final page callback and menu item to process the AJAX
<?php
function MYMODULE_menu() {
// ...code...
$items['MY/URL/SUBMIT'] = array(
'page callback' => 'MYMODULE_CALLBACK_SUBMIT',
'type' => MENU_CALLBACK,
);
// ...code...
}
function MYMODULE_CALLBACK_SUBMIT() {
// 1. validate $_GET (not shown, use your imagination)
// 2. process $_GET (not shown, use your imagination)
// 3. return a JSON object
// create return object
$returnO = new StdClass();
$returnO->status = true;
$returnO->message = 'MY INFORMATIVE MESSAGE HERE';
// output json result
print drupal_json($returnO);
// NOTE: if you don't die here, then the theme will be processed. we only want to return a JSON object
die;
}
?>
In the end what we have is a link that opens up a lightbox window that contains a form that is submitted via ajax.
My last thoughts: because the lightmodal functionality loads the URL from the href in the A tag, you might want to create a template file for your page layout that is simplified to prevent your normal page layout from being rendered. For instance, you could create a theme file called, page-MY-URL.tpl.php that contains the following:
<?php
if ($title) print "<h1>$title</h1>";
if ($messages) print $messages;
if ($help) print $help;
if ($content) print $content;
?>