Added confirmation dialog to delete forms
This commit is contained in:
parent
1b21bcf769
commit
ff179360cc
|
@ -275,6 +275,71 @@ ready(() => {
|
|||
document.querySelectorAll('.modal').forEach((element) => new bootstrap.Modal(element));
|
||||
});
|
||||
|
||||
/**
|
||||
* Show confirmation modal before submitting form
|
||||
*
|
||||
* Uses the buttons data attributes to show in the modal:
|
||||
* - data-confirm_title: Optional title of the modal
|
||||
* - data-confirm_submit: Body of the modal
|
||||
*
|
||||
* The class, title and content of the requesting button gets copied for confirmation
|
||||
*
|
||||
*/
|
||||
ready(() => {
|
||||
document.querySelectorAll('[data-confirm_submit_title], [data-confirm_submit_text]').forEach((element) => {
|
||||
let modalOpen = false;
|
||||
let oldType = element.type;
|
||||
if (element.type !== 'submit') {
|
||||
return;
|
||||
}
|
||||
|
||||
element.type = 'button';
|
||||
element.addEventListener('click', (event) => {
|
||||
if (modalOpen) {
|
||||
return;
|
||||
}
|
||||
event.preventDefault();
|
||||
|
||||
document.getElementById('confirmation-modal')?.remove();
|
||||
document.body.insertAdjacentHTML(
|
||||
'beforeend',
|
||||
`
|
||||
<div class="modal" tabindex="-1" id="confirmation-modal">
|
||||
<div class="modal-dialog">
|
||||
<div class="modal-content ${document.body.dataset.theme_type === 'light' ? 'bg-white' : 'bg-dark'}">
|
||||
<div class="modal-header">
|
||||
<h5 class="modal-title">${element.dataset.confirm_submit_title ?? ''}</h5>
|
||||
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
|
||||
</div>
|
||||
<div class="modal-body${element.dataset.confirm_submit_text ? '' : ' d-none'}">
|
||||
<p>${element.dataset.confirm_submit_text ?? ''}</p>
|
||||
</div>
|
||||
<div class="modal-footer">
|
||||
<button type="button" class="${element.className}"
|
||||
title="${element.title}" data-submit="">${element.innerHTML}</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
`
|
||||
);
|
||||
|
||||
let modal = document.getElementById('confirmation-modal');
|
||||
modal.addEventListener('hide.bs.modal', () => {
|
||||
modalOpen = false;
|
||||
});
|
||||
modal.querySelector('[data-submit]').addEventListener('click', (event) => {
|
||||
element.type = oldType;
|
||||
element.click();
|
||||
});
|
||||
|
||||
modalOpen = true;
|
||||
let bootstrapModal = new bootstrap.Modal(modal);
|
||||
bootstrapModal.show();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
/**
|
||||
* Show oauth buttons on welcome title click
|
||||
*/
|
||||
|
|
|
@ -1989,3 +1989,6 @@ msgstr "Was möchtest Du machen?"
|
|||
|
||||
msgid "registration.register"
|
||||
msgstr "Registrieren"
|
||||
|
||||
msgid "confirmation.delete"
|
||||
msgstr "Möchtest du es wirklich löschen?"
|
||||
|
|
|
@ -644,3 +644,6 @@ msgstr "Please enter a lastname in your settings!"
|
|||
|
||||
msgid "mobile.required.hint"
|
||||
msgstr "Please enter a mobile number in your settings!"
|
||||
|
||||
msgid "confirmation.delete"
|
||||
msgstr "Do you really want to delete it?"
|
||||
|
|
|
@ -57,7 +57,7 @@
|
|||
<form method="post" class="ps-1">
|
||||
{{ csrf() }}
|
||||
{{ f.hidden('id', location.id) }}
|
||||
{{ f.button(m.icon('trash'), {'title': __('form.delete'), 'name': 'delete', 'type': 'submit', 'btn_type': 'danger', 'size': 'sm'}) }}
|
||||
{{ f.delete(null, {'size': 'sm','confirm_title': location.name|e}) }}
|
||||
</form>
|
||||
|
||||
</div>
|
||||
|
|
|
@ -23,7 +23,7 @@
|
|||
|
||||
{% endblock %}
|
||||
</head>
|
||||
<body>
|
||||
<body data-theme_type="{{ theme.type }}">
|
||||
|
||||
{% block body %}
|
||||
{% block header %}
|
||||
|
|
|
@ -261,6 +261,8 @@ Renders a button.
|
|||
Must be a Bootstrap icon class without prefix, such as "info" or "check".
|
||||
@param {string} [opt.icon_right] - Optional icon to be added after the button label.
|
||||
Must be a Bootstrap icon class without prefix, such as "info" or "check".
|
||||
@param {string} [opt.confirm_title] - Optional value for the confirmation title.
|
||||
@param {string} [opt.confirm_text] - Optional value for the confirmation text.
|
||||
#}
|
||||
{% macro button(label, opt) %}
|
||||
<button
|
||||
|
@ -270,6 +272,8 @@ Renders a button.
|
|||
{%- if opt.name is defined %} name="{{ opt.name }}"{% endif %}
|
||||
{%- if opt.title is defined %} title="{{ opt.title }}"{% endif %}
|
||||
{%- if opt.value is defined or opt.name is defined %} value="{{ opt.value|default('1') }}"{% endif -%}
|
||||
{%- if opt.confirm_title is defined %} data-confirm_submit_title="{{ opt.confirm_title }}"{% endif -%}
|
||||
{%- if opt.confirm_text is defined %} data-confirm_submit_text="{{ opt.confirm_text }}"{% endif -%}
|
||||
>
|
||||
{%- if opt.icon_left is defined %}<span class="bi bi-{{ opt.icon_left }}"></span>{% endif %}
|
||||
{{ label }}
|
||||
|
@ -281,6 +285,16 @@ Renders a button.
|
|||
{{ _self.button(label|default(__('form.submit')), {'type': 'submit', 'btn_type': 'primary'}|merge(opt|default({}))) }}
|
||||
{%- endmacro %}
|
||||
|
||||
{% macro delete(label, opt) %}
|
||||
{{ _self.submit(label|default(' '), {
|
||||
'icon_left': 'trash',
|
||||
'title': __('form.delete'),
|
||||
'name': 'delete',
|
||||
'btn_type': 'danger',
|
||||
'confirm_text': __('confirmation.delete')
|
||||
}|merge(opt|default({}))) }}
|
||||
{%- endmacro %}
|
||||
|
||||
{#
|
||||
Renders a "checkbox" element that will be styled as switch.
|
||||
|
||||
|
|
|
@ -354,10 +354,14 @@
|
|||
'title': 'Click me!',
|
||||
}) }}
|
||||
</div>
|
||||
<code>f.submit(label)</code>
|
||||
<form id="form">
|
||||
<code>f.submit(label, opt)</code>
|
||||
<form class="prevent-default">
|
||||
{{ f.submit('Go!') }}
|
||||
</form>
|
||||
<code>f.delete(label, opt)</code>
|
||||
<form class="prevent-default">
|
||||
{{ f.delete('Delete it', {'confirm_title': 'Delete some item'}) }}
|
||||
</form>
|
||||
</div>
|
||||
|
||||
<div id="checkboxes" class="col-md-3 col-lg-2">
|
||||
|
@ -529,9 +533,11 @@ Por scientie, musica, sport etc, litot Europa usa li sam vocabular.</code></pre>
|
|||
</div>
|
||||
</div>
|
||||
<script>
|
||||
document.getElementById('form').addEventListener('submit', (e) => {
|
||||
e.preventDefault();
|
||||
return false;
|
||||
});
|
||||
[...document.getElementsByClassName('prevent-default')].forEach((element) => {
|
||||
element.addEventListener('submit', (e) => {
|
||||
e.preventDefault();
|
||||
return false;
|
||||
});
|
||||
})
|
||||
</script>
|
||||
{% endblock %}
|
||||
|
|
|
@ -33,7 +33,7 @@
|
|||
action="{{ url('/news/comment/' ~ comment.id) }}" enctype="multipart/form-data"
|
||||
method="post">
|
||||
{{ csrf() }}
|
||||
{{ f.submit(m.icon('trash'), {'name': 'delete', 'btn_type': 'danger', 'size': 'sm', 'title': __('form.delete')}) }}
|
||||
{{ f.delete(null, {'size': 'sm', 'confirm_title': comment.text[:40]|e}) }}
|
||||
</form>
|
||||
</div>
|
||||
{% endif %}
|
||||
|
|
|
@ -54,7 +54,7 @@
|
|||
>
|
||||
{{ csrf() }}
|
||||
{{ f.hidden('id', question.id) }}
|
||||
{{ f.submit(m.icon('trash'), {'name': 'delete', 'btn_type': 'danger', 'size': 'sm', 'title': __('form.delete')}) }}
|
||||
{{ f.delete(null, {'size': 'sm', 'confirm_title': question.text[:40]|e}) }}
|
||||
</form>
|
||||
{% endif %}
|
||||
|
||||
|
|
|
@ -20,10 +20,7 @@
|
|||
<form action="" enctype="multipart/form-data" method="post">
|
||||
{{ csrf() }}
|
||||
{{ f.hidden('id', 'all') }}
|
||||
{{ f.submit(
|
||||
__('form.delete_all'),
|
||||
{'name': 'delete', 'btn_type': 'danger', 'size': 'sm', 'icon_left': 'trash'}
|
||||
) }}
|
||||
{{ f.delete(__('form.delete_all'), {'size': 'sm', 'confirm_title': __('form.delete_all')}) }}
|
||||
</form>
|
||||
{% endif %}
|
||||
</th>
|
||||
|
|
Loading…
Reference in New Issue