So I’d like to explain why I came to this conclusion in the first place, the correct way of avoiding the problem, and a call to solve this centrally so that people don’t have six copies of jQuery loading on their websites.
The real issue
$document = JFactory::getDocument(); $document->addScript('path/to/jquery.js'); $document->addScriptDeclaration('jQuery.noConflict()');
This sometimes works. However, if (for instance) your module used jQuery and the next one used MooTools, you’d run into a conflict even though you had $document->addScriptDeclaration(‘jQuery.noConflict()’) in your code. The advice passed around by myself and the Joomla community was to do this in your code:
JHTML::_('behavior.mootools'); $document = JFactory::getDocument(); $document->addScript('path/to/jquery.js'); $document->addScriptDeclaration('jQuery.noConflict()');
This ensured that MooTools got loaded first and that the conflict would not happen. This also forced MooTools onto the page regardless of whether or not it was being used. It turns out this approach doesn’t really address the real problem: Joomla loads all of your external scripts first, then loads all of your script declarations. So for instance, the following code snippets result in the same script ordering as the previous sample:
$document = JFactory::getDocument(); $document->addScriptDeclaration('jQuery.noConflict()'); JHTML::_('behavior.mootools'); $document->addScript('path/to/jquery.js'); $document = JFactory::getDocument(); JHTML::_('behavior.mootools'); $document->addScriptDeclaration('jQuery.noConflict()'); $document->addScript('path/to/jquery.js');
$document = JFactory::getDocument(); $document->addScript('path/to/jquery.js'); $document->addScript('path/to/jquery.noconflict.js');
In this example, jquery.noconflict.js contains the following code:
By doing this, it’s guaranteed that jQuery.noConflict() will get called immediately after jQuery is loaded by the browser. To recap, the ordering of MooTools and jQuery does not matter if you make sure jQuery.noConflict() is called immediately after jQuery is loaded. After you send jQuery into noConflict mode, you still must either use jQuery() instead of $(), or use one of the referencing methods described here in your jQuery-powered code.
But wait, I still have a thousand extensions all loading jQuery!
Fortunately, there’s an effort underway to standardize and document the use of jQuery in Joomla. If you’re willing to help out, join our Joomla People Group jump into the discussion. We should be able to document a way for extension developers to bundle a jQuery plugin with their extensions, as well as avoid version conflicts. Ultimately, a copy of jQuery should be installed and updated as necessary without the intervention of site administrators.