Files
thrillwiki_django_no_react/backend/templates/components/modals/modal_confirm.html

185 lines
7.9 KiB
HTML

{% comment %}
Confirmation Modal Component
============================
Pre-styled confirmation dialog for destructive or important actions.
Purpose:
Provides a standardized confirmation dialog with customizable
title, message, and action buttons.
Usage Examples:
Basic confirmation:
<div x-data="{ showDeleteModal: false }">
<button @click="showDeleteModal = true">Delete</button>
{% include 'components/modals/modal_confirm.html' with
modal_id='delete-confirm'
show_var='showDeleteModal'
title='Delete Park'
message='Are you sure you want to delete this park? This action cannot be undone.'
confirm_text='Delete'
confirm_variant='destructive'
%}
</div>
With icon:
{% include 'components/modals/modal_confirm.html' with
modal_id='publish-confirm'
show_var='showPublishModal'
title='Publish Changes'
message='This will make your changes visible to all users.'
icon='fas fa-globe'
icon_variant='info'
confirm_text='Publish'
%}
With HTMX:
{% include 'components/modals/modal_confirm.html' with
modal_id='archive-confirm'
show_var='showArchiveModal'
title='Archive Item'
message='This will archive the item.'
confirm_hx_post='/api/archive/123/'
%}
Parameters:
Required:
- modal_id: Unique identifier for the modal
- show_var: Alpine.js variable name for show/hide state
- title: Modal title
- message: Confirmation message
Optional:
- icon: Icon class (default: auto based on variant)
- icon_variant: 'destructive', 'warning', 'info', 'success' (default: 'warning')
- confirm_text: Confirm button text (default: 'Confirm')
- confirm_variant: 'destructive', 'primary', 'warning' (default: 'primary')
- cancel_text: Cancel button text (default: 'Cancel')
- confirm_url: URL for confirm action (makes it a link)
- confirm_hx_post: HTMX post URL for confirm action
- confirm_hx_delete: HTMX delete URL for confirm action
- on_confirm: Alpine.js expression to run on confirm
Dependencies:
- modal_base.html component
- Tailwind CSS
- Alpine.js
- HTMX (optional)
{% endcomment %}
{% with icon_variant=icon_variant|default:'warning' confirm_variant=confirm_variant|default:'primary' confirm_text=confirm_text|default:'Confirm' cancel_text=cancel_text|default:'Cancel' %}
{# Determine icon based on variant if not specified #}
{% with default_icon=icon|default:'fas fa-exclamation-triangle' %}
<div id="{{ modal_id }}"
x-show="{{ show_var }}"
x-cloak
@keydown.escape.window="{{ show_var }} = false"
x-init="$watch('{{ show_var }}', value => { document.body.style.overflow = value ? 'hidden' : '' })"
class="fixed inset-0 z-[60] flex items-center justify-center p-4"
role="alertdialog"
aria-modal="true"
aria-labelledby="{{ modal_id }}-title"
aria-describedby="{{ modal_id }}-message">
{# Backdrop #}
<div class="fixed inset-0 bg-black/50 backdrop-blur-sm"
x-show="{{ show_var }}"
x-transition:enter="transition ease-out duration-200"
x-transition:enter-start="opacity-0"
x-transition:enter-end="opacity-100"
x-transition:leave="transition ease-in duration-150"
x-transition:leave-start="opacity-100"
x-transition:leave-end="opacity-0"
@click="{{ show_var }} = false"
aria-hidden="true">
</div>
{# Modal Content #}
<div class="relative w-full max-w-md bg-background rounded-xl shadow-2xl overflow-hidden border border-border"
x-show="{{ show_var }}"
x-transition:enter="transition ease-out duration-200"
x-transition:enter-start="opacity-0 scale-95"
x-transition:enter-end="opacity-100 scale-100"
x-transition:leave="transition ease-in duration-150"
x-transition:leave-start="opacity-100 scale-100"
x-transition:leave-end="opacity-0 scale-95"
@click.stop>
<div class="p-6">
{# Icon and Title #}
<div class="text-center">
{# Icon #}
<div class="mx-auto mb-4 w-14 h-14 rounded-full flex items-center justify-center
{% if icon_variant == 'destructive' or confirm_variant == 'destructive' %}bg-red-100 dark:bg-red-900/30
{% elif icon_variant == 'success' %}bg-green-100 dark:bg-green-900/30
{% elif icon_variant == 'info' %}bg-blue-100 dark:bg-blue-900/30
{% else %}bg-yellow-100 dark:bg-yellow-900/30{% endif %}">
<i class="{{ default_icon }} text-2xl
{% if icon_variant == 'destructive' or confirm_variant == 'destructive' %}text-red-600 dark:text-red-400
{% elif icon_variant == 'success' %}text-green-600 dark:text-green-400
{% elif icon_variant == 'info' %}text-blue-600 dark:text-blue-400
{% else %}text-yellow-600 dark:text-yellow-400{% endif %}"
aria-hidden="true"></i>
</div>
{# Title #}
<h3 id="{{ modal_id }}-title" class="text-lg font-semibold text-foreground mb-2">
{{ title }}
</h3>
{# Message #}
<p id="{{ modal_id }}-message" class="text-muted-foreground">
{{ message }}
</p>
</div>
{# Actions #}
<div class="mt-6 flex flex-col-reverse sm:flex-row gap-3 sm:justify-center">
{# Cancel button #}
<button type="button"
@click="{{ show_var }} = false"
class="btn btn-outline w-full sm:w-auto">
{{ cancel_text }}
</button>
{# Confirm button #}
{% if confirm_url %}
<a href="{{ confirm_url }}"
class="btn w-full sm:w-auto text-center
{% if confirm_variant == 'destructive' %}btn-destructive
{% elif confirm_variant == 'warning' %}bg-yellow-600 hover:bg-yellow-700 text-white
{% else %}btn-primary{% endif %}">
{{ confirm_text }}
</a>
{% elif confirm_hx_post or confirm_hx_delete %}
<button type="button"
{% if confirm_hx_post %}hx-post="{{ confirm_hx_post }}"{% endif %}
{% if confirm_hx_delete %}hx-delete="{{ confirm_hx_delete }}"{% endif %}
hx-swap="outerHTML"
@htmx:after-request="{{ show_var }} = false"
class="btn w-full sm:w-auto
{% if confirm_variant == 'destructive' %}btn-destructive
{% elif confirm_variant == 'warning' %}bg-yellow-600 hover:bg-yellow-700 text-white
{% else %}btn-primary{% endif %}">
{{ confirm_text }}
</button>
{% else %}
<button type="button"
@click="{% if on_confirm %}{{ on_confirm }};{% endif %} {{ show_var }} = false"
class="btn w-full sm:w-auto
{% if confirm_variant == 'destructive' %}btn-destructive
{% elif confirm_variant == 'warning' %}bg-yellow-600 hover:bg-yellow-700 text-white
{% else %}btn-primary{% endif %}">
{{ confirm_text }}
</button>
{% endif %}
</div>
</div>
</div>
</div>
{% endwith %}
{% endwith %}