Templates & Frontend
Put the Joomla Login Form in a Modal Dialog
A login form sitting permanently in a sidebar takes up room on every page for something visitors need once. Moving it into a modal is a template job, not an extension job: one alternative layout for mod_login and a native <dialog> element.
Create the alternative layout
Copy the module's layout into your template so updates cannot overwrite it:
mkdir -p templates/yourtemplate/html/mod_login
cp modules/mod_login/tmpl/default.php templates/yourtemplate/html/mod_login/modal.php
Naming it something other than default.php matters: default.php would silently replace the layout everywhere the module appears, while a separate name becomes an option you pick per module instance.
Select it in the module's Advanced tab, under Layout.
Wrap the form
The stock layout has two branches — one rendered for signed-in users, one for guests. You only want the guest branch in a dialog. Wrap that part:
<button type="button" class="login-trigger" data-dialog="login-dialog">
<?php echo Text::_('JLOGIN'); ?>
</button>
<dialog id="login-dialog" class="login-dialog">
<form method="dialog" class="login-dialog__close">
<button value="cancel" aria-label="Close">×</button>
</form>
<!-- the existing login form markup goes here, unchanged -->
</dialog>
Leave the form's own action, hidden fields and CSRF token exactly as they are. The token is what makes the login work; a form that posts without it is rejected.
Open it
document.querySelectorAll('[data-dialog]').forEach((trigger) => {
trigger.addEventListener('click', () => {
document.getElementById(trigger.dataset.dialog)?.showModal();
});
});
That is the whole script. showModal() gives you the backdrop, focus trapping and Esc to close for free — all the behaviour the old modal libraries had to implement by hand.
Register it through the web asset manager rather than a raw <script> tag, so it is versioned and deferred with everything else:
use Joomla\CMS\Factory;
Factory::getApplication()
->getDocument()
->getWebAssetManager()
->registerAndUseScript(
'tpl.login-dialog',
'media/templates/site/yourtemplate/js/login-dialog.js',
['version' => 'auto'],
['defer' => true]
);
Style the backdrop
.login-dialog {
border: 0;
padding: 2rem;
max-width: 22rem;
}
.login-dialog::backdrop {
background: rgb(0 0 0 / 0.6);
}
Note what you no longer need: the old approach hid the form with display: none and relied on the modal script to reveal it. A <dialog> is hidden until opened, so if scripting fails the form stays closed rather than appearing unstyled halfway down the page.
Two things worth checking
Failed logins reload the page. Decide what should happen then — either let the visitor reopen the dialog, or reopen it automatically when the page carries an error message, so they do not lose the context of what they were doing.
And keep the trigger a real <button>. An <a href="#"> styled as a button is not reachable the same way by keyboard or screen reader, and a login form is the last place to be careless about that.
One thing you may run into while searching: guides that call behavior.modal to open a modal. That helper belongs to a modal library Joomla no longer ships, and the call does nothing on a current site.