107 lines
5.6 KiB
Twig
107 lines
5.6 KiB
Twig
{% set weekdays = ['Mo', 'Di', 'Mi', 'Do', 'Fr', 'Sa', 'So'] %}
|
|
{% set visible_per_day = 2 %}
|
|
|
|
<div class="rounded-md border border-gray-200 p-4">
|
|
<div class="flex items-center justify-between pb-4">
|
|
{% if has_prev %}
|
|
<button type="button"
|
|
class="p-1 rounded-md hover:bg-gray-100"
|
|
aria-label="Voriger Monat"
|
|
hx-get="{{ path('app_booking_month', { month: prev_month|date('Y-m') }) }}"
|
|
hx-swap="none">
|
|
{{ ux_icon('lucide:chevron-left', { class: 'w-5 h-5' }) }}
|
|
</button>
|
|
{% else %}
|
|
<span class="p-1 text-gray-300" aria-hidden="true">{{ ux_icon('lucide:chevron-left', { class: 'w-5 h-5' }) }}</span>
|
|
{% endif %}
|
|
|
|
<div class="font-bold">
|
|
{{ month_start|format_datetime(pattern: 'LLLL y') }}
|
|
</div>
|
|
|
|
{% if has_next %}
|
|
<button type="button"
|
|
class="p-1 rounded-md hover:bg-gray-100"
|
|
aria-label="Nächster Monat"
|
|
hx-get="{{ path('app_booking_month', { month: next_month|date('Y-m') }) }}"
|
|
hx-swap="none">
|
|
{{ ux_icon('lucide:chevron-right', { class: 'w-5 h-5' }) }}
|
|
</button>
|
|
{% else %}
|
|
<span class="p-1 text-gray-300" aria-hidden="true"
|
|
title="Weiter voraus kann nicht gebucht werden">{{ ux_icon('lucide:chevron-right', { class: 'w-5 h-5' }) }}</span>
|
|
{% endif %}
|
|
</div>
|
|
|
|
<div class="grid grid-cols-7 gap-1 text-center text-xs text-gray-500 pb-1">
|
|
{% for weekday in weekdays %}<div>{{ weekday }}</div>{% endfor %}
|
|
</div>
|
|
|
|
<div class="grid grid-cols-7 gap-1">
|
|
{% for week in weeks %}
|
|
{% for day in week %}
|
|
{% set classes = 'flex flex-col gap-0.5 rounded-md border p-1 text-left h-16 sm:h-24 overflow-hidden' %}
|
|
{% if not day.in_month %}
|
|
{% set classes = classes ~ ' border-transparent text-gray-300' %}
|
|
{% elseif day.is_past %}
|
|
{% set classes = classes ~ ' border-dashed border-gray-200 text-gray-400' %}
|
|
{% elseif day.is_weekend %}
|
|
{% set classes = classes ~ ' border-transparent bg-gray-50 text-gray-400' %}
|
|
{% else %}
|
|
{% set classes = classes ~ ' border-gray-200' %}
|
|
{% endif %}
|
|
{% if day.is_today %}
|
|
{% set classes = classes ~ ' ring-1 ring-primary' %}
|
|
{% endif %}
|
|
|
|
<div class="{{ classes }}" data-date="{{ day.date|date('Y-m-d') }}">
|
|
<div class="text-xs leading-none">{{ day.date|date('j') }}</div>
|
|
|
|
{% if day.bookings is not empty %}
|
|
<div class="flex flex-wrap gap-0.5 sm:hidden">
|
|
{% for booking in day.bookings %}
|
|
<span class="w-1.5 h-1.5 rounded-full {{ day.is_past ? 'bg-gray-300' : 'bg-primary' }}"></span>
|
|
{% endfor %}
|
|
</div>
|
|
{% endif %}
|
|
|
|
<div class="hidden sm:flex sm:flex-col sm:gap-0.5 sm:min-w-0">
|
|
{% for booking in day.bookings|slice(0, visible_per_day) %}
|
|
<a class="flex items-center gap-1 rounded px-1 py-0.5 text-[10px] leading-tight min-w-0
|
|
{{ day.is_past ? 'bg-gray-100 text-gray-500' : 'bg-primary-bg text-primary-dark hover:bg-primary hover:text-white' }}"
|
|
href="{{ path('app_board', { type: booking.resource.type.value, date: booking.date|date('Y-m-d') }) }}"
|
|
title="{{ booking.resource.type.label }} · {{ booking.resource.label }} · {{ booking.timeRange }}{{ booking.partOfSeries ? ' · wiederkehrend' : '' }}{{ booking.overridden ? ' · abweichend' : '' }}">
|
|
{{ ux_icon(booking.resource.type.icon, { class: 'w-3 h-3 shrink-0' }) }}
|
|
<span class="truncate">
|
|
{{- booking.timeRange.allDay ? booking.resource.label : booking.timeRange.start ~ ' ' ~ booking.resource.label -}}
|
|
</span>
|
|
{% if booking.partOfSeries %}
|
|
{{ ux_icon('lucide:repeat', { class: 'w-2.5 h-2.5 shrink-0 opacity-60' }) }}
|
|
{% endif %}
|
|
{% if booking.overridden %}
|
|
<span class="w-1.5 h-1.5 shrink-0 rounded-full bg-amber-500"></span>
|
|
{% endif %}
|
|
</a>
|
|
{% endfor %}
|
|
|
|
{% if day.bookings|length > visible_per_day %}
|
|
<span class="text-[10px] leading-tight text-gray-500">+{{ day.bookings|length - visible_per_day }} weitere</span>
|
|
{% endif %}
|
|
</div>
|
|
</div>
|
|
{% endfor %}
|
|
{% endfor %}
|
|
</div>
|
|
|
|
<div class="pt-4 text-xs text-gray-500 space-y-1">
|
|
<div class="flex items-center gap-2">
|
|
{{ ux_icon('lucide:repeat', { class: 'w-3 h-3' }) }} Teil einer Wiederholung
|
|
</div>
|
|
<div class="flex items-center gap-2">
|
|
<span class="w-1.5 h-1.5 rounded-full bg-amber-500"></span> Zeit weicht von der Wiederholung ab
|
|
</div>
|
|
<div>gestrichelt = vergangen, nicht mehr buchbar</div>
|
|
<div>Klick auf einen Termin öffnet den Plan des Tages</div>
|
|
</div>
|
|
</div>
|