AJAX in Joomla!

You want a form that updates one selector based on the selection made in another selector. For example, in your form, the user might click on a link to generate a select of all the site users so he can choose one user to interact with. You don’t want the list of users on the form, initially, for whatever reason.

The obvious solution comes to mind – AJAX. How do you accomplish that in Joomla?

First, you’ll need a component to listen for the AJAX requests and supply the updated HTML information to the form. While you’re at it, you probably want to make the form part of the component, just to be elegant.

Joomla! 1.5+ is built on a Model-View Controller concept, which basically means we want to keep our data (the model) separated from the display of it (the view). The MVC paradigm is a way of breaking an application, or even just a piece of an application’s interface, into three parts: the model, the view, and the controller.

 

MVC

 

 

 

The Model

The model is the part of the component that allows access to manipulate the application’s data. It provides the routines necessary to add, remove, update, and retrieve information in the application. In our example, the model will query the database to get appropriate options in a selector.

The View

The view is the part of the component that is used to render the application in the browser for the viewer by feeding it into a template. The view doesn’t manipulate the data – it just displays it.

The Controller

The controller is responsible for handling user actions, in this case, page requests. It does not display the data, but it triggers the methods in the model which manipulate it (which then triggers the methods in the view to display it).

 

This MVC pattern is implemented in Joomla! using three classes: JModel, JView, and JController

If you open up a component directory in your Joomla! site, you might notice a lot of files. It may seem like a lot of files to do a simple task, but bear in mind, this is the framework for really large tasks also.

We’re going to need a working directory somewhere to build a few files in before we get to the meat of this application. Make a folder called com_ajaxhandler and put the following directories and files in it. Just make empty files for now – we’ll fill them in as we go.

/com_ajaxhandler

  • /admin(administration folder – the part you see in the back end of Joomla!)
    • index.html (blank file)
    • admin.ajaxhandler.php (this will create the controller)
    • toolbar.ajaxhandler.php (toolbar in admin back end – not strictly necessary)
    • toolbar.ajaxhandler.html.php (tool bar definition and a help menu item for this component – not strictly necessary)
    • /controllers (here’s the component controllers)
      • default.php (the default controller)
      • form1.php (controller for our form)
    • /models (the model)
      • ajaxhandler.php (just one model)
    • /views (one for each controller)
      • /default
        • view.php
      • /form1
        • view.php
  • /component (the part you see in the front end)
    • ajaxhandler.php (generates our form and selector)
  • com_ajaxhandler.xml (defines all the files for the joomla installer)

 

Don’t worry, the source code is attached to this article 😉

 

Let’s look at the component/ajaxhandler.php first. This is the file that will display in the content area on a page where you set a menu link to it. It should show the user the form, and when he clicks on just the right spot, should show him a select of all the users in the site.

 

/**
* @package AjaxHandler
* @version 1.0
* @copyright Copyright (C) 2005 Open Source Matters. All rights reserved.
* @license http://www.gnu.org/copyleft/gpl.html GNU/GPL, see LICENSE.php
* Joomla! is free software and parts of it may contain or be derived from the
* GNU General Public License or other free or open source software licenses.
* See COPYRIGHT.php for copyright notices and details.
*/

// no direct access
defined( ‘_JEXEC’ ) or die( ‘Restricted access’ );

$action = JRequest::getVar( ‘action’, ‘none’ );
switch ($action) {
    case ‘selector1’:
        /* this case is reached when a no-html call is sent to index2.php
          it spits out the javascript to replace the text in the div
          hence all the header calls here at the beginning
        */
        //header(“Cache-Control: no-cache”);
        header(“Pragma: nocache”);
        //header(“Content-Type: text/xml; charset=utf-8”);
        header(‘Content-type: text/javascript’);
        // Date in the past
        header(‘Expires: Mon, 26 Jul 1997 05:00:00 GMT’);
        // always modified
        header(‘Last-Modified: ‘ . gmdate(‘D, d M Y H:i:s’) . ‘ GMT’);
        // HTTP/1.1
        header(‘Cache-Control: no-store, no-cache, must-revalidate’);
        header(‘Cache-Control: post-check=0, pre-check=0’, false);
       
        //let’s get our list of users from the database now
        $query = “select * from #__users”;
        $db = & JFactory::getDBO(); // get instance to database
        $db->setQuery($query); //set the query and execute it
        $rows = $db->loadObjectList(); // put the result set in $rows
        if (count($rows) > 0) { // make sure you got a result set before using it
            $selector = “select a userid . “\”>” . $row->username . “”;               
        }
        $selector = str_replace(“‘”, “\'”, $selector); // because javascript sucks

        echo ”       
            $(‘joo_users’).setHTML(‘” . $selector . “‘);
        “; // change whatever is in the joo_users div to be the selector just built
    break; // all done – get out
    default:
        /* what to do when no ajax request comes in
         – what the component shows when this component is
           assigned to a menu link and user goes there */
        /* the default case displays the form */
        // get the document reference
            $document  = & JFactory::GetDocument();
            JHTML::_(‘behavior.mootools’);

        // add the javascript to actually “do” the ajax client-side
            $document->addScriptDeclaration(“
            window.addEvent(‘domready’, include_rpc);
            function include_rpc(script_filename) {
                if (script_filename != null) {
                    var html_doc = document.getElementsByTagName(‘head’).item(0);
                    var js = document.createElement(‘script’);
                    js.setAttribute(‘language’, ‘javascript’);
                    js.setAttribute(‘type’, ‘text/javascript’);
                    js.setAttribute(‘src’, script_filename);
                    html_doc.appendChild(js);
                }
                return false;
            }  
        “);
        // out put the form
            echo “<div id=\”joo_users\”><a href=\”#\” onclick=\”include_rpc(‘index2.php?option=com_ajaxhandler&action=selector1&no_html=1’);\”>Click here to see all users</a></div>”;
    break;
}
//shouldn’t be doing anything outside of the main switch
?>

 

We’ll go through the admin side of things in our next installment of this article. Basically, the admin provides a specific version of the JController, JModel, and JView classes so our new component knows how to behave inside Joomla!

To see it in action here, click the Demo link in the Main Menu in the top of the left-most column on this page.

To install it on your own Joomla! site, to see how it works, install it through the backend like you would any component. Then add a menu link to one of your menus and give it type Ajax Handler. Go to that menu link, and you’ll have a clicky-link that changes to a selector of all your users. (User names are slightly obfuscated in this site’s demo)


Leave a Reply

Your email address will not be published. Required fields are marked *