forked from Ruderverein-Donau-Linz/rowt
first draft of normannen deployment
This commit is contained in:
@ -1,100 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<link rel="stylesheet" href="/public/table.css" />
|
||||
<div class="w-full">
|
||||
<h1 class="h1">Abzeichen für {{ rowingbadge_year }}</h1>
|
||||
<div class="text-black dark:text-white">
|
||||
<table id="basic">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Name</th>
|
||||
<th>Erster Log</th>
|
||||
<th>Letzter Log</th>
|
||||
<th>Gesamt-KM</th>
|
||||
<th>Äquatorpreis (ÄP)</th>
|
||||
<th>
|
||||
ÄP diese
|
||||
<br>
|
||||
Saison bekommen
|
||||
</th>
|
||||
<th>
|
||||
Fahrtenabzeichen (FA)
|
||||
<br>
|
||||
geschafft
|
||||
</th>
|
||||
<th>FA - KM</th>
|
||||
<th>FA - fehlende KM</th>
|
||||
<th>Eintagesausfahrten</th>
|
||||
<th>Mehrtagesausfahrten</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for person in people %}
|
||||
{% set user = person.0 %}
|
||||
{% set achievement = person.1 %}
|
||||
<tr>
|
||||
<td>{{ user.name }}</td>
|
||||
<td>
|
||||
{% if achievement.year_first_mentioned %}{{ achievement.year_first_mentioned }}{% endif %}
|
||||
</td>
|
||||
<td>
|
||||
{% if achievement.year_last_mentioned %}{{ achievement.year_last_mentioned }}{% endif %}
|
||||
</td>
|
||||
<td>{{ achievement.all_time_km }}</td>
|
||||
<td>{{ achievement.curr_equatorprice_name }}</td>
|
||||
<td>
|
||||
{% if achievement.new_equatorprice_this_season %}
|
||||
🎉
|
||||
{% else %}
|
||||
-
|
||||
{% endif %}
|
||||
</td>
|
||||
{% if achievement.rowingbadge %}
|
||||
{% set badge = achievement.rowingbadge %}
|
||||
<td>
|
||||
{% if badge.achieved %}
|
||||
ja
|
||||
{% else %}
|
||||
nein
|
||||
{% endif %}
|
||||
</td>
|
||||
<td>{{ badge.rowed_km }} / {{ badge.required_km }}</td>
|
||||
<td>{{ badge.missing_km }}</td>
|
||||
<td>
|
||||
<details>
|
||||
<summary>
|
||||
> {{ badge.single_day_trips_required_distance }} km: {{ badge.single_day_trips_over_required_distance | length }} / 2
|
||||
</summary>
|
||||
{% for log in badge.single_day_trips_over_required_distance %}
|
||||
{{ log::show_old(log=log, state="completed", only_ones=false, index=loop.index, hide_type=true) }}
|
||||
{% endfor %}
|
||||
</details>
|
||||
</td>
|
||||
<td>
|
||||
<details>
|
||||
<summary>
|
||||
> {{ badge.multi_day_trips_required_distance }} km: {{ badge.multi_day_trips_over_required_distance | length }} / 1
|
||||
</summary>
|
||||
{% for log in badge.multi_day_trips_over_required_distance %}
|
||||
{{ log::show_old(log=log, state="completed", only_ones=false, index=loop.index, hide_type=true) }}
|
||||
{% endfor %}
|
||||
</details>
|
||||
</td>
|
||||
{% else %}
|
||||
<td>Geb.datum fehlt 👻</td>
|
||||
<td>Geb.datum fehlt 👻</td>
|
||||
<td>Geb.datum fehlt 👻</td>
|
||||
<td>Geb.datum fehlt 👻</td>
|
||||
<td>Geb.datum fehlt 👻</td>
|
||||
{% endif %}
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
<script src="/public/jstable.min.js"></script>
|
||||
<script src="/public/table.js"></script>
|
||||
{% endblock content %}
|
@ -1,10 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/boat" as boat %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Boats</h1>
|
||||
{{ boat::new() }}
|
||||
{% for boat in boats %}{{ boat::edit(boat=boat, uuid=loop.index) }}{% endfor %}
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,11 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">List</h1>
|
||||
<form action="/admin/list" method="post">
|
||||
<textarea name="list" rows="4" cols="50"></textarea>
|
||||
<input type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,10 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">List - Result</h1>
|
||||
<ol>
|
||||
{% for person in result %}<li>{{ person }}</li>{% endfor %}
|
||||
</ol>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,27 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/boat" as boat %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full dark:text-white">
|
||||
<h1 class="h1">Mail</h1>
|
||||
<div class="grid ">
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Mail versenden</h2>
|
||||
<form action="/admin/mail"
|
||||
method="post"
|
||||
enctype="multipart/form-data"
|
||||
class="grid gap-3 p-3">
|
||||
{{ macros::select(label="Gruppe", data=roles, name="role_id") }}
|
||||
{{ macros::input(label="Betreff", name="subject", type="text", required=true) }}
|
||||
<div class="">
|
||||
<label for="content" class=" text-sm text-gray-600 dark:text-white ">Inhalt</label>
|
||||
<textarea id="content" name="body" rows="4" cols="50" class="input rounded-md"></textarea>
|
||||
</div>
|
||||
<input type="file" name="files" multiple />
|
||||
<input type="submit" class="btn btn-primary" value="Abschicken" />
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,38 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Schnupper Verwaltung</h1>
|
||||
<div class="grid gap-3">
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5">
|
||||
<h2 class="h2">Angemeldete Personen: {{ schnupperanten | length }}</h2>
|
||||
<ol>
|
||||
{% for user in schnupperanten %}
|
||||
<li class="border-t border-gray-200 dark:border-primary-600 px-3 py-1">
|
||||
<span class="flex items-center justify-between">
|
||||
<span>
|
||||
<span class="status-damage status-damage-{% if "paid" in user.roles %}none {% else %}locked {% endif %}"></span> {{ user.name }} ({{ user.mail }}
|
||||
{%- if user.notes %} | {{ user.notes }}
|
||||
{% endif -%}
|
||||
)
|
||||
</span>
|
||||
<a class="btn btn-primary"
|
||||
href="/admin/user/move/schnupperant/{{ user.id }}/to/scheckbuch"
|
||||
onclick="return confirm('Willst du wirklich ein Scheckbuch erstellen? Die Person erhält ein Mail mit allen Infos.')">Zu Scheckbuch umwandeln</a>
|
||||
</span>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ol>
|
||||
</div>
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5">
|
||||
<h2 class="h2">Legende</h2>
|
||||
<div class="px-3 py-1">
|
||||
<span class="status-damage status-damage-none"></span> Bezahlt - Juhuuu!
|
||||
</div>
|
||||
<div class="px-3 py-1">
|
||||
<span class="status-damage status-damage-locked"></span> Noch nicht bezahlt
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,43 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Gebühren</h1>
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Namen..." />
|
||||
</div>
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
<div class="border-r border-l border-gray-200 dark:border-primary-600">
|
||||
{% for fee in fees | sort(attribute="name") %}
|
||||
<div class="border-t border-gray-200 dark:border-primary-600 {% if fee.paid %}bg-[#15803d] text-white {% else %} bg-white dark:bg-primary-900 text-black dark:text-white {% endif %} flex justify-between items-center px-3 py-1 "
|
||||
data-filterable="true"
|
||||
data-filter="{{ fee.name }} {% if fee.paid %} has-already-paid {% else %} has-not-paid {% endif %}"
|
||||
class="bg-white dark:bg-primary-900 p-3 rounded-md w-full">
|
||||
<div class="grid md:grid-cols-3 gap-3 w-full py-3">
|
||||
<div>
|
||||
<strong>{{ fee.name }}</strong>
|
||||
<span class="block">{{ fee.sum_in_cents / 100 }}€</span>
|
||||
</div>
|
||||
<div>
|
||||
{% for p in fee.parts %}
|
||||
{{ p.0 }} ({{ p.1 / 100 }}€)
|
||||
{% if not loop.last %}+{% endif %}
|
||||
{% endfor %}
|
||||
</div>
|
||||
{% if "admin" in loggedin_user.roles or "kassier" in loggedin_user.roles %}
|
||||
<div class="text-end">
|
||||
<a href="/admin/user/fees/paid?{{ fee.user_ids }}"
|
||||
class="btn btn-primary">Zahlungsstatus ändern</a>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -2,13 +2,13 @@
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Users</h1>
|
||||
<h1 class="h1">Mitgliederverwaltung</h1>
|
||||
{% if allowed_to_edit %}
|
||||
<form action="/admin/user/new"
|
||||
method="post"
|
||||
class="mt-4 bg-primary-900 rounded-md text-white px-3 pb-3 pt-2 sm:flex items-end justify-between">
|
||||
<div class="w-full">
|
||||
<h2 class="text-md font-bold mb-2 uppercase tracking-wide">Neuen User hinzufügen</h2>
|
||||
<h2 class="text-md font-bold mb-2 uppercase tracking-wide">Neues Mitglied hinzufügen</h2>
|
||||
<div class="grid md:grid-cols-3">
|
||||
<div>
|
||||
<label for="name" class="sr-only">Name</label>
|
||||
@ -33,13 +33,13 @@
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach (Name, [yes|no]-role:<name>, has-[no-]membership-pdf)" />
|
||||
placeholder="Suchen nach (Name, [yes|no]-role:<name>" />
|
||||
</div>
|
||||
<!-- END filterBar -->
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
{% for user in users %}
|
||||
<div data-filterable="true"
|
||||
data-filter="{{ user.name }} {% for role in roles %} {% if role.name in user.roles %} yes-role:{{ role.name }} {% else %} no-role:{{ role.name }} {% endif %} role-{{ role }} {% endfor %} {% if user.membership_pdf %}has-membership-pdf{% else %}has-no-membership-pdf{% endif %}"
|
||||
data-filter="{{ user.name }} {% for role in roles %} {% if role.name in user.roles %} yes-role:{{ macros::fancy_role_name(name=role.name) }} {% else %} no-role:{{ role.name }} {% endif %} role-{{ role }} {% endfor %}"
|
||||
class="border-t bg-white dark:bg-primary-900 py-3 px-4 relative">
|
||||
<details class="block dark:text-white w-full">
|
||||
<summary>
|
||||
@ -52,15 +52,14 @@
|
||||
enctype="multipart/form-data"
|
||||
class="inline">
|
||||
• <a class="font-normal text-primary-600 dark:text-primary-200 hover:text-primary-900 dark:hover:text-primary-300 underline"
|
||||
href="/admin/user/{{ user.id }}/send-welcome-mail"
|
||||
onclick="return confirm('Willst du wirklich das Willkommensmail an {{ user.name }} ausschicken?');">Willkommensmail verschicken</a>
|
||||
onclick="return confirm('Demo aktiv, nun würde der Benutzer eine Mail bekommen mit der Info wie er ruad.at verwendet.');">Willkommensmail verschicken</a>
|
||||
</form>
|
||||
{% endif %}
|
||||
{% if user.last_access %}• ⏳ {{ user.last_access | date }}{% endif %}
|
||||
{% if user.last_access %}• Zuletzt eingeloggt: {{ user.last_access | date() }}{% endif %}
|
||||
</span>
|
||||
<small class="block text-gray-600 dark:text-gray-100">
|
||||
{% for role in user.roles -%}
|
||||
{{ role }}
|
||||
{{ macros::fancy_role_name(name=role) }}
|
||||
{%- if not loop.last %},
|
||||
{% endif -%}
|
||||
{% endfor %}
|
||||
@ -79,59 +78,14 @@
|
||||
<div class="w-full grid gap-3 mt-3">
|
||||
<input type="hidden" name="id" value="{{ user.id }}" />
|
||||
<div class="grid sm:grid-cols-2 lg:grid-cols-4 gap-3">
|
||||
{% for cluster, cluster_roles in roles | group_by(attribute="cluster") %}
|
||||
<label for="cluster_{{ loop.index }}">{{ cluster }}</label>
|
||||
{# Determine the initially selected role within the cluster #}
|
||||
{% set_global selected_role_id = "none" %}
|
||||
{% for role in cluster_roles %}
|
||||
{% if selected_role_id == "none" and role.name in user.roles %}
|
||||
{% set_global selected_role_id = role.id %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{# Set default name to the selected role ID or first role if none selected #}
|
||||
<select id="cluster_{{ loop.index }}"
|
||||
{% if selected_role_id == 'none' %} {% else %} name="roles[{{ selected_role_id }}]" {% endif %}
|
||||
{% if allowed_to_edit == false %}disabled{% endif %}
|
||||
onchange=" if (this.value === '') { this.removeAttribute('name'); } else { this.name = 'roles[' + this.options[this.selectedIndex].getAttribute('data-role-id') + ']'; }">
|
||||
<option value=""
|
||||
data-role-id="none"
|
||||
{% if selected_role_id == 'none' %}selected="selected"{% endif %}>
|
||||
None
|
||||
</option>
|
||||
{% for role in cluster_roles %}
|
||||
<option value="on"
|
||||
data-role-id="{{ role.id }}"
|
||||
{% if role.id == selected_role_id %}selected="selected"{% endif %}>
|
||||
{{ role.name }}
|
||||
</option>
|
||||
{% endfor %}
|
||||
</select>
|
||||
{% endfor %}
|
||||
{% for role in roles %}
|
||||
{% if not role.cluster %}
|
||||
{{ macros::checkbox(label=role.name, name="roles[" ~ role.id ~ "]", id=loop.index , checked=role.name in user.roles, disabled=allowed_to_edit == false) }}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
<hr class="sm:col-span-2 lg:col-span-4 my-3" />
|
||||
{% if user.membership_pdf %}
|
||||
<a href="/admin/user/{{ user.id }}/membership"
|
||||
class="text-black dark:text-white">Beitrittserklärung herunterladen</a>
|
||||
{% else %}
|
||||
{{ macros::input(label='Beitrittserklärung', name='membership_pdf', id=loop.index, type="file", readonly=allowed_to_edit == false, accept='application/pdf') }}
|
||||
{% endif %}
|
||||
{{ macros::input(label='DOB', name='dob', id=loop.index, type="text", value=user.dob, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Weight (kg)', name='weight', id=loop.index, type="text", value=user.weight, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Sex', name='sex', id=loop.index, type="text", value=user.sex, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Mitglied seit', name='member_since_date', id=loop.index, type="text", value=user.member_since_date, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Geburtsdatum', name='birthdate', id=loop.index, type="text", value=user.birthdate, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Mail', name='mail', id=loop.index, type="text", value=user.mail, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Nickname', name='nickname', id=loop.index, type="text", value=user.nickname, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Notizen', name='notes', id=loop.index, type="text", value=user.notes, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Telefon', name='phone', id=loop.index, type="text", value=user.phone, readonly=allowed_to_edit == false) }}
|
||||
{{ macros::input(label='Adresse', name='address', id=loop.index, type="text", value=user.address, readonly=allowed_to_edit == false) }}
|
||||
{% if allowed_to_edit %}
|
||||
{{ macros::select(label="Familie", data=families, name='family_id', selected_id=user.family_id, display=['names'], default="Keine Familie", new_last_entry='Neue Familie anlegen') }}
|
||||
{% endif %}
|
||||
{{ macros::input(label='Name', name='name', id=loop.index, type="text", value=user.name) }}
|
||||
{{ macros::input(label='Mail', name='mail', id=loop.index, type="text", value="Demo Version: Mails deaktiviert", readonly=true) }}
|
||||
</div>
|
||||
</div>
|
||||
{% if allowed_to_edit %}
|
||||
|
@ -1,70 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5">
|
||||
<h1 class="h1">Scheckbücher</h1>
|
||||
<form action="/admin/user/new/scheckbuch"
|
||||
method="post"
|
||||
class="mt-4 bg-primary-900 rounded-md text-white px-3 pb-3 pt-2 sm:flex items-end justify-between">
|
||||
<div class="w-full">
|
||||
<h2 class="text-md font-bold mb-2 uppercase tracking-wide">Neues Scheckbuch hinzufügen</h2>
|
||||
<div class="grid md:grid-cols-3">
|
||||
<div>
|
||||
<label for="name" class="sr-only">Name</label>
|
||||
<input type="text"
|
||||
name="name"
|
||||
class="relative block rounded-md border-0 py-1.5 px-2 text-gray-900 ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-primary-600 sm:text-sm sm:leading-6 mb-2 md:mb-0"
|
||||
placeholder="Name" />
|
||||
</div>
|
||||
<div>
|
||||
<label for="name" class="sr-only">Mail</label>
|
||||
<input type="mail"
|
||||
name="mail"
|
||||
class="relative block rounded-md border-0 py-1.5 px-2 text-gray-900 ring-1 ring-inset ring-gray-300 placeholder:text-gray-400 focus:ring-2 focus:ring-inset focus:ring-primary-600 sm:text-sm sm:leading-6 mb-2 md:mb-0"
|
||||
placeholder="Mail" />
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="text-right">
|
||||
<input value="Hinzufügen"
|
||||
type="submit"
|
||||
class="w-28 mt-2 sm:mt-0 rounded-md bg-primary-500 px-3 py-2 text-sm font-semibold text-white hover:bg-primary-500 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-600 cursor-pointer" />
|
||||
</div>
|
||||
</form>
|
||||
<!-- START filterBar -->
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Name" />
|
||||
</div>
|
||||
<!-- END filterBar -->
|
||||
<div class="bg-primary-100 dark:bg-primary-950 p-3 rounded-b-md grid gap-4">
|
||||
<div id="filter-result-js"
|
||||
class="text-primary-950 dark:text-white text-right"></div>
|
||||
{% for scheckbook in scheckbooks %}
|
||||
{% set user = scheckbook.1 %}
|
||||
{% set trips = scheckbook.0 %}
|
||||
<div {% if "paid" in user.roles %}style="background-color: green;"{% endif %}
|
||||
data-filterable="true"
|
||||
data-filter="{{ user.name }} {% if "paid" in user.roles %} has-already-paid {% else %} has-not-paid {% endif %}"
|
||||
class="bg-white dark:bg-primary-900 p-3 rounded-md w-full">
|
||||
<div class="grid sm:grid-cols-1 gap-3">
|
||||
<div style="width: 100%" class="col-span-2">
|
||||
<b>{{ user.name }} - Ausfahrten: {{ trips | length }}</b>
|
||||
{% for trip in trips %}
|
||||
<li>{{ log::show_old(log=trip, state="completed", only_ones=false, index=loop.index) }}</li>
|
||||
{% endfor %}
|
||||
</div>
|
||||
{% if "admin" in loggedin_user.roles or "kassier" in loggedin_user.roles %}
|
||||
<a href="/admin/user/fees/paid?user_ids[]={{ user.id }}">Zahlungsstatus ändern</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -2,9 +2,6 @@
|
||||
{% block content %}
|
||||
<div class="w-full max-w-md space-y-8">
|
||||
<div>
|
||||
<img class="mx-auto h-16 w-auto"
|
||||
src="https://rudernlinz.at/wp-content/uploads/2021/02/cropped-logo.png"
|
||||
alt="Logo Ruderassistent">
|
||||
<h1 class="mt-6 h1">Ruderassistent</h1>
|
||||
</div>
|
||||
{% if flash %}{{ macros::alert(message=flash.1, type=flash.0, class="sm:col-span-2 lg:col-span-3") }}{% endif %}
|
||||
|
@ -1,106 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Bootschäden</h1>
|
||||
<h2 class="text-md font-bold tracking-wide bg-primary-900 mt-3 p-3 text-white flex justify-between items-center rounded-md">
|
||||
Neuen Schaden
|
||||
<a href="#"
|
||||
class="inline-flex justify-center rounded-md bg-primary-600 mx-1 px-3 py-2 text-sm font-semibold text-white hover:bg-primary-500 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-600 cursor-pointer"
|
||||
data-sidebar="true"
|
||||
data-trigger="sidebar"
|
||||
data-header="Neuen Schaden anlegen"
|
||||
data-body="#new-damage">
|
||||
{% include "includes/plus-icon" %}
|
||||
<span class="sr-only">Neuen Schaden eintragen</span>
|
||||
</a>
|
||||
</h2>
|
||||
<div class="hidden">
|
||||
<div id="new-damage">
|
||||
<form action="/boatdamage" method="post" class="grid gap-3">
|
||||
{{ log::boat_select(only_ones=false, id='boat') }}
|
||||
{% if not loggedin_user %}{{ macros::select(label='Gemeldet von', data=user, name='user_id') }}{% endif %}
|
||||
{{ macros::input(label='Beschreibung des Schadens', name='desc', type='text', required=true, wrapper_class='col-span-4') }}
|
||||
<div class="col-span-4">
|
||||
{{ macros::checkbox(label='Boot sperren', name='lock_boat', type='text', required=true) }}
|
||||
</div>
|
||||
<input type="submit"
|
||||
class="btn btn-primary w-full col-span-4"
|
||||
value="Schaden eintragen" />
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Namen...">
|
||||
</div>
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
{% for boatdamage in boatdamages | sort(attribute="verified") %}
|
||||
<div data-filterable="true"
|
||||
data-filter="{{ boatdamage.boat.name }} {{ boatdamage.user_created.name }}"
|
||||
class="w-full border-t bg-white dark:bg-primary-900 text-black dark:text-white p-3 {% if boatdamage.verified_at %}opacity-50{% endif %}">
|
||||
<div class="w-full">
|
||||
<strong>{{ boatdamage.created_at | date(format='%d.%m.%Y') }} <span class="font-normal text-gray-600 dark:text-gray-100">({{ boatdamage.boat.name }})</span></strong>
|
||||
{% if boatdamage.boat.damage %}
|
||||
<small class="block text-gray-600 dark:text-gray-100">(Boot gesperrt)</small>
|
||||
{% endif %}
|
||||
<div>{{ boatdamage.desc }}</div>
|
||||
<small class="block text-gray-600 dark:text-gray-100">
|
||||
Schaden eingetragen von {{ boatdamage.user_created.name }} am/um {{ boatdamage.created_at | date(format='%d.%m.%Y (%H:%M)') }}
|
||||
</small>
|
||||
{% if boatdamage.fixed_at %}
|
||||
<small class="block text-gray-600 dark:text-gray-100">Repariert von {{ boatdamage.user_fixed.name }} am/um {{ boatdamage.fixed_at | date(format='%d.%m.%Y (%H:%M)') }}</small>
|
||||
{% else %}
|
||||
{% if loggedin_user and loggedin_user.allowed_to_steer %}
|
||||
<form action="/boatdamage/{{ boatdamage.id }}/fixed"
|
||||
method="post"
|
||||
class="flex justify-between mt-3">
|
||||
<input type="text"
|
||||
name="desc"
|
||||
value="{{ boatdamage.desc }}"
|
||||
class="grow input rounded-s" />
|
||||
{% if loggedin_user and "tech" in loggedin_user.roles %}
|
||||
<input type="submit"
|
||||
class="btn btn-primary"
|
||||
style="border-top-left-radius: 0;
|
||||
border-bottom-left-radius: 0"
|
||||
value="Repariert und verifiziert" />
|
||||
{% else %}
|
||||
<input type="submit"
|
||||
class="btn btn-primary"
|
||||
style="border-top-left-radius: 0;
|
||||
border-bottom-left-radius: 0"
|
||||
value="Repariert" />
|
||||
{% endif %}
|
||||
</form>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% if boatdamage.verified_at %}
|
||||
<small class="block text-gray-600 dark:text-gray-100">Verifiziert von {{ boatdamage.user_verified.name }} am/um {{ boatdamage.verified_at | date(format='%d.%m.%Y (%H:%M)') }}</small>
|
||||
{% else %}
|
||||
{% if loggedin_user and "tech" in loggedin_user.roles and boatdamage.fixed_at %}
|
||||
<form action="/boatdamage/{{ boatdamage.id }}/verified"
|
||||
method="post"
|
||||
class="flex justify-between mt-3">
|
||||
<input type="text"
|
||||
name="desc"
|
||||
value="{{ boatdamage.desc }}"
|
||||
class="grow input rounded-s" />
|
||||
<input type="submit"
|
||||
class="btn btn-dark"
|
||||
style="border-top-left-radius: 0;
|
||||
border-bottom-left-radius: 0"
|
||||
value="Verifiziert" />
|
||||
</form>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,98 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Bootsreservierungen</h1>
|
||||
<h2 class="text-md font-bold tracking-wide bg-primary-900 mt-3 p-3 text-white flex justify-between items-center rounded-md">
|
||||
Neue Reservierung
|
||||
<a href="#"
|
||||
class="inline-flex justify-center rounded-md bg-primary-600 mx-1 px-3 py-2 text-sm font-semibold text-white hover:bg-primary-500 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-600 cursor-pointer"
|
||||
data-sidebar="true"
|
||||
data-trigger="sidebar"
|
||||
data-header="Neue Reservierung anlegen"
|
||||
data-body="#new-reservation">
|
||||
{% include "includes/plus-icon" %}
|
||||
<span class="sr-only">Neue Reservierung eintragen</span>
|
||||
</a>
|
||||
</h2>
|
||||
<div class="hidden">
|
||||
<div id="new-reservation">
|
||||
<form action="/boatreservation/new" method="post" class="grid gap-3">
|
||||
{{ log::boat_select(only_ones=false, id='boat') }}
|
||||
{% if not loggedin_user %}{{ macros::select(label='Reserviert von', data=user, name='user_id_applicant') }}{% endif %}
|
||||
{{ macros::input(label='Beginn', name='start_date', type='date', required=true, wrapper_class='col-span-4') }}
|
||||
{{ macros::input(label='Ende', name='end_date', type='date', required=true, wrapper_class='col-span-4') }}
|
||||
{{ macros::input(label='Uhrzeit (zB ab 14:00 Uhr, ganztägig, ...)', name='time_desc', type='text', required=true, wrapper_class='col-span-4') }}
|
||||
{{ macros::input(label='Zweck (Wanderfahrt, ...)', name='usage', type='text', required=true, wrapper_class='col-span-4') }}
|
||||
<input type="submit"
|
||||
class="btn btn-primary w-full col-span-4"
|
||||
value="Reservierung eintragen" />
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Namen...">
|
||||
</div>
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
{% for reservation in boatreservations %}
|
||||
{% set allowed_to_edit = false %}
|
||||
{% if loggedin_user %}
|
||||
{% if loggedin_user.id == reservation.user_applicant.id or "admin" in loggedin_user.roles %}
|
||||
{% set allowed_to_edit = true %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
<div data-filterable="true"
|
||||
data-filter="{{ reservation.user_applicant.name }} {{ reservation.boat.name }}"
|
||||
class="w-full border-t bg-white dark:bg-primary-900 text-black dark:text-white p-3">
|
||||
<div class="w-full">
|
||||
<strong>Boot:</strong>
|
||||
{{ reservation.boat.name }}
|
||||
<br />
|
||||
<strong>Reservierung:</strong>
|
||||
{{ reservation.user_applicant.name }}
|
||||
<br />
|
||||
<strong>Datum:</strong>
|
||||
{{ reservation.start_date }}
|
||||
{% if reservation.end_date != reservation.start_date %}
|
||||
-
|
||||
{{ reservation.end_date }}
|
||||
{% endif %}
|
||||
<br />
|
||||
{% if not allowed_to_edit %}
|
||||
<strong>Uhrzeit:</strong>
|
||||
{{ reservation.time_desc }}
|
||||
<br />
|
||||
<strong>Zweck:</strong>
|
||||
{{ reservation.usage }}
|
||||
{% endif %}
|
||||
{% if allowed_to_edit %}
|
||||
<form action="/boatreservation"
|
||||
method="post"
|
||||
class="bg-white dark:bg-primary-900 pt-3 rounded-md w-full">
|
||||
<div class="w-full grid gap-3">
|
||||
<input type="hidden" name="id" value="{{ reservation.id }}" />
|
||||
{{ macros::input(label='Uhrzeit', name='time_desc', id=loop.index, type="text", value=reservation.time_desc, readonly=false) }}
|
||||
{{ macros::input(label='Zweck', name='usage', id=loop.index, type="text", value=reservation.usage, readonly=false) }}
|
||||
</div>
|
||||
<div class="mt-3 text-right">
|
||||
<a href="/boatreservation/{{ reservation.id }}/delete"
|
||||
class="w-28 btn btn-alert"
|
||||
onclick="return confirm('Willst du diese Reservierung wirklich löschen?');">
|
||||
{% include "includes/delete-icon" %}
|
||||
Löschen
|
||||
</a>
|
||||
<input value="Ändern" type="submit" class="w-28 btn btn-primary ml-1" />
|
||||
</div>
|
||||
</form>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,39 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Aktuelle Woche</h1>
|
||||
<details>
|
||||
<summary>Dirty Thirty</summary>
|
||||
<p>
|
||||
<div class="border-r border-l">
|
||||
<textarea style="width: 100%; height: 300px;">
|
||||
{%- for stat in thirty %}
|
||||
{%- set names = stat.name | split(pat=" ") %}{% set lastname_index = names | length - 1 %}{% set lastname = names[lastname_index] %}{{ lastname }}	
|
||||
{%- for name in names -%}
|
||||
{% if loop.index != lastname_index +1 %}{{ name }}{% endif %}
|
||||
{%- endfor -%}
|
||||
	{{ stat.dob }}	{{ stat.weight }}	{{ stat.sex }}		DLI	{{ stat.result }}
|
||||
{%- endfor -%}
|
||||
</textarea>
|
||||
</div>
|
||||
</p>
|
||||
</details>
|
||||
<details>
|
||||
<summary>Dirty Dozen</summary>
|
||||
<p>
|
||||
<div class="border-r border-l">
|
||||
<textarea style="width: 100%; height: 300px;">
|
||||
{%- for stat in dozen -%}
|
||||
{%- set names = stat.name | split(pat=" ") %}{% set lastname_index = names | length - 1 %}{% set lastname = names[lastname_index] %}{{ lastname }}	
|
||||
{%- for name in names -%}
|
||||
{% if loop.index != lastname_index +1 %}{{ name }}{% endif %}
|
||||
{%- endfor -%}
|
||||
	{{ stat.dob }}	{{ stat.weight }}	{{ stat.sex }}		DLI	{{ stat.result }}
|
||||
{%- endfor -%}
|
||||
</textarea>
|
||||
</div>
|
||||
</p>
|
||||
</details>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,241 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Ergo Challenges</h1>
|
||||
<div class="grid gap-3">
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Ergo Challenge?!</h2>
|
||||
<div class="p-3">
|
||||
<ul class="list-disc ms-2">
|
||||
<li class="py-1">
|
||||
<a href="https://rudernlinz.at/termin"
|
||||
target="_blank"
|
||||
class="link-primary">Überblick der Challenges</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
Eintragung ist jederzeit möglich, alle Daten die bis Sonntag 23:59 hier hochgeladen wurden, werden gesammelt an die Ister Ergo Challenge geschickt
|
||||
<li class="py-1">
|
||||
Montag → gemeinsames Training; bitte um <a href="/planned" class="link-primary">Anmeldung</a>, damit jeder einen Ergo hat
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="https://data.ergochallenge.at"
|
||||
target="_blank"
|
||||
style="text-decoration: underline">Offizielle Ergebnisse</a>, bei Fehlern direkt mit <a href="mailto:office@ergochallenge.at"
|
||||
style="text-decoration: underline">Christian (Ister)</a> Kontakt aufnehmen
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
<details class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md p-2">
|
||||
<summary class="cursor-pointer">
|
||||
<strong>Um was geht es bei den Ergochallenges?</strong>
|
||||
</summary>
|
||||
<p class="py-2 ">
|
||||
Der Linzer Verein Ister veranstaltet seit einigen Jahren zwei Challenges im Winter, ‘Dirty Thirty’ (6x im Winter) und ‘Dirty Dozen’ (12 Wochen lang).
|
||||
<ul class="list-decimal ms-4">
|
||||
<li class="py-1">
|
||||
Bei <strong>Dirty Thirty</strong> geht es darum so viele Kilometer wie möglich in 30 Minuten zu fahren.
|
||||
</li>
|
||||
<li class="py-1">
|
||||
Bei <strong>Dirty Dozen</strong> werden jede Woche neue Ziele ausgeschrieben, gestartet wird mit einem Halbmarathon und es geht runter bis auf 100m.
|
||||
</li>
|
||||
</ul>
|
||||
<p class="py-2">
|
||||
Ihr könnt gerne bei allen Challenges mitmachen und es ist möglich jederzeit ein- bzw. auszusteigen. Für alle komplett neuen Teilnehmer würde ich allerdings empfehlen die ersten beiden Dirty Dozen Challenges (Halbmarathon und 16 Kilometer) auszulassen und es am Anfang etwas ruhiger anzugehen. Es steht der Spaß und die Festigung der Technik im Vordergrund, nicht Rekorde.
|
||||
</p>
|
||||
<strong>Video Tipps 🐞</strong>
|
||||
<ul class="list-disc ms-3">
|
||||
<li class="py-1">
|
||||
<a href="https://www.youtube.com/watch?v=TJsQPV6LNPI"
|
||||
target="_blank"
|
||||
style="text-decoration: underline">Intro</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="https://www.youtube.com/watch?v=VE663Kg0c00"
|
||||
target="_blank"
|
||||
style="text-decoration: underline">Grundlagen</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="https://www.youtube.com/watch?v=KOacKLOpWkI"
|
||||
target="_blank"
|
||||
style="text-decoration: underline">Schlagaufbau</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="https://www.youtube.com/watch?v=m6VP11EDjcM"
|
||||
target="_blank"
|
||||
style="text-decoration: underline">PM5 Monitor</a>
|
||||
</li>
|
||||
</ul>
|
||||
</details>
|
||||
<details class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md p-2">
|
||||
<summary class="cursor-pointer">
|
||||
<strong>Deine Daten</strong>
|
||||
</summary>
|
||||
<div class="pt-3">
|
||||
<p>
|
||||
Folgende Daten hat der Ruderassistent von dir. Wenn diese nicht mehr aktuell sind, bitte gewünschte Änderungen an Philipp melden (Tel. nr siehe Signal, oder an <a href="mailto:it@rudernlinz.at"
|
||||
class="text-primary-600 dark:text-primary-200 hover:text-primary-950 hover:dark:text-primary-300 underline"
|
||||
target="_blank">it@rudernlinz.at</a>).
|
||||
<br />
|
||||
<br />
|
||||
<ul>
|
||||
<li>Geburtsdatum: {{ loggedin_user.dob }}</li>
|
||||
<li>Gewicht: {{ loggedin_user.weight }} kg</li>
|
||||
<li>Geschlecht: {{ loggedin_user.sex }}</li>
|
||||
</ul>
|
||||
</p>
|
||||
</div>
|
||||
</details>
|
||||
</div>
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow grid gap-3">
|
||||
<h2 class="h2">
|
||||
Neuer Eintrag
|
||||
</h1>
|
||||
<details class="p-2">
|
||||
<summary class="cursor-pointer">Dirty Thirty</summary>
|
||||
<div class="mt-3">
|
||||
<form action="/ergo/thirty"
|
||||
class="grid gap-3"
|
||||
method="post"
|
||||
enctype="multipart/form-data">
|
||||
<div>
|
||||
<label for="user-thirty" class="text-sm text-gray-600 dark:text-gray-100">Ergo-Fahrer</label>
|
||||
<select name="user" id="user-thirty" class="input rounded-md">
|
||||
<option disabled="disabled">User auswählen</option>
|
||||
{% for user in users %}
|
||||
{% if user.id == loggedin_user.id %}
|
||||
<option value="{{ user.id }}" selected="selected">{{ user.name }}</option>
|
||||
{% else %}
|
||||
<option value="{{ user.id }}">{{ user.name }}</option>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</select>
|
||||
</div>
|
||||
{{ macros::input(label="Distanz [m]", name="result", required=true, type="number", class="input rounded-md") }}
|
||||
<div>
|
||||
<label for="file-thirty" class="text-sm text-gray-600 dark:text-gray-100">Ergebnis-Foto vom Ergo-Display</label>
|
||||
<input type="file"
|
||||
id="file-thirty"
|
||||
name="proof"
|
||||
class="input rounded-md"
|
||||
accept="image/*">
|
||||
</div>
|
||||
<div class="text-end">
|
||||
<input type="submit" value="Speichern" class="btn btn-primary btn-fw m-auto" />
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</details>
|
||||
<details class="p-2">
|
||||
<summary class="cursor-pointer">Dirty Dozen</summary>
|
||||
<div class="mt-3">
|
||||
<form action="/ergo/dozen"
|
||||
class="grid gap-3"
|
||||
method="post"
|
||||
enctype="multipart/form-data">
|
||||
<div>
|
||||
<label for="user-dozen" class="text-sm text-gray-600 dark:text-gray-100">Ergo-Fahrer</label>
|
||||
<select name="user" id="user-dozen" class="input rounded-md">
|
||||
<option disabled="disabled">User auswählen</option>
|
||||
{% for user in users %}
|
||||
{% if user.id == loggedin_user.id %}
|
||||
<option value="{{ user.id }}" selected="selected">{{ user.name }}</option>
|
||||
{% else %}
|
||||
<option value="{{ user.id }}">{{ user.name }}</option>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</select>
|
||||
</div>
|
||||
{{ macros::input(label="Zeit [hh:mm:ss.s] oder Distanz [m]", name="result", required=true, type="text", class="input rounded-md", pattern="(?:\d+:\d{2}:\d{2}\.\d+|\d{1,2}:\d{2}\.\d+|\d+(\.\d+)?)") }}
|
||||
<div>
|
||||
<label for="file-dozen" class="text-sm text-gray-600 dark:text-gray-100">Ergebnis-Foto vom Ergo-Display</label>
|
||||
<input type="file"
|
||||
id="file-dozen"
|
||||
name="proof"
|
||||
class="input rounded-md"
|
||||
accept="image/*">
|
||||
</div>
|
||||
<div class="text-end">
|
||||
<input type="submit" value="Speichern" class="btn btn-primary btn-fw m-auto" />
|
||||
</div>
|
||||
</form>
|
||||
</div>
|
||||
</details>
|
||||
</div>
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow grid gap-3">
|
||||
<h2 class="h2">Aktuelle Woche</h2>
|
||||
<details class="p-2">
|
||||
<summary class="cursor-pointer">
|
||||
Dirty Thirty <small class="text-gray-600 dark:text-white">({{ thirty | length }})</small>
|
||||
</summary>
|
||||
<div class="mt-3">
|
||||
<ol>
|
||||
{% for stat in thirty %}
|
||||
<li>
|
||||
<strong>{{ stat.name }}:</strong> {{ stat.result }}
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ol>
|
||||
</div>
|
||||
</details>
|
||||
<details class="p-2">
|
||||
<summary class="cursor-pointer">
|
||||
Dirty Dozen <small class="text-gray-600 dark:text-white">({{ dozen | length }})</small>
|
||||
</summary>
|
||||
<div class="mt-3">
|
||||
<ol>
|
||||
{% for stat in dozen %}
|
||||
<li>
|
||||
<strong>{{ stat.name }}:</strong> {{ stat.result }}
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ol>
|
||||
</div>
|
||||
</details>
|
||||
</div>
|
||||
{% if "admin" in loggedin_user.roles %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow grid gap-3">
|
||||
<h2 class="h2">Update</h2>
|
||||
<details class="p-2">
|
||||
<summary class="cursor-pointer">
|
||||
Dirty Thirty <small class="text-gray-600 dark:text-white">({{ thirty | length }})</small>
|
||||
</summary>
|
||||
<div class="mt-3">
|
||||
<ol>
|
||||
{% for stat in thirty %}
|
||||
<li>
|
||||
<form action="/ergo/thirty/user/{{ stat.id }}/new" method="get">
|
||||
{{ stat.name }}:
|
||||
<input type="text" value="{{ stat.result }}" name="new" style="color: black" />
|
||||
<input type="submit" />
|
||||
</form>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ol>
|
||||
</div>
|
||||
</details>
|
||||
<details class="p-2">
|
||||
<summary class="cursor-pointer">
|
||||
Dirty Dozen <small class="text-gray-600 dark:text-white">({{ dozen | length }})</small>
|
||||
</summary>
|
||||
<div class="mt-3">
|
||||
<ol>
|
||||
{% for stat in dozen %}
|
||||
<li>
|
||||
<form action="/ergo/dozen/user/{{ stat.id }}/new" method="get">
|
||||
{{ stat.name }}:
|
||||
<input type="text" value="{{ stat.result }}" name="new" style="color: black" />
|
||||
<input type="submit" />
|
||||
</form>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ol>
|
||||
</div>
|
||||
</details>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -1,37 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/boat" as boat %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full dark:text-white">
|
||||
<h1 class="h1">Ergo Challenge</h1>
|
||||
<div class="grid ">
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<p class="px-3 pt-3">
|
||||
Schön, dass du heuer bei der Ergo Challenge mitmachen willst!
|
||||
Dafür benötigen wir 3 Daten: Geburtsjahr, Gewicht und Geschlecht.
|
||||
{% if loggedin_user.weight %}Wir haben von dir schon Daten, bitte überprüfe (und aktualisiere) diese kurz:{% endif %}
|
||||
</p>
|
||||
<form action="/ergo/set-data" method="post" class="grid gap-3 p-3">
|
||||
{{ macros::input(label="Geburtsjahr [YYYY]", name="birthyear", required=true, type="number", class="input rounded-md", value=loggedin_user.dob) }}
|
||||
{{ macros::input(label="Gewicht [kg]", name="weight", required=true, type="number", class="input rounded-md", value=loggedin_user.weight) }}
|
||||
<div>
|
||||
<label for="sex" class="text-sm text-gray-600 dark:text-gray-100">Geschlecht</label>
|
||||
<select name="sex" id="sex" class="input rounded-md" required>
|
||||
<option disabled="disabled"
|
||||
{% if loggedin_user.sex != 'f' and loggedin_user.sex != 'm' %}selected="selected"{% endif %}>
|
||||
Geschlecht auswählen
|
||||
</option>
|
||||
<option value="f"
|
||||
{% if loggedin_user.sex == 'f' %}selected="selected"{% endif %}>weiblich</option>
|
||||
<option value="m"
|
||||
{% if loggedin_user.sex == 'm' %}selected="selected"{% endif %}>männlich</option>
|
||||
</select>
|
||||
<small class="block py-1">Du fühlst dich beim Geschlecht nicht angesprochen? Dann melde dich bitte direkt beim Ergo-Christian, Kontaktmöglichkeit auf der nächsten Seite.</small>
|
||||
</div>
|
||||
<input type="submit" class="btn btn-primary" value="Abschicken" />
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endblock content %}
|
@ -9,7 +9,7 @@
|
||||
{{ macros::input(label='Startzeit', name='tripdetails.planned_starting_time', type='time', required=true) }}
|
||||
{{ macros::input(label='Anzahl Steuerleute', name='planned_amount_cox', type='number', required=true, min='0') }}
|
||||
{{ macros::input(label='Anzahl Ruderer (ohne Steuerperson)', name='tripdetails.max_people', type='number', required=true, min='0') }}
|
||||
{{ macros::checkbox(label='Scheckbuch-Anmeldungen erlauben', name='tripdetails.allow_guests') }}
|
||||
{{ macros::checkbox(label='Anfänger-Anmeldungen erlauben', name='tripdetails.allow_guests') }}
|
||||
{{ macros::checkbox(label='Immer anzeigen', name='always_show') }}
|
||||
{{ macros::input(label='Anmerkungen', name='tripdetails.notes', type='input') }}
|
||||
{{ macros::select(label='Typ', data=trip_types, name='tripdetails.trip_type', default='Reguläre Ausfahrt') }}
|
||||
|
@ -4,7 +4,7 @@
|
||||
<input class="day-js" type="hidden" name="day" value="" />
|
||||
{{ macros::input(label='Startzeit (zB "10:00")', name='planned_starting_time', type='time', required=true) }}
|
||||
{{ macros::input(label='Anzahl Ruderer (ohne Steuerperson)', name='max_people', type='number', required=true, min='0') }}
|
||||
{{ macros::checkbox(label='Scheckbuch-Anmeldungen erlauben', name='allow_guests') }}
|
||||
{{ macros::checkbox(label='Anfänger-Anmeldungen erlauben', name='allow_guests') }}
|
||||
{{ macros::input(label='Anmerkungen', name='notes', type='input') }}
|
||||
{% if loggedin_user.allowed_to_steer %}
|
||||
{{ macros::select(label='Typ', data=trip_types, name='trip_type', default='Reguläre Ausfahrt') }}
|
||||
|
@ -106,31 +106,10 @@ function setChoiceByLabel(choicesInstance, label) {
|
||||
</a>
|
||||
<div class="hidden">
|
||||
<div id="mobile-menu">
|
||||
{% if "Donau Linz" in loggedin_user.roles %}
|
||||
<a href="/planned" class="block w-100 py-2 hover:text-primary-600">Geplante Ausfahrten</a>
|
||||
<a href="/log" class="block w-100 py-2 hover:text-primary-600 border-t">Ausfahrt eintragen</a>
|
||||
<a href="/log/show"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Logbuch</a>
|
||||
<a href="/stat" class="block w-100 py-2 hover:text-primary-600 border-t">Statistik</a>
|
||||
<a href="/stat/boats"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Bootsauswertung</a>
|
||||
<a href="/boatdamage"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Bootsschaden</a>
|
||||
<a href="/boatreservation"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Bootsreservierung</a>
|
||||
<a href="/trailerreservation"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Hängerreservierung</a>
|
||||
{% endif %}
|
||||
{% if loggedin_user.weight and loggedin_user.sex and loggedin_user.dob %}
|
||||
<a href="/ergo" class="block w-100 py-2 hover:text-primary-600 border-t">Ergo</a>
|
||||
{% endif %}
|
||||
{% if "admin" in loggedin_user.roles or "Vorstand" in loggedin_user.roles %}
|
||||
<a href="/admin/user"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Userverwaltung</a>
|
||||
{% endif %}
|
||||
<a href="/" class="block w-100 py-2 hover:text-primary-600">Geplante Ausfahrten</a>
|
||||
{% if "admin" in loggedin_user.roles %}
|
||||
<a href="/admin/boat"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Boote</a>
|
||||
<a href="/admin/user"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Mitgliederverwaltung</a>
|
||||
{% endif %}
|
||||
<a href="/auth/logout"
|
||||
class="block w-100 py-2 hover:text-primary-600 border-t">Ausloggen
|
||||
@ -177,6 +156,19 @@ function setChoiceByLabel(choicesInstance, label) {
|
||||
{% if readonly %}readonly{% endif %}>
|
||||
</div>
|
||||
{% endmacro input %}
|
||||
{% macro fancy_role_name(name) %}
|
||||
{%- if name == "cox" -%}
|
||||
Steuerperson
|
||||
{%- elif name == "manage_events" -%}
|
||||
Eventmanager
|
||||
{%- elif name == "admin" -%}
|
||||
Admin
|
||||
{%- elif name == "scheckbuch" -%}
|
||||
Anfänger
|
||||
{%- else -%}
|
||||
{{name}}
|
||||
{%- endif -%}
|
||||
{% endmacro fancy_role_name %}
|
||||
{% macro checkbox(label, name, id='', checked=false, class='', disabled=false, readonly=false) %}
|
||||
<label for="{{ name }}{{ id }}"
|
||||
class="flex items-center cursor-pointer text-black dark:text-white hover:text-gray-900 dark:hover:text-gray-100 {{ class }}">
|
||||
@ -187,7 +179,7 @@ function setChoiceByLabel(choicesInstance, label) {
|
||||
{% if disabled %}disabled{% endif %}
|
||||
{% if readonly %}readonly="readonly"{% endif %}
|
||||
class="h-4 w-4 accent-primary-600 dark:accent-primary-200 mr-2" />
|
||||
{{ label }}
|
||||
{{ self::fancy_role_name(name=label) }}
|
||||
</label>
|
||||
{% endmacro checkbox %}
|
||||
{% macro select(label, data, name='trip_type', default='', id='', selected_id='', display='', extras='', class='', wrapper_class='', required=false, show_seats=false, new_last_entry='', nonSelectableDefault=false, only_ergo=false) %}
|
||||
@ -230,11 +222,11 @@ function setChoiceByLabel(choicesInstance, label) {
|
||||
{% for rower in participants %}
|
||||
<div class="relative">
|
||||
{{ rower.name }}
|
||||
{% if rower.is_guest %}<small class="text-gray-600 dark:text-gray-100">(Scheckbuch)</small>{% endif %}
|
||||
{% if rower.is_guest %}<small class="text-gray-600 dark:text-gray-100">(Anfänger)</small>{% endif %}
|
||||
{% if rower.is_real_guest %}
|
||||
<small class="text-gray-600 dark:text-gray-100">(Gast)</small>
|
||||
{% if allow_removing %}
|
||||
<a href="/planned/remove/{{ trip_details_id }}/{{ rower.name | urlencode }}"
|
||||
<a href="/remove/{{ trip_details_id }}/{{ rower.name | urlencode }}"
|
||||
class="absolute r-0 bg-red-500 w-5 h-5 text-white rounded-full flex items-center justify-center transform rotate-45 top-0 right-0">
|
||||
<svg class="inline h-5 w-5"
|
||||
width="16"
|
||||
|
@ -2,458 +2,416 @@
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Ruder­assistent</h1>
|
||||
<div class="grid gap-3 my-5">
|
||||
<div class="m-auto">
|
||||
<a href="/planned"
|
||||
style="display:inline-flex"
|
||||
class="btn btn-primary flex items-center justify-between w-80 max-w-full">
|
||||
<span class="text-2xl">🚣♀️</span>
|
||||
<span class="text-xl px-3">Geplante Ausfahrten</span>
|
||||
<span class="text-2xl">🚣♂️</span>
|
||||
</a>
|
||||
</div>
|
||||
{% if show_quick_ergo_button %}
|
||||
<div class="m-auto">
|
||||
<a href="/ergo"
|
||||
style="display:inline-flex"
|
||||
class="btn btn-primary flex items-center justify-between w-80 max-w-full">
|
||||
<span class="text-2xl">💪</span>
|
||||
<span class="text-xl px-3">Ergo Challenge</span>
|
||||
<span class="text-2xl">💪🏿</span>
|
||||
</a>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if notifications %}
|
||||
<div id="notification"
|
||||
class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Nachrichten</h2>
|
||||
{% if loggedin_user.amount_unread_notifications > 10 %}
|
||||
<div class="text-primary-950 dark:text-white bg-gray-200 dark:bg-primary-950 bg-opacity-80 text-center pb-3 px-3">
|
||||
Du hast viele ungelesene Benachrichtigungen. Um deine Oberfläche übersichtlich zu halten und wichtige Updates nicht zu verpassen, nimm dir bitte einen Moment Zeit sie zu überprüfen und als gelesen zu markieren (✓).
|
||||
</div>
|
||||
<div class="max-w-screen-xl w-full grid sm:grid-cols-2 lg:grid-cols-3 gap-4">
|
||||
<h1 class="h1 sm:col-span-2 lg:col-span-3">Ausfahrten</h1>
|
||||
{% include "includes/buttons" %}
|
||||
{% for day in days %}
|
||||
{% set amount_trips = day.events | length + day.trips | length %}
|
||||
{% set_global day_cox_needed = false %}
|
||||
{% if day.events | length > 0 %}
|
||||
{% for event in day.events %}
|
||||
{% if event.cox_needed %}
|
||||
{% set_global day_cox_needed = true %}
|
||||
{% endif %}
|
||||
<div class="divide-y">
|
||||
{% for notification in notifications %}
|
||||
{% if not notification.read_at %}
|
||||
<div class="relative flex justify-between items-center p-3">
|
||||
<div class="grow me-4">
|
||||
<small class="uppercase text-gray-600 dark:text-gray-100">
|
||||
<strong>{{ notification.category }}</strong> • {{ notification.created_at | date(format="%d.%m.%Y %H:%M",) }}
|
||||
</small>
|
||||
<div class="mt-1">{{ notification.message | safe }}</div>
|
||||
</div>
|
||||
<div>
|
||||
{% if notification.link %}
|
||||
<a href="{{ notification.link }}" class="inline-block">
|
||||
<button class="btn btn-primary" type="button">🔗</button>
|
||||
</a>
|
||||
{% endif %}
|
||||
{% if not notification.read_at %}
|
||||
<a href="/notification/{{ notification.id }}/read" class="inline-block">
|
||||
<button class="btn btn-primary" type="button">
|
||||
✓
|
||||
<span class="sr-only">Notification gelesen</span>
|
||||
</button>
|
||||
</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
<div id="{{ day.day| date(format="%Y-%m-%d") }}"
|
||||
class="bg-white dark:bg-primary-900 rounded-md flex justify-between flex-col shadow reset-js"
|
||||
style="min-height: 10rem"
|
||||
data-trips="{{ amount_trips }}"
|
||||
data-month="{{ day.day| date(format='%m') }}"
|
||||
data-coxneeded="{{ day_cox_needed }}">
|
||||
<div>
|
||||
<h2 class="font-bold uppercase tracking-wide text-center rounded-t-md {% if day.is_pinned %} text-white bg-primary-950 {% else %} text-primary-950 dark:text-white bg-gray-200 dark:bg-primary-950 bg-opacity-80 {% endif %} text-lg px-3 py-3 ">
|
||||
{{ day.day| date(format="%d.%m.%Y") }}
|
||||
<small class="inline-block ml-1 text-xs {% if day.is_pinned %} text-gray-200 {% else %} text-gray-500 dark:text-gray-100 {% endif %}">{{ day.day | date(format="%A", locale="de_AT") }}
|
||||
{% if day.max_waterlevel %}
|
||||
• <a href="https://hydro.ooe.gv.at/#/overview/Wasserstand/station/16668/Linz/Wasserstand"
|
||||
target="_blank"
|
||||
title="Prognostizierter maximaler Wasserstand am {{ day.day | date(format="%A", locale="de_AT") }}: {{ day.max_waterlevel.avg }} ± {{ day.max_waterlevel.fluctuation }} cm (ungeprüfte Rohdaten, für Details siehe die Infos dazu im Impressum)">🌊{{ day.max_waterlevel.avg }} ± {{ day.max_waterlevel.fluctuation }} cm</a>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</div>
|
||||
<details class="py-3 border-t rounded-b-md">
|
||||
<summary class="px-3 cursor-pointer">Vergangene Nachrichten (14 Tage)</summary>
|
||||
<div class="divide-y text-sm">
|
||||
{% for notification in notifications %}
|
||||
{% if notification.read_at %}
|
||||
<div class="p-3 relative">
|
||||
<small class="uppercase text-gray-600 dark:text-gray-100">
|
||||
<strong>{{ notification.category }}</strong> • {{ notification.created_at | date(format="%d.%m.%Y %H:%M") }}
|
||||
</small>
|
||||
<div class="mt-1">{{ notification.message | safe }}</div>
|
||||
{% if notification.link %}
|
||||
<a href="{{ notification.link }}" class="inline-block">
|
||||
<button class="btn btn-primary" type="button">🔗</button>
|
||||
</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</div>
|
||||
</details>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if "Donau Linz" in loggedin_user.roles and "Unterstützend" not in loggedin_user.roles and "Förderndes Mitglied" not in loggedin_user.roles %}
|
||||
<dialog id="call-for-action"
|
||||
class="max-w-screen-sm dark:bg-primary-600 dark:text-white rounded-md"
|
||||
onclick="document.getElementById('call-for-action').close()">
|
||||
<div onclick="event.stopPropagation();" class="p-3">
|
||||
<button type="button"
|
||||
onclick="document.getElementById('call-for-action').close()"
|
||||
title="Schließen"
|
||||
class="sidebar-close border-0 bg-primary-100 focus:bg-primary-50 text-black flex items-center justify-center transform rotate-45 absolute right-0 mr-3">
|
||||
<svg class="inline h-5 w-5"
|
||||
width="16"
|
||||
height="16"
|
||||
fill="currentColor"
|
||||
viewBox="0 0 16 16">
|
||||
<path d="M8 4a.5.5 0 0 1 .5.5v3h3a.5.5 0 0 1 0 1h-3v3a.5.5 0 0 1-1 0v-3h-3a.5.5 0 0 1 0-1h3v-3A.5.5 0 0 1 8 4z"></path>
|
||||
</svg>
|
||||
</button>
|
||||
<div class="mt-8">
|
||||
<p>
|
||||
Du hast Ideen für sinnvolle neue Funktionen für diese Ruderapp? Melde dich bei Philipp, Marie oder <a href="mailto:it@rudernlinz.at" class="underline">it@rudernlinz.at</a>.
|
||||
</p>
|
||||
<p class="mt-3">
|
||||
Wenn du darüber hinaus Lust hast, deine Skills in ein Projekt zu stecken, das Wellen schlagen wird (😀), dann komm an Bord! Wir sind offen für frische Ideen, haben jedoch auch selber noch genügend; langweilig wird uns bestimmt nicht.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</dialog>
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">
|
||||
Deine Ruderkarriere
|
||||
<span class="text-xl"
|
||||
onclick="document.getElementById('call-for-action').showModal()">💡</span>
|
||||
</h2>
|
||||
<div class="mx-2 divide-y divide-gray-200 dark:divide-primary-600">
|
||||
<div class="py-3">
|
||||
<details>
|
||||
<summary>
|
||||
<h3 class="inline">
|
||||
<span class="text-xl">
|
||||
{% if achievements.rowingbadge and achievements.rowingbadge.achieved %}
|
||||
🎉
|
||||
{% else %}
|
||||
📋
|
||||
{% endif %}
|
||||
</span>
|
||||
Fahrtenabzeichen
|
||||
{% if achievements.rowingbadge %}{{ achievements.rowingbadge.year }}{% endif %}
|
||||
<span><a href="http://www.rudern.at/OFFICE/Downloads/Ausschreibungen/2022/Wanderfahrten//Fahrtenabzeichen%20%C3%84quatorpreis%20und%20Danubius%202022.pdf"
|
||||
target="_blank"
|
||||
class="w-6 h-6 inline-flex align-center justify-center rounded-full bg-primary-500 ml-2 text-white">?</a></span>
|
||||
</h3>
|
||||
</summary>
|
||||
{% if achievements.rowingbadge %}
|
||||
{% set badge = achievements.rowingbadge %}
|
||||
<div class="mb-3">{{ badge.category }}</div>
|
||||
<label for="rowingbadge" class="label">Kilometer ({{ badge.rowed_km }} / {{ badge.required_km }} km)</label>
|
||||
<progress id="rowingbadge"
|
||||
class="w-full block my-3"
|
||||
value="{{ badge.rowed_km }}"
|
||||
max="{{ badge.required_km }}"></progress>
|
||||
<h4 class="font-bold mt-4">Wanderfahrten</h4>
|
||||
<div>Nur eine der folgenden Optionen muss erreicht werden:</div>
|
||||
<ol class="list-decimal ml-4 my-3">
|
||||
<li>
|
||||
{% if badge.multi_day_trips_over_required_distance | length >= 1 %}
|
||||
✅
|
||||
{% else %}
|
||||
❌
|
||||
{% endif %}
|
||||
1 mehrtägige Wanderfahrt > {{ badge.multi_day_trips_required_distance }} km
|
||||
</li>
|
||||
<li>
|
||||
{% if badge.single_day_trips_over_required_distance | length >= 2 %}
|
||||
✅
|
||||
{% else %}
|
||||
❌
|
||||
{% endif %}
|
||||
2 eintägige Wanderfahrten > {{ badge.single_day_trips_required_distance }} km
|
||||
</li>
|
||||
</ol>
|
||||
<details>
|
||||
<summary>Details zu den Wanderfahrten</summary>
|
||||
<div class="mt-3">
|
||||
{% for log in badge.single_day_trips_over_required_distance %}
|
||||
{{ log::show_old(log=log, state="completed", only_ones=false, index=loop.index) }}
|
||||
{% endfor %}
|
||||
{% for log in badge.multi_day_trips_over_required_distance %}
|
||||
{{ log::show_old(log=log, state="completed", only_ones=false, index=loop.index) }}
|
||||
{% endfor %}
|
||||
</div>
|
||||
</details>
|
||||
{% else %}
|
||||
<div class="mt-3">
|
||||
Wir haben leider kein Geburtsdatum von dir und können dir leider deinen heurigen Status für das Fahrtenabzeichen nicht anzeigen. Wenn du dein Geburtsdatum an <a href="mailto:it@rudernlinz.at" class="underline">it@rudernlinz.at</a> schreibst, lässt sich das ändern :-)
|
||||
</div>
|
||||
{% endif %}
|
||||
</details>
|
||||
</div>
|
||||
<div class="py-3">
|
||||
<details>
|
||||
<summary>
|
||||
<h3 class="mb-3 inline">
|
||||
{% set price = achievements.equatorprice %}
|
||||
<span class="text-xl">
|
||||
{% if achievements.curr_equatorprice_name == "-" %}
|
||||
📋
|
||||
{% elif achievements.curr_equatorprice_name == "Bronze" %}
|
||||
🥉
|
||||
{% elif achievements.curr_equatorprice_name == "Silber" %}
|
||||
🥈
|
||||
{% elif achievements.curr_equatorprice_name == "Gold" %}
|
||||
🥇
|
||||
{% elif achievements.curr_equatorprice_name == "Diamant" %}
|
||||
💍
|
||||
{% endif %}
|
||||
</span>
|
||||
Äquatorpreis
|
||||
<span><a href="http://www.rudern.at/OFFICE/Downloads/Ausschreibungen/2022/Wanderfahrten//Fahrtenabzeichen%20%C3%84quatorpreis%20und%20Danubius%202022.pdf"
|
||||
target="_blank"
|
||||
class="w-6 h-6 inline-flex align-center justify-center rounded-full bg-primary-500 ml-2 text-white">?</a></span>
|
||||
</h3>
|
||||
</summary>
|
||||
<div class="mt-3">
|
||||
{% if price.level == "DONE" %}
|
||||
Gratuliere, du hast alles in deinem Rudererleben erreicht, was es (beim Äquatorpreis) zu erreichen gibt.
|
||||
{% else %}
|
||||
<label for="equatorprice" class="label">{{ price.desc }} ({{ price.rowed_km }} / {{ price.required_km }} km)</label>
|
||||
<progress id="equatorprice"
|
||||
class="w-full block my-3"
|
||||
value="{{ price.rowed_km }}"
|
||||
max="{{ price.required_km }}"></progress>
|
||||
<details>
|
||||
<summary>Details</summary>
|
||||
Du bist insgesamt {{ price.rowed_km }} km gerudert. Um den Äquatorpreis in {{ price.desc }} zu erhalten, benötigst du noch {{ price.missing_km }} km um die notwendigen {{ price.required_km }} km zu erreichen.
|
||||
</details>
|
||||
{% endif %}
|
||||
</div>
|
||||
</details>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if "Donau Linz" in loggedin_user.roles and "Unterstützend" not in loggedin_user.roles and "Förderndes Mitglied" not in loggedin_user.roles %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Vereinsmitglied</h2>
|
||||
<ul class="list-none ms-2 divide-y divide-gray-200 dark:divide-primary-600">
|
||||
{% if "Unterstützend" not in loggedin_user.roles and "Förderndes Mitglied" not in loggedin_user.roles %}
|
||||
<li class="py-1">
|
||||
<a href="/planned" class="block w-100 py-2 hover:text-primary-600">Geplante Ausfahrten</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/log" class="block w-100 py-2 hover:text-primary-600">Ausfahrt eintragen</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/log/show" class="block w-100 py-2 hover:text-primary-600">Logbuch</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/stat" class="block w-100 py-2 hover:text-primary-600">Statistik</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/stat/boats" class="block w-100 py-2 hover:text-primary-600">Bootsauswertung</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/boatdamage" class="block w-100 py-2 hover:text-primary-600">Bootsschaden</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/boatreservation"
|
||||
class="block w-100 py-2 hover:text-primary-600">Bootsreservierung</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/trailerreservation"
|
||||
class="block w-100 py-2 hover:text-primary-600">Hängerreservierung</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/steering" class="block w-100 py-2 hover:text-primary-600">Steuerleute & Co</a>
|
||||
</li>
|
||||
<div class="py-3">
|
||||
<p>
|
||||
<details>
|
||||
<summary>
|
||||
Kalender
|
||||
</summary>
|
||||
<p class="mt-3">
|
||||
Du möchtest immer up-to-date mit den Events und Ausfahrten bleiben? Wir bieten 3 verschiedene Arten von Kalender an:
|
||||
</p>
|
||||
<ol class="list-decimal ml-5 my-3">
|
||||
<li>
|
||||
<strong>Alle Events und Ausfahrten</strong>, zu denen du dich angemeldet hast: <a class="underline break-all"
|
||||
href="https://app.rudernlinz.at/cal/personal/{{ loggedin_user.id }}/{{ loggedin_user.user_token }}">https://app.rudernlinz.at/cal/personal/{{ loggedin_user.id }}/{{ loggedin_user.user_token }}</a>
|
||||
<br />
|
||||
<small>Dieser Link enthält einen zufällig generierten Teil, damit nur du (und jene, denen du diesen Link weitergibst) Zugang zu diesen Daten hast.</small>
|
||||
</li>
|
||||
<li>
|
||||
<strong>Allgemeiner Kalender</strong>, zB save-the-dates (Wanderfahrten, ...): <a href="https://rudernlinz.at/cal" class="break-all underline">https://rudernlinz.at/cal</a>
|
||||
</li>
|
||||
<li>
|
||||
<strong>Alle Events</strong>: <a class="break-all underline" href="https://app.rudernlinz.at/cal">https://app.rudernlinz.at/cal</a>
|
||||
<br />
|
||||
<small>Beachte, dass dieser Kalender keine Ausfahrten enthält, die von einzelnen Steuerpersonen augeschrieben werden. Dieser Kalender wird zB auf <a href="https://rudernlinz.at/termine" class="underline">https://rudernlinz.at/termine</a> verwendet und wir möchten keine persönlichen Daten (Namen etc.) leaken.</small>
|
||||
</li>
|
||||
</ol>
|
||||
Du kannst die Kalender einfach in deinen Kalender als "externen Kalender" synchronisieren. Die genauen Schritte hängen von deiner verwendeten Software ab.
|
||||
</details>
|
||||
</p>
|
||||
</div>
|
||||
<div class="py-3">
|
||||
<p>
|
||||
<details>
|
||||
<summary>
|
||||
Signal-Gruppenchat Donau Linz
|
||||
</summary>
|
||||
<p class="mt-3">
|
||||
Mit diesem Link kannst du unserer Signal Gruppe beitreten: <a class="break-all underline" href="https://signal.group/#CjQKICFrq6zSsRHxrucS3jEcQn6lknEXacAykwwLV3vNLKxPEhA17jxz7cpjfu3JZokLq1TH">https://signal.group/#CjQKICFrq6zSsRHxrucS3jEcQn6lknEXacAykwwLV3vNLKxPEhA17jxz7cpjfu3JZokLq1TH</a>
|
||||
</p>
|
||||
</details>
|
||||
</p>
|
||||
</div>
|
||||
{% endif %}
|
||||
<div class="py-3">
|
||||
<p>
|
||||
<details>
|
||||
<summary>
|
||||
WLAN-Passwort
|
||||
</summary>
|
||||
<p class="mt-3">
|
||||
Das Passwort für unser "ASKÖ Ruderverein Donau Linz" WLAN ist <q>donau1921</q> (ohne Anführungszeichen). Bitte an keine vereinsfremden Personen weitergeben.
|
||||
</p>
|
||||
</details>
|
||||
</p>
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if "cox" in loggedin_user.roles or "Bootsführer" in loggedin_user.roles %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Steuerperson</h2>
|
||||
<ul class="list-none ms-2 divide-y divide-gray-200 dark:divide-primary-600">
|
||||
<div class="py-3">
|
||||
<p>
|
||||
<details>
|
||||
<summary>
|
||||
Signal-Gruppenchat Steuerpersonen Donau Linz
|
||||
</summary>
|
||||
<p class="mt-3">
|
||||
Mit diesem Link kannst du unserer Signal Gruppe beitreten: <a class="underline" href="https://signal.group/#CjQKIHJInNb3zSVW7ipLo7_ygIqVxhxUaaNYx4sy2jdklLsIEhBHJNM2KZM1UnBdQxWy_Gdp">https://signal.group/#CjQKIHJInNb3zSVW7ipLo7_ygIqVxhxUaaNYx4sy2jdklLsIEhBHJNM2KZM1UnBdQxWy_Gdp</a>
|
||||
</p>
|
||||
</details>
|
||||
</p>
|
||||
</div>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if "scheckbuch" in loggedin_user.roles %}
|
||||
<div class="grid gap-3 mb-4">
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Scheckbuch</h2>
|
||||
{% if "paid" not in loggedin_user.roles %}
|
||||
<div class="p-3 dark:text-white bg-white dark:bg-primary-900">
|
||||
Bitte nimm zur nächsten Ausfahrt die {{ costs_scheckbuch / 100 }} € für das Scheckbuch mit. Falls du das bereits gemacht hast, gibt uns bitte kurz Bescheid, dass dies noch nicht eingetragen wurde.
|
||||
</div>
|
||||
</small>
|
||||
{% if day.weather %}
|
||||
<small class="inline-block text-xs {% if day.is_pinned %} text-gray-200 {% else %} text-gray-500 dark:text-gray-100 {% endif %}">
|
||||
Temp: {{ day.weather.max_temp | round }}° • Windböe: {{ day.weather.wind_gust | round }} km/h • Regen: {{ day.weather.rain_mm | round }} mm
|
||||
</small>
|
||||
{% endif %}
|
||||
<div class="text-sm p-3 bg-gray-200 bg-opacity-80 dark:bg-primary-950 dark:text-white text-primary-950">
|
||||
<h3>Du hast bisher an {{ last_trips | length }} deiner 5 Scheckbuch-Ausfahrten teilgenommen.</h3>
|
||||
{% if last_trips %}
|
||||
<ol class="mt-3">
|
||||
{% for last_trip in last_trips %}
|
||||
<li>{{ log::show_old(log=last_trip, state="completed", only_ones=false, index=loop.index) }}</li>
|
||||
{% endfor %}
|
||||
</ol>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
</h2>
|
||||
{% if day.events | length > 0 or day.trips | length > 0 %}
|
||||
<div class="grid grid-cols-1 gap-3 mb-3">
|
||||
{# --- START Events --- #}
|
||||
{% if day.events | length > 0 %}
|
||||
{% for event in day.events | sort(attribute="planned_starting_time") %}
|
||||
{% set amount_cur_cox = event.cox | length %}
|
||||
{% set amount_cox_missing = event.planned_amount_cox - amount_cur_cox %}
|
||||
<div class="pt-2 px-3 border-t border-gray-200"
|
||||
style="order: {{ event.planned_starting_time | replace(from=":", to="") }}">
|
||||
<div class="flex justify-between items-center">
|
||||
<div class="mr-1">
|
||||
{% if event.always_show and not day.regular_sees_this_day %}
|
||||
<span title="Du siehst diese Ausfahrt schon, obwohl sie mehr als {{ amount_days_to_show_trips_ahead }} Tage in der Zukunft liegt. Du Magier!">🔮</span>
|
||||
{% endif -%}
|
||||
{%- if event.max_people == 0 %}
|
||||
<strong class="text-[#f43f5e]">⚠ Absage
|
||||
{{ event.planned_starting_time }}
|
||||
Uhr
|
||||
</strong>
|
||||
<small class="text-[#f43f5e]">({{ event.name }}
|
||||
{%- if event.trip_type %}
|
||||
- {{ event.trip_type.icon | safe }} {{ event.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% else %}
|
||||
<strong class="text-primary-900 dark:text-white">
|
||||
{{ event.planned_starting_time }}
|
||||
Uhr
|
||||
</strong>
|
||||
<small class="text-gray-600 dark:text-gray-100">({{ event.name }}
|
||||
{%- if event.trip_type %}
|
||||
- {{ event.trip_type.icon | safe }} {{ event.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% endif %}
|
||||
<br />
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>{{ event.planned_starting_time }} Uhr</strong> ({{ event.name }})
|
||||
{% if event.trip_type %}<small class='block'>{{ event.trip_type.desc }}</small>{% endif %}
|
||||
{% if event.notes %}<small class='block'>{{ event.notes }}</small>{% endif %}
|
||||
" data-body="#event{{ event.trip_details_id }}" class="inline-block link-primary mr-3">
|
||||
Details
|
||||
</a>
|
||||
</div>
|
||||
<div class="text-right grid gap-2">
|
||||
{# --- START Row Buttons --- #}
|
||||
{% set_global cur_user_participates = false %}
|
||||
{% for rower in event.rower %}
|
||||
{% if rower.name == loggedin_user.name %}
|
||||
{% set_global cur_user_participates = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if cur_user_participates %}
|
||||
<a href="/remove/{{ event.trip_details_id }}"
|
||||
class="btn btn-attention btn-fw">Abmelden</a>
|
||||
{% endif %}
|
||||
{% if event.max_people > event.rower | length and cur_user_participates == false %}
|
||||
<a href="/join/{{ event.trip_details_id }}"
|
||||
class="btn btn-primary btn-fw"
|
||||
{% if event.trip_type %}onclick="return confirm('{{ event.trip_type.question }}');"{% endif %}>Mitrudern</a>
|
||||
{% endif %}
|
||||
{# --- END Row Buttons --- #}
|
||||
{# --- START Cox Buttons --- #}
|
||||
{% if loggedin_user.allowed_to_steer %}
|
||||
{% set_global cur_user_participates = false %}
|
||||
{% for cox in event.cox %}
|
||||
{% if cox.name == loggedin_user.name %}
|
||||
{% set_global cur_user_participates = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if cur_user_participates %}
|
||||
<a href="/cox/remove/{{ event.id }}"
|
||||
class="block btn btn-attention btn-fw">
|
||||
{% include "includes/cox-icon" %}
|
||||
Abmelden
|
||||
</a>
|
||||
{% elif event.planned_amount_cox > 0 %}
|
||||
<a href="/cox/join/{{ event.id }}"
|
||||
class="block btn {% if amount_cox_missing > 0 %} btn-dark {% else %} btn-gray {% endif %} btn-fw"
|
||||
{% if event.trip_type %}onclick="return confirm('{{ event.trip_type.question }}');"{% endif %}>
|
||||
{% include "includes/cox-icon" %}
|
||||
Steuern
|
||||
</a>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END Cox Buttons --- #}
|
||||
</div>
|
||||
</div>
|
||||
{# --- START Sidebar Content --- #}
|
||||
<div class="hidden">
|
||||
<div id="event{{ event.trip_details_id }}">
|
||||
{# --- START List Coxes --- #}
|
||||
{% if event.planned_amount_cox > 0 %}
|
||||
{% if event.max_people == 0 %}
|
||||
{{ macros::box(participants=event.cox, empty_seats="", header='Absage', bg='[#f43f5e]') }}
|
||||
{% else %}
|
||||
{% if amount_cox_missing > 0 %}
|
||||
{{ macros::box(participants=event.cox, empty_seats=event.planned_amount_cox - amount_cur_cox, header='Noch benötigte Steuerleute:', text='Keine Steuerleute angemeldet') }}
|
||||
{% else %}
|
||||
{{ macros::box(participants=event.cox, empty_seats="", header='Genügend Steuerleute haben sich angemeldet :-)', text='Keine Steuerleute angemeldet') }}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END List Coxes --- #}
|
||||
{# --- START List Rowers --- #}
|
||||
{% set amount_cur_rower = event.rower | length %}
|
||||
{% if event.max_people == 0 %}
|
||||
{{ macros::box(header='Absage', bg='[#f43f5e]', participants=event.rower, trip_details_id=event.trip_details_id, allow_removing="manage_events" in loggedin_user.roles) }}
|
||||
{% else %}
|
||||
{{ macros::box(participants=event.rower, empty_seats=event.max_people - amount_cur_rower, bg='primary-100', color='black', trip_details_id=event.trip_details_id, allow_removing="manage_events" in loggedin_user.roles) }}
|
||||
{% endif %}
|
||||
{# --- END List Rowers --- #}
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
<form action="/join/{{ event.trip_details_id }}" method="get" />
|
||||
{{ macros::input(label='Gast', class="input rounded-t", name='user_note', type='text', required=true) }}
|
||||
<input value="Gast hinzufügen"
|
||||
class="btn btn-primary w-full rounded-t-none-important"
|
||||
type="submit" />
|
||||
</form>
|
||||
{% endif %}
|
||||
{% if event.allow_guests %}
|
||||
<div class="text-primary-900 bg-primary-50 text-center p-1 mb-4">Gäste willkommen!</div>
|
||||
{% endif %}
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
{# --- START Edit Form --- #}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Ausfahrt bearbeiten</h3>
|
||||
<form action="/admin/planned-event" method="post" class="grid gap-3">
|
||||
<input type="hidden" name="_method" value="put" />
|
||||
<input type="hidden" name="id" value="{{ event.id }}" />
|
||||
{{ macros::input(label='Titel', name='name', type='input', value=event.name) }}
|
||||
{{ macros::input(label='Anzahl Ruderer', name='max_people', type='number', required=true, value=event.max_people, min='1') }}
|
||||
{{ macros::input(label='Anzahl Steuerleute', name='planned_amount_cox', type='number', value=event.planned_amount_cox, required=true, min='0') }}
|
||||
{{ macros::checkbox(label='Immer anzeigen', name='always_show', id=event.id,checked=event.always_show) }}
|
||||
{{ macros::checkbox(label='Gesperrt', name='is_locked', id=event.id,checked=event.is_locked) }}
|
||||
{{ macros::select(label='Typ', name='trip_type', data=trip_types, default='Reguläre Ausfahrt', selected_id=event.trip_type_id) }}
|
||||
{{ macros::input(label='Anmerkungen', name='notes', type='input', value=event.notes) }}
|
||||
<input value="Speichern" class="btn btn-primary" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{# --- END Edit Form --- #}
|
||||
{# --- START Delete Btn --- #}
|
||||
{% if event.rower | length == 0 and amount_cur_cox == 0 %}
|
||||
<div class="text-right mt-6">
|
||||
<a href="/admin/planned-event/{{ event.id }}/delete"
|
||||
class="inline-block btn btn-alert">
|
||||
{% include "includes/delete-icon" %}
|
||||
Termin löschen
|
||||
</a>
|
||||
</div>
|
||||
{% else %}
|
||||
{% if event.max_people == 0 %}
|
||||
Wenn du deine Absage absagen (:^)) willst, einfach entsprechende Anzahl an Ruderer oben eintragen.
|
||||
{% else %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Event absagen</h3>
|
||||
<form action="/admin/planned-event" method="post" class="grid">
|
||||
<input type="hidden" name="_method" value="put" />
|
||||
<input type="hidden" name="id" value="{{ event.id }}" />
|
||||
{{ macros::input(label='Grund der Absage', name='notes', type='input', value='') }}
|
||||
{{ macros::input(label='', name='max_people', type='hidden', value=0) }}
|
||||
{{ macros::input(label='', name='name', type='hidden', value=event.name) }}
|
||||
{{ macros::input(label='', name='max_people', type='hidden', value=event.max_people) }}
|
||||
{{ macros::input(label='', name='planned_amount_cox', type='hidden', value=event.planned_amount_cox) }}
|
||||
{{ macros::input(label='', name='always_show', type='hidden', value=event.always_show) }}
|
||||
{{ macros::input(label='', name='is_locked', type='hidden', value=event.is_locked) }}
|
||||
{{ macros::input(label='', name='trip_type', type='hidden', value=event.trip_type_id) }}
|
||||
<input value="Ausfahrt absagen" class="btn btn-alert" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END Delete Btn --- #}
|
||||
</div>
|
||||
</div>
|
||||
{# --- END Sidebar Content --- #}
|
||||
</div>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
{# --- END Events --- #}
|
||||
{# --- START Trips --- #}
|
||||
{% if day.trips | length > 0 %}
|
||||
{% for trip in day.trips | sort(attribute="planned_starting_time") %}
|
||||
<div class="pt-2 px-3 reset-js border-t border-gray-200"
|
||||
style="order: {{ trip.planned_starting_time | replace(from=":", to="") }}"
|
||||
data-coxneeded="false">
|
||||
<div class="flex justify-between items-center">
|
||||
<div class="mr-1">
|
||||
{% if trip.always_show and not day.regular_sees_this_day %}
|
||||
<span title="Du siehst diese Ausfahrt schon, obwohl sie mehr als {{ amount_days_to_show_trips_ahead }} Tage in der Zukunft liegt. Du Magier!">🔮</span>
|
||||
{% endif -%}
|
||||
{% if trip.max_people == 0 %}
|
||||
<strong class="text-[#f43f5e]">⚠
|
||||
{{ trip.planned_starting_time }}
|
||||
Uhr</strong>
|
||||
<small class="text-[#f43f5e]">(Absage
|
||||
{{ trip.cox_name -}}
|
||||
{% if trip.trip_type %}
|
||||
-
|
||||
{{ trip.trip_type.icon | safe }} {{ trip.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% else %}
|
||||
<strong class="text-primary-900 dark:text-white">{{ trip.planned_starting_time }}
|
||||
Uhr</strong>
|
||||
<small class="text-gray-600 dark:text-gray-100">({{ trip.cox_name -}}
|
||||
{% if trip.trip_type %}
|
||||
- {{ trip.trip_type.icon | safe }} {{ trip.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% endif %}
|
||||
<br />
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>
|
||||
{% if trip.max_people == 0 %}⚠{% endif %}
|
||||
{{ trip.planned_starting_time }} Uhr</strong> ({{ trip.cox_name }})
|
||||
{% if trip.trip_type %}<small class='block'>{{ trip.trip_type.desc }}</small>{% endif %}
|
||||
{% if trip.notes %}<small class='block'>{{ trip.notes }}</small>{% endif %}
|
||||
" data-body="#trip{{ trip.trip_details_id }}" class="inline-block link-primary mr-3">
|
||||
Details
|
||||
</a>
|
||||
</div>
|
||||
<div>
|
||||
{% set_global cur_user_participates = false %}
|
||||
{% for rower in trip.rower %}
|
||||
{% if rower.name == loggedin_user.name %}
|
||||
{% set_global cur_user_participates = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if cur_user_participates %}
|
||||
<a href="/remove/{{ trip.trip_details_id }}"
|
||||
class="btn btn-attention btn-fw">Abmelden</a>
|
||||
{% endif %}
|
||||
{% if trip.max_people > trip.rower | length and trip.cox_id != loggedin_user.id and cur_user_participates == false %}
|
||||
<a href="/join/{{ trip.trip_details_id }}"
|
||||
class="btn btn-primary btn-fw"
|
||||
{% if trip.trip_type %}onclick="return confirm('{{ trip.trip_type.question }}');"{% endif %}>Mitrudern</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{# --- START Sidebar Content --- #}
|
||||
<div class="hidden">
|
||||
<div id="trip{{ trip.trip_details_id }}">
|
||||
{% if trip.max_people == 0 %}
|
||||
{# --- border-[#f43f5e] bg-[#f43f5e] --- #}
|
||||
{{ macros::box(participants=trip.rower,bg='[#f43f5e]',header='Absage', trip_details_id=trip.trip_details_id, allow_removing=loggedin_user.id == trip.cox_id) }}
|
||||
{% else %}
|
||||
{% set amount_cur_rower = trip.rower | length %}
|
||||
{{ macros::box(participants=trip.rower, empty_seats=trip.max_people - amount_cur_rower, bg='primary-100', color='black', trip_details_id=trip.trip_details_id, allow_removing=loggedin_user.id == trip.cox_id) }}
|
||||
{% if trip.cox_id == loggedin_user.id %}
|
||||
<form action="/join/{{ trip.trip_details_id }}" method="get" />
|
||||
{{ macros::input(label='Gast', class="input rounded-t", name='user_note', type='text', required=true) }}
|
||||
<input value="Gast hinzufügen"
|
||||
class="btn btn-primary w-full rounded-t-none-important"
|
||||
type="submit" />
|
||||
</form>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- START Edit Form --- #}
|
||||
{% if trip.cox_id == loggedin_user.id %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Ausfahrt bearbeiten</h3>
|
||||
<form action="/cox/trip/{{ trip.id }}" method="post" class="grid gap-3">
|
||||
{{ macros::input(label='Anzahl Ruderer', name='max_people', type='number', required=true, value=trip.max_people, min=trip.rower | length) }}
|
||||
{{ macros::input(label='Anmerkungen', name='notes', type='input', value=trip.notes) }}
|
||||
{{ macros::checkbox(label='Gesperrt', name='is_locked', id=trip.id,checked=trip.is_locked) }}
|
||||
{% if loggedin_user.allowed_to_steer %}
|
||||
{{ macros::select(label='Typ', name='trip_type', data=trip_types, default='Reguläre Ausfahrt', selected_id=trip.trip_type_id, only_ergo=not loggedin_user.allowed_to_steer) }}
|
||||
{% else %}
|
||||
{{ macros::select(label='Typ', name='trip_type', data=trip_types, selected_id=trip.trip_type_id, only_ergo=not loggedin_user.allowed_to_steer, only_ergos=true) }}
|
||||
{% endif %}
|
||||
<input value="Speichern" class="btn btn-primary" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% if trip.rower | length == 0 %}
|
||||
<div class="text-right mt-6">
|
||||
<a href="/cox/remove/trip/{{ trip.id }}"
|
||||
class="inline-block btn btn-alert">
|
||||
{% include "includes/delete-icon" %}
|
||||
Termin löschen
|
||||
</a>
|
||||
</div>
|
||||
{% else %}
|
||||
{% if trip.max_people == 0 %}
|
||||
Wenn du deine Absage absagen (:^)) willst, einfach entsprechende Anzahl an Ruderer oben eintragen.
|
||||
{% else %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Ausfahrt absagen</h3>
|
||||
<form action="/cox/trip/{{ trip.id }}" method="post" class="grid">
|
||||
{{ macros::input(label='', name='max_people', type='hidden', value=0) }}
|
||||
{{ macros::input(label='Grund der Absage', name='notes', type='input', value='') }}
|
||||
{{ macros::input(label='', name='is_locked', type='hidden', value=trip.is_locked) }}
|
||||
{{ macros::input(label='', name='trip_type', type='hidden', value=trip.trip_type_id) }}
|
||||
<input value="Ausfahrt absagen" class="btn btn-alert" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END Edit Form --- #}
|
||||
{# --- START Admin Form --- #}
|
||||
{% if allowed_to_update_always_show_trip %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Admin-Modus</h3>
|
||||
{% if not day.regular_sees_this_day %}
|
||||
<form action="/cox/trip/{{ trip.id }}/toggle-always-show"
|
||||
method="get"
|
||||
class="grid gap-3">
|
||||
{% if not trip.always_show %}
|
||||
<small>Diese Ausfahrt sehen aktuell nur Steuerleute (und Admins). {{ amount_days_to_show_trips_ahead }} Tage vorher sehen sie dann alle.</small>
|
||||
{% else %}
|
||||
<small>Diese Ausfahrt sehen alle Mitglieder.</small>
|
||||
{% endif %}
|
||||
<input value="{% if trip.always_show %}Ausfahrt nur Steuerleute (und Admins) anzeigen{% else %}Ausfahrt allen anzeigen{% endif %}"
|
||||
class="btn btn-primary"
|
||||
type="submit" />
|
||||
</form>
|
||||
{% endif %}
|
||||
<a href="/cox/remove/trip/{{ trip.id }}"
|
||||
class="inline-block btn btn-alert mt-5 w-full">
|
||||
{% include "includes/delete-icon" %}
|
||||
Termin löschen
|
||||
</a>
|
||||
</div>
|
||||
{% endif %}
|
||||
{# --- END Admin Form --- #}
|
||||
</div>
|
||||
</div>
|
||||
{# --- END Sidebar Content --- #}
|
||||
</div>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
{# --- END Trips --- #}
|
||||
</div>
|
||||
{% endif %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Ergo</h2>
|
||||
<div class="p-3">
|
||||
<ul class="list-none ms-2">
|
||||
<li class="py-1">
|
||||
<a href="/ergo" class="block w-100 py-2 hover:text-primary-600">Ergo</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
{% if "schnupper-betreuer" in loggedin_user.roles %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Schnupper-Betreuer</h2>
|
||||
<ul class="list-none ms-2 divide-y divide-gray-200 dark:divide-primary-600">
|
||||
<li class="py-1">
|
||||
<a href="/admin/schnupper"
|
||||
class="block w-100 py-2 hover:text-primary-600">Schnuppern</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if "Vorstand" in loggedin_user.roles %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Vorstand</h2>
|
||||
<ul class="list-none ms-2 divide-y divide-gray-200 dark:divide-primary-600">
|
||||
<li class="py-1">
|
||||
<a href="/admin/user/fees"
|
||||
class="block w-100 py-2 hover:text-primary-600">Übersicht User Gebühren</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/user/scheckbuch"
|
||||
class="block w-100 py-2 hover:text-primary-600">Scheckbuch</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/user" class="block w-100 py-2 hover:text-primary-600">User</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/board/boathouse"
|
||||
class="block w-100 py-2 hover:text-primary-600">Bootshaus</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/mail" class="block w-100 py-2 hover:text-primary-600">Mail ausschicken</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/notification"
|
||||
class="block w-100 py-2 hover:text-primary-600">Nachricht ausschreiben</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/board/achievement"
|
||||
class="block w-100 py-2 hover:text-primary-600">Abzeichen</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% if "admin" in loggedin_user.roles %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Admin</h2>
|
||||
<ul class="list-none ms-2 divide-y divide-gray-200 dark:divide-primary-600">
|
||||
<li class="py-1">
|
||||
<a href="/admin/boat" class="block w-100 py-2 hover:text-primary-600">Boote</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/user" class="block w-100 py-2 hover:text-primary-600">User</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/rss" class="block w-100 py-2 hover:text-primary-600">Logs</a>
|
||||
</li>
|
||||
<li class="py-1">
|
||||
<a href="/admin/list" class="block w-100 py-2 hover:text-primary-600">Fingerabdruck-Liste überprüfen</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
{% endif %}
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Allgemein</h2>
|
||||
<div class="p-3">
|
||||
<ul class="list-none ms-2">
|
||||
<li class="py-1">
|
||||
<a href="https://wiki.rudernlinz.at/ruderassistent#faq"
|
||||
target="_blank"
|
||||
class="block w-100 py-2 hover:text-primary-600">FAQ (extern)</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{# --- START Add Buttons --- #}
|
||||
{% if "manage_events" in loggedin_user.roles or loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
<div class="grid {% if "manage_events" in loggedin_user.roles and (loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles) %}grid-cols-2{% endif %} text-center">
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>Event</strong> am {{ day.day| date(format='%d.%m.%Y') }} erstellen" data-day="{{ day.day }}" data-body="#addEventForm" class="relative inline-block w-full bg-primary-900 hover:bg-primary-950 focus:bg-primary-950 dark:bg-primary-950 text-white py-2 text-sm font-semibold
|
||||
{% if loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
rounded-bl-md
|
||||
{% else %}
|
||||
rounded-b-md
|
||||
{% endif %}
|
||||
">
|
||||
<span class="absolute inset-y-0 left-0 flex items-center pl-3">{% include "includes/plus-icon" %}</span>
|
||||
Event
|
||||
</a>
|
||||
{% endif %}
|
||||
{% if loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>Ausfahrt</strong> am {{ day.day| date(format='%d.%m.%Y') }} erstellen" data-day="{{ day.day }}" data-body="#sidebarForm" class="relative inline-block w-full py-2 text-primary-900 hover:text-primary-950 dark:bg-primary-600 dark:text-white dark:hover:bg-primary-500 dark:hover:text-white focus:text-primary-950 text-sm font-semibold bg-gray-100 hover:bg-gray-200 focus:bg-gray-200
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
rounded-br-md
|
||||
{% else %}
|
||||
rounded-b-md
|
||||
{% endif %}
|
||||
">
|
||||
<span class="absolute inset-y-0 left-0 flex items-center pl-3">{% include "includes/plus-icon" %}</span>
|
||||
{% if not loggedin_user.allowed_to_steer %}Ergo-Session
|
||||
{%- else -%}
|
||||
Ausfahrt{%endif%}
|
||||
</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
{# --- END Add Buttons --- #}
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% if loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
{% include "forms/trip" %}
|
||||
{% endif %}
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
{% include "forms/event" %}
|
||||
{% endif %}
|
||||
{% endblock content %}
|
||||
|
@ -1,61 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="w-full">
|
||||
<h1 class="h1">Logbuch</h1>
|
||||
{% if flash and not loggedin_user %}
|
||||
<div class="pt-3 max-w-lg m-auto">
|
||||
{{ macros::alert(message=flash.1, type=flash.0, class="sm:col-span-2 lg:col-span-3") }}
|
||||
</div>
|
||||
{% endif %}
|
||||
<div class="w-full grid lg:grid-cols-5 gap-3 mt-5">
|
||||
<div>
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md hidden md:block shadow">
|
||||
<h2 class="h2">Boote</h2>
|
||||
<div>{{ log::show_boats(only_ones=false) }}</div>
|
||||
</div>
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md hidden lg:block shadow mt-3">
|
||||
<h2 class="h2">Schnellauswahl</h2>
|
||||
<div>
|
||||
{% for boat in boats | reverse %}
|
||||
{% if boat.id in [42, 36] %}
|
||||
<div class="p-3 boats-js text-black dark:text-white border-t {% if boat.damage != 'locked' and not boat.on_water %} cursor-pointer hover:text-primary-900 dark:hover:text-gray-100 hover:bg-gray-100 dark:hover:bg-primary-950 {% endif %}"
|
||||
{% if boat.damage != 'locked' and not boat.on_water %} data-seats="{{ boat.amount_seats }}" data-default_shipmaster_only_steering="{{ boat.default_shipmaster_only_steering }}" data-default-destination="{{ boat.default_destination }}" data-onclick="true" {% endif %}
|
||||
data-id="{{ boat.id }}">
|
||||
<span class="status-damage status-damage-{{ boat.damage }}"></span>
|
||||
<span {% if boat.damage == 'locked' or boat.on_water %}class="opacity-50"{% endif %}>{{ boat.name }}
|
||||
{% if boat.owner %}<span class="opacity-50">(privat)</span>{% endif %}
|
||||
</span>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="lg:col-span-3">
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md shadow">
|
||||
<h2 class="h2">Neue Ausfahrt</h2>
|
||||
<div class="p-3">{{ log::new(only_ones=false, shipmaster=-1) }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md shadow pb-2">
|
||||
<h2 class="h2">Am Wasser</h2>
|
||||
<div>
|
||||
{% if on_water | length > 0 %}
|
||||
{% for log in on_water %}
|
||||
{{ log::show(log=log, state="on_water", allowed_to_close=true, only_ones=false) }}
|
||||
{% endfor %}
|
||||
{% else %}
|
||||
<p class="p-3 text-center text-black dark:text-white">Kein Boot am Wasser</p>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{{ macros::boatreservation() }}
|
||||
{{ macros::plannedtrips() }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<script src="/public/logbook.js"></script>
|
||||
{% endblock content %}
|
@ -1,65 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">
|
||||
Logbuch
|
||||
{% if loggedin_user and "admin" in loggedin_user.roles %}
|
||||
<select id="yearSelect"
|
||||
onchange="changeYear()"
|
||||
style="background: transparent;
|
||||
background-image: none;
|
||||
text-decoration: underline"></select>
|
||||
{% endif %}
|
||||
</h1>
|
||||
<div class="mt-3">
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Bootsname oder Ruderer...">
|
||||
</div>
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
{% for log in logs %}
|
||||
{% set_global allowed_to_edit = false %}
|
||||
{% if loggedin_user %}
|
||||
{% if "Vorstand" in loggedin_user.roles %}
|
||||
{% set_global allowed_to_edit = true %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{{ log::show_old(log=log, state="completed", only_ones=false, index=loop.index, allowed_to_edit=allowed_to_edit) }}
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
<script>
|
||||
function getYearFromURL() {
|
||||
var queryParams = new URLSearchParams(window.location.search);
|
||||
return queryParams.get('year');
|
||||
}
|
||||
|
||||
function populateYears() {
|
||||
var select = document.getElementById('yearSelect');
|
||||
var currentYear = new Date().getFullYear();
|
||||
var selectedYear = getYearFromURL() || currentYear;
|
||||
for (var year = 2019; year <= currentYear; year++) {
|
||||
var option = document.createElement('option');
|
||||
option.value = option.textContent = year;
|
||||
if (year == selectedYear) {
|
||||
option.selected = true;
|
||||
}
|
||||
select.appendChild(option);
|
||||
}
|
||||
}
|
||||
|
||||
function changeYear() {
|
||||
var selectedYear = document.getElementById('yearSelect').value;
|
||||
window.location.href = '?year=' + selectedYear;
|
||||
}
|
||||
|
||||
// Call this function when the page loads
|
||||
populateYears();
|
||||
</script>
|
||||
{% endblock content %}
|
@ -1,44 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="w-full">
|
||||
<h1 class="h1">Logbuch</h1>
|
||||
<div class="w-full grid lg:grid-cols-5 gap-3 mt-5">
|
||||
<div>
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md hidden lg:block shadow">
|
||||
<h2 class="h2">Boote</h2>
|
||||
<div>{{ log::show_boats(only_ones=false) }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="lg:col-span-3">
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md shadow">
|
||||
<h2 class="h2">Neue Ausfahrt</h2>
|
||||
<div class="p-3">{{ log::new(shipmaster=loggedin_user.id) }}</div>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<div class="bg-white dark:bg-primary-900 rounded-md shadow pb-2">
|
||||
<h2 class="h2">Am Wasser</h2>
|
||||
{% if on_water | length > 0 %}
|
||||
{% for log in on_water %}
|
||||
{% if log.shipmaster == loggedin_user.id %}
|
||||
{{ log::show(log=log, state="on_water", allowed_to_close=true, only_ones=not loggedin_user.allowed_to_steer) }}
|
||||
{% elif "Vorstand" in loggedin_user.roles %}
|
||||
{{ log::show(log=log, state="on_water", allowed_to_close=true, only_ones=not loggedin_user.allowed_to_steer) }}
|
||||
{% else %}
|
||||
{{ log::show(log=log, state="on_water", only_ones=true) }}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% else %}
|
||||
<p class="p-3 text-center text-black dark:text-white">Kein Boot am Wasser</p>
|
||||
{% endif %}
|
||||
</div>
|
||||
{{ macros::boatreservation() }}
|
||||
{{ macros::plannedtrips() }}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% if loggedin_user %}<script>var loggedin_user_id = "{{ loggedin_user.id }}";</script>{% endif %}
|
||||
<script src="/public/logbook.js"></script>
|
||||
{% endblock content %}
|
@ -1,469 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-xl w-full grid sm:grid-cols-2 lg:grid-cols-3 gap-4">
|
||||
{% if "paid" not in loggedin_user.roles and "Donau Linz" in loggedin_user.roles %}
|
||||
<div class="grid gap-3 sm:col-span-2 lg:col-span-3">
|
||||
<div class="bg-white dark:bg-primary-900 text-black dark:text-white rounded-md block shadow mt-5"
|
||||
role="alert">
|
||||
<h2 class="h2">Vereinsgebühren</h2>
|
||||
<div class="text-sm p-3">
|
||||
{% include "includes/qrcode" %}
|
||||
<div id="qrcode"
|
||||
style="float: left;
|
||||
padding-top: 10 pt;
|
||||
padding-right: 10pt;
|
||||
padding-bottom: 10pt"></div>
|
||||
<script type="text/javascript">
|
||||
var sepaqr = new sepaQR({
|
||||
benefName: 'ASKÖ Ruderverein Donau Linz',
|
||||
benefBIC: 'ASPKAT2LXXX',
|
||||
benefAccNr: 'AT582032032100729256',
|
||||
amountEuro: {{ fee.sum_in_cents/100 }},
|
||||
remittanceInf: 'Vereinsgebühren {{ fee.name }}',
|
||||
});
|
||||
|
||||
var code = sepaqr.makeCodeInto("qrcode");
|
||||
|
||||
</script>
|
||||
<b>Dein Vereinsbeitrag ({{ fee.name }}): {{ fee.sum_in_cents / 100 }}€
|
||||
{% if fee.parts | length == 1 %}({{ fee.parts[0].0 }}){% endif %}
|
||||
</b>
|
||||
<br />
|
||||
{% if fee.parts | length > 1 %}
|
||||
<small>
|
||||
Setzt sich zusammen aus:
|
||||
<ul style="list-style: circle; padding-left: 1em;">
|
||||
{% for p in fee.parts %}
|
||||
<li>
|
||||
{{ p.0 }} ({{ p.1 / 100 }}€)
|
||||
{% if not loop.last %}+{% endif %}
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ul>
|
||||
</small>
|
||||
{% endif %}
|
||||
Bitte auf folgendes Konto überweisen: IBAN AT58 2032 0321 0072 9256. Alternativ kannst du auch mit deiner Bankapp den QR Code scannen, damit sollten alle Daten vorausgefüllt sein.
|
||||
<br />
|
||||
Falls die Berechnung nicht stimmt (korrekte Preise findest du <a href="https://rudernlinz.at/unser-verein/gebuhren/"
|
||||
target="_blank"
|
||||
rel="noopener noreferrer">hier</a>) melde dich bitte bei it@rudernlinz.at. @Studenten: Bitte die aktuelle Studienbestätigung an it@rudernlinz.at schicken.
|
||||
<br />
|
||||
<small><a href="https://rudernlinz.at/unser-verein/vorstand/" target="_blank">Unsere Kassiere</a> aktualisieren den Ruderassistent unregelmäßig mit unserem Bankkonto. Falls du schon bezahlt hast, kannst du diese Nachricht getrost ignorieren. Wenn du schon vor "einigen Wochen" bezahlt hast bitte bei kassier@rudernlinz.at nachfragen :^)</small>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endif %}
|
||||
<h1 class="h1 sm:col-span-2 lg:col-span-3">Ausfahrten</h1>
|
||||
{% include "includes/buttons" %}
|
||||
{% for day in days %}
|
||||
{% set amount_trips = day.events | length + day.trips | length %}
|
||||
{% set_global day_cox_needed = false %}
|
||||
{% if day.events | length > 0 %}
|
||||
{% for event in day.events %}
|
||||
{% if event.cox_needed %}
|
||||
{% set_global day_cox_needed = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
<div id="{{ day.day| date(format="%Y-%m-%d") }}"
|
||||
class="bg-white dark:bg-primary-900 rounded-md flex justify-between flex-col shadow reset-js"
|
||||
style="min-height: 10rem"
|
||||
data-trips="{{ amount_trips }}"
|
||||
data-month="{{ day.day| date(format='%m') }}"
|
||||
data-coxneeded="{{ day_cox_needed }}">
|
||||
<div>
|
||||
<h2 class="font-bold uppercase tracking-wide text-center rounded-t-md {% if day.is_pinned %} text-white bg-primary-950 {% else %} text-primary-950 dark:text-white bg-gray-200 dark:bg-primary-950 bg-opacity-80 {% endif %} text-lg px-3 py-3 ">
|
||||
{{ day.day| date(format="%d.%m.%Y") }}
|
||||
<small class="inline-block ml-1 text-xs {% if day.is_pinned %} text-gray-200 {% else %} text-gray-500 dark:text-gray-100 {% endif %}">{{ day.day | date(format="%A", locale="de_AT") }}
|
||||
{% if day.max_waterlevel %}
|
||||
• <a href="https://hydro.ooe.gv.at/#/overview/Wasserstand/station/16668/Linz/Wasserstand"
|
||||
target="_blank"
|
||||
title="Prognostizierter maximaler Wasserstand am {{ day.day | date(format="%A", locale="de_AT") }}: {{ day.max_waterlevel.avg }} ± {{ day.max_waterlevel.fluctuation }} cm (ungeprüfte Rohdaten, für Details siehe die Infos dazu im Impressum)">🌊{{ day.max_waterlevel.avg }} ± {{ day.max_waterlevel.fluctuation }} cm</a>
|
||||
{% endif %}
|
||||
</small>
|
||||
{% if day.weather %}
|
||||
<small class="inline-block text-xs {% if day.is_pinned %} text-gray-200 {% else %} text-gray-500 dark:text-gray-100 {% endif %}">
|
||||
Temp: {{ day.weather.max_temp | round }}° • Windböe: {{ day.weather.wind_gust | round }} km/h • Regen: {{ day.weather.rain_mm | round }} mm
|
||||
</small>
|
||||
{% endif %}
|
||||
</h2>
|
||||
{% if day.events | length > 0 or day.trips | length > 0 %}
|
||||
<div class="grid grid-cols-1 gap-3 mb-3">
|
||||
{# --- START Events --- #}
|
||||
{% if day.events | length > 0 %}
|
||||
{% for event in day.events | sort(attribute="planned_starting_time") %}
|
||||
{% set amount_cur_cox = event.cox | length %}
|
||||
{% set amount_cox_missing = event.planned_amount_cox - amount_cur_cox %}
|
||||
<div class="pt-2 px-3 border-t border-gray-200"
|
||||
style="order: {{ event.planned_starting_time | replace(from=":", to="") }}">
|
||||
<div class="flex justify-between items-center">
|
||||
<div class="mr-1">
|
||||
{% if event.always_show and not day.regular_sees_this_day %}
|
||||
<span title="Du siehst diese Ausfahrt schon, obwohl sie mehr als {{ amount_days_to_show_trips_ahead }} Tage in der Zukunft liegt. Du Magier!">🔮</span>
|
||||
{% endif -%}
|
||||
{%- if event.max_people == 0 %}
|
||||
<strong class="text-[#f43f5e]">⚠ Absage
|
||||
{{ event.planned_starting_time }}
|
||||
Uhr
|
||||
</strong>
|
||||
<small class="text-[#f43f5e]">({{ event.name }}
|
||||
{%- if event.trip_type %}
|
||||
- {{ event.trip_type.icon | safe }} {{ event.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% else %}
|
||||
<strong class="text-primary-900 dark:text-white">
|
||||
{{ event.planned_starting_time }}
|
||||
Uhr
|
||||
</strong>
|
||||
<small class="text-gray-600 dark:text-gray-100">({{ event.name }}
|
||||
{%- if event.trip_type %}
|
||||
- {{ event.trip_type.icon | safe }} {{ event.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% endif %}
|
||||
<br />
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>{{ event.planned_starting_time }} Uhr</strong> ({{ event.name }})
|
||||
{% if event.trip_type %}<small class='block'>{{ event.trip_type.desc }}</small>{% endif %}
|
||||
{% if event.notes %}<small class='block'>{{ event.notes }}</small>{% endif %}
|
||||
" data-body="#event{{ event.trip_details_id }}" class="inline-block link-primary mr-3">
|
||||
Details
|
||||
</a>
|
||||
</div>
|
||||
<div class="text-right grid gap-2">
|
||||
{# --- START Row Buttons --- #}
|
||||
{% set_global cur_user_participates = false %}
|
||||
{% for rower in event.rower %}
|
||||
{% if rower.name == loggedin_user.name %}
|
||||
{% set_global cur_user_participates = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if cur_user_participates %}
|
||||
<a href="/planned/remove/{{ event.trip_details_id }}"
|
||||
class="btn btn-attention btn-fw">Abmelden</a>
|
||||
{% endif %}
|
||||
{% if event.max_people > event.rower | length and cur_user_participates == false %}
|
||||
<a href="/planned/join/{{ event.trip_details_id }}"
|
||||
class="btn btn-primary btn-fw"
|
||||
{% if event.trip_type %}onclick="return confirm('{{ event.trip_type.question }}');"{% endif %}>Mitrudern</a>
|
||||
{% endif %}
|
||||
{# --- END Row Buttons --- #}
|
||||
{# --- START Cox Buttons --- #}
|
||||
{% if loggedin_user.allowed_to_steer %}
|
||||
{% set_global cur_user_participates = false %}
|
||||
{% for cox in event.cox %}
|
||||
{% if cox.name == loggedin_user.name %}
|
||||
{% set_global cur_user_participates = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if cur_user_participates %}
|
||||
<a href="/cox/remove/{{ event.id }}"
|
||||
class="block btn btn-attention btn-fw">
|
||||
{% include "includes/cox-icon" %}
|
||||
Abmelden
|
||||
</a>
|
||||
{% elif event.planned_amount_cox > 0 %}
|
||||
<a href="/cox/join/{{ event.id }}"
|
||||
class="block btn {% if amount_cox_missing > 0 %} btn-dark {% else %} btn-gray {% endif %} btn-fw"
|
||||
{% if event.trip_type %}onclick="return confirm('{{ event.trip_type.question }}');"{% endif %}>
|
||||
{% include "includes/cox-icon" %}
|
||||
Steuern
|
||||
</a>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END Cox Buttons --- #}
|
||||
</div>
|
||||
</div>
|
||||
{# --- START Sidebar Content --- #}
|
||||
<div class="hidden">
|
||||
<div id="event{{ event.trip_details_id }}">
|
||||
{# --- START List Coxes --- #}
|
||||
{% if event.planned_amount_cox > 0 %}
|
||||
{% if event.max_people == 0 %}
|
||||
{{ macros::box(participants=event.cox, empty_seats="", header='Absage', bg='[#f43f5e]') }}
|
||||
{% else %}
|
||||
{% if amount_cox_missing > 0 %}
|
||||
{{ macros::box(participants=event.cox, empty_seats=event.planned_amount_cox - amount_cur_cox, header='Noch benötigte Steuerleute:', text='Keine Steuerleute angemeldet') }}
|
||||
{% else %}
|
||||
{{ macros::box(participants=event.cox, empty_seats="", header='Genügend Steuerleute haben sich angemeldet :-)', text='Keine Steuerleute angemeldet') }}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END List Coxes --- #}
|
||||
{# --- START List Rowers --- #}
|
||||
{% set amount_cur_rower = event.rower | length %}
|
||||
{% if event.max_people == 0 %}
|
||||
{{ macros::box(header='Absage', bg='[#f43f5e]', participants=event.rower, trip_details_id=event.trip_details_id, allow_removing="manage_events" in loggedin_user.roles) }}
|
||||
{% else %}
|
||||
{{ macros::box(participants=event.rower, empty_seats=event.max_people - amount_cur_rower, bg='primary-100', color='black', trip_details_id=event.trip_details_id, allow_removing="manage_events" in loggedin_user.roles) }}
|
||||
{% endif %}
|
||||
{# --- END List Rowers --- #}
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
<form action="/planned/join/{{ event.trip_details_id }}" method="get" />
|
||||
{{ macros::input(label='Gast', class="input rounded-t", name='user_note', type='text', required=true) }}
|
||||
<input value="Gast hinzufügen"
|
||||
class="btn btn-primary w-full rounded-t-none-important"
|
||||
type="submit" />
|
||||
</form>
|
||||
{% endif %}
|
||||
{% if event.allow_guests %}
|
||||
<div class="text-primary-900 bg-primary-50 text-center p-1 mb-4">Gäste willkommen!</div>
|
||||
{% endif %}
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
{# --- START Edit Form --- #}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Ausfahrt bearbeiten</h3>
|
||||
<form action="/admin/planned-event" method="post" class="grid gap-3">
|
||||
<input type="hidden" name="_method" value="put" />
|
||||
<input type="hidden" name="id" value="{{ event.id }}" />
|
||||
{{ macros::input(label='Titel', name='name', type='input', value=event.name) }}
|
||||
{{ macros::input(label='Anzahl Ruderer', name='max_people', type='number', required=true, value=event.max_people, min='1') }}
|
||||
{{ macros::input(label='Anzahl Steuerleute', name='planned_amount_cox', type='number', value=event.planned_amount_cox, required=true, min='0') }}
|
||||
{{ macros::checkbox(label='Immer anzeigen', name='always_show', id=event.id,checked=event.always_show) }}
|
||||
{{ macros::checkbox(label='Gesperrt', name='is_locked', id=event.id,checked=event.is_locked) }}
|
||||
{{ macros::select(label='Typ', name='trip_type', data=trip_types, default='Reguläre Ausfahrt', selected_id=event.trip_type_id) }}
|
||||
{{ macros::input(label='Anmerkungen', name='notes', type='input', value=event.notes) }}
|
||||
<input value="Speichern" class="btn btn-primary" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{# --- END Edit Form --- #}
|
||||
{# --- START Delete Btn --- #}
|
||||
{% if event.rower | length == 0 and amount_cur_cox == 0 %}
|
||||
<div class="text-right mt-6">
|
||||
<a href="/admin/planned-event/{{ event.id }}/delete"
|
||||
class="inline-block btn btn-alert">
|
||||
{% include "includes/delete-icon" %}
|
||||
Termin löschen
|
||||
</a>
|
||||
</div>
|
||||
{% else %}
|
||||
{% if event.max_people == 0 %}
|
||||
Wenn du deine Absage absagen (:^)) willst, einfach entsprechende Anzahl an Ruderer oben eintragen.
|
||||
{% else %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Event absagen</h3>
|
||||
<form action="/admin/planned-event" method="post" class="grid">
|
||||
<input type="hidden" name="_method" value="put" />
|
||||
<input type="hidden" name="id" value="{{ event.id }}" />
|
||||
{{ macros::input(label='Grund der Absage', name='notes', type='input', value='') }}
|
||||
{{ macros::input(label='', name='max_people', type='hidden', value=0) }}
|
||||
{{ macros::input(label='', name='name', type='hidden', value=event.name) }}
|
||||
{{ macros::input(label='', name='max_people', type='hidden', value=event.max_people) }}
|
||||
{{ macros::input(label='', name='planned_amount_cox', type='hidden', value=event.planned_amount_cox) }}
|
||||
{{ macros::input(label='', name='always_show', type='hidden', value=event.always_show) }}
|
||||
{{ macros::input(label='', name='is_locked', type='hidden', value=event.is_locked) }}
|
||||
{{ macros::input(label='', name='trip_type', type='hidden', value=event.trip_type_id) }}
|
||||
<input value="Ausfahrt absagen" class="btn btn-alert" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END Delete Btn --- #}
|
||||
</div>
|
||||
</div>
|
||||
{# --- END Sidebar Content --- #}
|
||||
</div>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
{# --- END Events --- #}
|
||||
{# --- START Trips --- #}
|
||||
{% if day.trips | length > 0 %}
|
||||
{% for trip in day.trips | sort(attribute="planned_starting_time") %}
|
||||
<div class="pt-2 px-3 reset-js border-t border-gray-200"
|
||||
style="order: {{ trip.planned_starting_time | replace(from=":", to="") }}"
|
||||
data-coxneeded="false">
|
||||
<div class="flex justify-between items-center">
|
||||
<div class="mr-1">
|
||||
{% if trip.always_show and not day.regular_sees_this_day %}
|
||||
<span title="Du siehst diese Ausfahrt schon, obwohl sie mehr als {{ amount_days_to_show_trips_ahead }} Tage in der Zukunft liegt. Du Magier!">🔮</span>
|
||||
{% endif -%}
|
||||
{% if trip.max_people == 0 %}
|
||||
<strong class="text-[#f43f5e]">⚠
|
||||
{{ trip.planned_starting_time }}
|
||||
Uhr</strong>
|
||||
<small class="text-[#f43f5e]">(Absage
|
||||
{{ trip.cox_name -}}
|
||||
{% if trip.trip_type %}
|
||||
-
|
||||
{{ trip.trip_type.icon | safe }} {{ trip.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% else %}
|
||||
<strong class="text-primary-900 dark:text-white">{{ trip.planned_starting_time }}
|
||||
Uhr</strong>
|
||||
<small class="text-gray-600 dark:text-gray-100">({{ trip.cox_name -}}
|
||||
{% if trip.trip_type %}
|
||||
- {{ trip.trip_type.icon | safe }} {{ trip.trip_type.name }}
|
||||
{%- endif -%}
|
||||
)</small>
|
||||
{% endif %}
|
||||
<br />
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>
|
||||
{% if trip.max_people == 0 %}⚠{% endif %}
|
||||
{{ trip.planned_starting_time }} Uhr</strong> ({{ trip.cox_name }})
|
||||
{% if trip.trip_type %}<small class='block'>{{ trip.trip_type.desc }}</small>{% endif %}
|
||||
{% if trip.notes %}<small class='block'>{{ trip.notes }}</small>{% endif %}
|
||||
" data-body="#trip{{ trip.trip_details_id }}" class="inline-block link-primary mr-3">
|
||||
Details
|
||||
</a>
|
||||
</div>
|
||||
<div>
|
||||
{% set_global cur_user_participates = false %}
|
||||
{% for rower in trip.rower %}
|
||||
{% if rower.name == loggedin_user.name %}
|
||||
{% set_global cur_user_participates = true %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if cur_user_participates %}
|
||||
<a href="/planned/remove/{{ trip.trip_details_id }}"
|
||||
class="btn btn-attention btn-fw">Abmelden</a>
|
||||
{% endif %}
|
||||
{% if trip.max_people > trip.rower | length and trip.cox_id != loggedin_user.id and cur_user_participates == false %}
|
||||
<a href="/planned/join/{{ trip.trip_details_id }}"
|
||||
class="btn btn-primary btn-fw"
|
||||
{% if trip.trip_type %}onclick="return confirm('{{ trip.trip_type.question }}');"{% endif %}>Mitrudern</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{# --- START Sidebar Content --- #}
|
||||
<div class="hidden">
|
||||
<div id="trip{{ trip.trip_details_id }}">
|
||||
{% if trip.max_people == 0 %}
|
||||
{# --- border-[#f43f5e] bg-[#f43f5e] --- #}
|
||||
{{ macros::box(participants=trip.rower,bg='[#f43f5e]',header='Absage', trip_details_id=trip.trip_details_id, allow_removing=loggedin_user.id == trip.cox_id) }}
|
||||
{% else %}
|
||||
{% set amount_cur_rower = trip.rower | length %}
|
||||
{{ macros::box(participants=trip.rower, empty_seats=trip.max_people - amount_cur_rower, bg='primary-100', color='black', trip_details_id=trip.trip_details_id, allow_removing=loggedin_user.id == trip.cox_id) }}
|
||||
{% if trip.cox_id == loggedin_user.id %}
|
||||
<form action="/planned/join/{{ trip.trip_details_id }}" method="get" />
|
||||
{{ macros::input(label='Gast', class="input rounded-t", name='user_note', type='text', required=true) }}
|
||||
<input value="Gast hinzufügen"
|
||||
class="btn btn-primary w-full rounded-t-none-important"
|
||||
type="submit" />
|
||||
</form>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- START Edit Form --- #}
|
||||
{% if trip.cox_id == loggedin_user.id %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Ausfahrt bearbeiten</h3>
|
||||
<form action="/cox/trip/{{ trip.id }}" method="post" class="grid gap-3">
|
||||
{{ macros::input(label='Anzahl Ruderer', name='max_people', type='number', required=true, value=trip.max_people, min=trip.rower | length) }}
|
||||
{{ macros::input(label='Anmerkungen', name='notes', type='input', value=trip.notes) }}
|
||||
{{ macros::checkbox(label='Gesperrt', name='is_locked', id=trip.id,checked=trip.is_locked) }}
|
||||
{% if loggedin_user.allowed_to_steer %}
|
||||
{{ macros::select(label='Typ', name='trip_type', data=trip_types, default='Reguläre Ausfahrt', selected_id=trip.trip_type_id, only_ergo=not loggedin_user.allowed_to_steer) }}
|
||||
{% else %}
|
||||
{{ macros::select(label='Typ', name='trip_type', data=trip_types, selected_id=trip.trip_type_id, only_ergo=not loggedin_user.allowed_to_steer, only_ergos=true) }}
|
||||
{% endif %}
|
||||
<input value="Speichern" class="btn btn-primary" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% if trip.rower | length == 0 %}
|
||||
<div class="text-right mt-6">
|
||||
<a href="/cox/remove/trip/{{ trip.id }}"
|
||||
class="inline-block btn btn-alert">
|
||||
{% include "includes/delete-icon" %}
|
||||
Termin löschen
|
||||
</a>
|
||||
</div>
|
||||
{% else %}
|
||||
{% if trip.max_people == 0 %}
|
||||
Wenn du deine Absage absagen (:^)) willst, einfach entsprechende Anzahl an Ruderer oben eintragen.
|
||||
{% else %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Ausfahrt absagen</h3>
|
||||
<form action="/cox/trip/{{ trip.id }}" method="post" class="grid">
|
||||
{{ macros::input(label='', name='max_people', type='hidden', value=0) }}
|
||||
{{ macros::input(label='Grund der Absage', name='notes', type='input', value='') }}
|
||||
{{ macros::input(label='', name='is_locked', type='hidden', value=trip.is_locked) }}
|
||||
{{ macros::input(label='', name='trip_type', type='hidden', value=trip.trip_type_id) }}
|
||||
<input value="Ausfahrt absagen" class="btn btn-alert" type="submit" />
|
||||
</form>
|
||||
</div>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{# --- END Edit Form --- #}
|
||||
{# --- START Admin Form --- #}
|
||||
{% if allowed_to_update_always_show_trip %}
|
||||
<div class="bg-gray-100 dark:bg-primary-900 p-3 mt-4 rounded-md">
|
||||
<h3 class="text-primary-950 dark:text-white font-bold uppercase tracking-wide mb-2">Admin-Modus</h3>
|
||||
{% if not day.regular_sees_this_day %}
|
||||
<form action="/cox/trip/{{ trip.id }}/toggle-always-show"
|
||||
method="get"
|
||||
class="grid gap-3">
|
||||
{% if not trip.always_show %}
|
||||
<small>Diese Ausfahrt sehen aktuell nur Steuerleute (und Admins). {{ amount_days_to_show_trips_ahead }} Tage vorher sehen sie dann alle.</small>
|
||||
{% else %}
|
||||
<small>Diese Ausfahrt sehen alle Mitglieder.</small>
|
||||
{% endif %}
|
||||
<input value="{% if trip.always_show %}Ausfahrt nur Steuerleute (und Admins) anzeigen{% else %}Ausfahrt allen anzeigen{% endif %}"
|
||||
class="btn btn-primary"
|
||||
type="submit" />
|
||||
</form>
|
||||
{% endif %}
|
||||
<a href="/cox/remove/trip/{{ trip.id }}"
|
||||
class="inline-block btn btn-alert mt-5 w-full">
|
||||
{% include "includes/delete-icon" %}
|
||||
Termin löschen
|
||||
</a>
|
||||
</div>
|
||||
{% endif %}
|
||||
{# --- END Admin Form --- #}
|
||||
</div>
|
||||
</div>
|
||||
{# --- END Sidebar Content --- #}
|
||||
</div>
|
||||
{% endfor %}
|
||||
{% endif %}
|
||||
{# --- END Trips --- #}
|
||||
</div>
|
||||
{% endif %}
|
||||
</div>
|
||||
{# --- START Add Buttons --- #}
|
||||
{% if "manage_events" in loggedin_user.roles or loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
<div class="grid {% if "manage_events" in loggedin_user.roles and (loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles) %}grid-cols-2{% endif %} text-center">
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>Event</strong> am {{ day.day| date(format='%d.%m.%Y') }} erstellen" data-day="{{ day.day }}" data-body="#addEventForm" class="relative inline-block w-full bg-primary-900 hover:bg-primary-950 focus:bg-primary-950 dark:bg-primary-950 text-white py-2 text-sm font-semibold
|
||||
{% if loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
rounded-bl-md
|
||||
{% else %}
|
||||
rounded-b-md
|
||||
{% endif %}
|
||||
">
|
||||
<span class="absolute inset-y-0 left-0 flex items-center pl-3">{% include "includes/plus-icon" %}</span>
|
||||
Event
|
||||
</a>
|
||||
{% endif %}
|
||||
{% if loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
<a href="#" data-sidebar="true" data-trigger="sidebar" data-header="<strong>Ausfahrt</strong> am {{ day.day| date(format='%d.%m.%Y') }} erstellen" data-day="{{ day.day }}" data-body="#sidebarForm" class="relative inline-block w-full py-2 text-primary-900 hover:text-primary-950 dark:bg-primary-600 dark:text-white dark:hover:bg-primary-500 dark:hover:text-white focus:text-primary-950 text-sm font-semibold bg-gray-100 hover:bg-gray-200 focus:bg-gray-200
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
rounded-br-md
|
||||
{% else %}
|
||||
rounded-b-md
|
||||
{% endif %}
|
||||
">
|
||||
<span class="absolute inset-y-0 left-0 flex items-center pl-3">{% include "includes/plus-icon" %}</span>
|
||||
{% if not loggedin_user.allowed_to_steer %}Ergo-Session
|
||||
{%- else -%}
|
||||
Ausfahrt{%endif%}
|
||||
</a>
|
||||
{% endif %}
|
||||
</div>
|
||||
{% endif %}
|
||||
{# --- END Add Buttons --- #}
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
</div>
|
||||
{% if loggedin_user.allowed_to_steer or "ergo" in loggedin_user.roles %}
|
||||
{% include "forms/trip" %}
|
||||
{% endif %}
|
||||
{% if "manage_events" in loggedin_user.roles %}
|
||||
{% include "forms/event" %}
|
||||
{% endif %}
|
||||
{% endblock content %}
|
@ -1,42 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<link rel="stylesheet" href="/public/table.css" />
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Bootsauswertung</h1>
|
||||
<div class="text-black dark:text-white">
|
||||
<table id="basic">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Name</th>
|
||||
<th>Art</th>
|
||||
<th>Eigentümer</th>
|
||||
<th>Ort</th>
|
||||
{% for year in stat.pot_years | sort | reverse %}<th>{{ year }}</th>{% endfor %}
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for boat in stat.boats %}
|
||||
<tr>
|
||||
<td>{{ boat.name }}</td>
|
||||
<td>{{ boat.cat }}</td>
|
||||
<td>{{ boat.owner }}</td>
|
||||
<td>{{ boat.location }}</td>
|
||||
{% for year in stat.pot_years | sort | reverse %}
|
||||
<td>
|
||||
{% if year~'' in boat.years %}
|
||||
{{ boat.years[year] }}
|
||||
{% else %}
|
||||
0
|
||||
{% endif %}
|
||||
</td>
|
||||
{% endfor %}
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</div>
|
||||
<script src="/public/jstable.min.js"></script>
|
||||
<script src="/public/table.js"></script>
|
||||
{% endblock content %}
|
@ -1,101 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">
|
||||
Statistik
|
||||
<select id="yearSelect"
|
||||
onchange="changeYear()"
|
||||
style="background: transparent;
|
||||
background-image: none;
|
||||
text-decoration: underline"></select>
|
||||
</h1>
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Namen..." />
|
||||
</div>
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
<div class="border-r border-l border-gray-200 dark:border-primary-600">
|
||||
{% set_global km = 0 %} {% set_global index = 1 %}
|
||||
{% for s in stat %}
|
||||
<div class="border-t border-gray-200 dark:border-primary-600 bg-white dark:bg-primary-900 text-black dark:text-white flex justify-between items-center px-3 py-1"
|
||||
data-filterable="true"
|
||||
data-filter="{{ s.name }}">
|
||||
<span class="text-sm text-gray-600 dark:text-gray-100 w-10">
|
||||
{% if km != s.rowed_km %}
|
||||
{{ loop.index }}
|
||||
{% set_global index = loop.index %}
|
||||
{% else %}
|
||||
{{ index }}
|
||||
{% endif %}
|
||||
</span>
|
||||
<span class="grow">{{ s.name }}</span>
|
||||
<span>{{ s.rowed_km }} km</span>
|
||||
{% set_global km = s.rowed_km %}
|
||||
</div>
|
||||
{% endfor %}
|
||||
<div class="border-t border-gray-200 dark:border-primary-600 bg-white dark:bg-primary-900 text-black dark:text-white flex justify-between items-center px-3 py-1"
|
||||
data-filterable="true"
|
||||
data-filter="Summe Vereinsmitglieder">
|
||||
<span class="text-sm text-gray-600 dark:text-gray-100 w-10"></span>
|
||||
<span class="grow"><b>Summe Vereinsmitglieder</b></span>
|
||||
<span><b>{{ club_km }} km</b></span>
|
||||
</div>
|
||||
<div class="border-t border-gray-200 dark:border-primary-600 bg-white dark:bg-primary-900 text-black dark:text-white flex justify-between items-center px-3 py-1"
|
||||
data-filterable="true"
|
||||
data-filter="Summe {{ guest_km.name }}">
|
||||
<span class="text-sm text-gray-600 dark:text-gray-100 w-10"></span>
|
||||
<span class="grow"><b>Summe {{ guest_km.name }}</b></span>
|
||||
<span><b>{{ guest_km.rowed_km }} km</b></span>
|
||||
</div>
|
||||
<div class="border-t border-gray-200 dark:border-primary-600 border-b bg-white dark:bg-primary-900 text-black dark:text-white flex justify-between items-center px-3 py-1"
|
||||
data-filterable="true"
|
||||
data-filter="Gesamtsumme">
|
||||
<span class="text-sm text-gray-600 dark:text-gray-100 w-10"></span>
|
||||
<span class="grow"><b>Gesamtsumme</b></span>
|
||||
<span><b>{{ club_km + guest_km.rowed_km }} km</b></span>
|
||||
</div>
|
||||
</div>
|
||||
<div id="container" class="w-full"></div>
|
||||
</div>
|
||||
<script>
|
||||
{% if personal %}
|
||||
const data = [
|
||||
{%- for p in personal %}{ date: '{{p.date}}', km: {{p.km}} },{%- endfor %}
|
||||
]
|
||||
sessionStorage.setItem('userStats', JSON.stringify(data));
|
||||
{% endif %}
|
||||
|
||||
function getYearFromURL() {
|
||||
var queryParams = new URLSearchParams(window.location.search);
|
||||
return queryParams.get('year');
|
||||
}
|
||||
|
||||
function populateYears() {
|
||||
var select = document.getElementById('yearSelect');
|
||||
var currentYear = new Date().getFullYear();
|
||||
var selectedYear = getYearFromURL() || currentYear;
|
||||
for (var year = 1977; year <= currentYear; year++) {
|
||||
var option = document.createElement('option');
|
||||
option.value = option.textContent = year;
|
||||
if (year == selectedYear) {
|
||||
option.selected = true;
|
||||
}
|
||||
select.appendChild(option);
|
||||
}
|
||||
}
|
||||
|
||||
function changeYear() {
|
||||
var selectedYear = document.getElementById('yearSelect').value;
|
||||
window.location.href = '?year=' + selectedYear;
|
||||
}
|
||||
|
||||
// Call this function when the page loads
|
||||
populateYears();
|
||||
</script>
|
||||
<script src="/public/logbook.js"></script>
|
||||
{% endblock content %}
|
@ -1,98 +0,0 @@
|
||||
{% import "includes/macros" as macros %}
|
||||
{% import "includes/forms/log" as log %}
|
||||
{% extends "base" %}
|
||||
{% block content %}
|
||||
<div class="max-w-screen-lg w-full">
|
||||
<h1 class="h1">Hängerreservierungen</h1>
|
||||
<h2 class="text-md font-bold tracking-wide bg-primary-900 mt-3 p-3 text-white flex justify-between items-center rounded-md">
|
||||
Neue Reservierung
|
||||
<a href="#"
|
||||
class="inline-flex justify-center rounded-md bg-primary-600 mx-1 px-3 py-2 text-sm font-semibold text-white hover:bg-primary-500 focus-visible:outline focus-visible:outline-2 focus-visible:outline-offset-2 focus-visible:outline-primary-600 cursor-pointer"
|
||||
data-sidebar="true"
|
||||
data-trigger="sidebar"
|
||||
data-header="Neue Reservierung anlegen"
|
||||
data-body="#new-reservation">
|
||||
{% include "includes/plus-icon" %}
|
||||
<span class="sr-only">Neue Reservierung eintragen</span>
|
||||
</a>
|
||||
</h2>
|
||||
<div class="hidden">
|
||||
<div id="new-reservation">
|
||||
<form action="/trailerreservation/new" method="post" class="grid gap-3">
|
||||
{{ macros::select(label="Anhänger", data=trailers, name="trailer_id", id="trailer_id", display=["name"], wrapper_class="col-span-4", nonSelectableDefault=" -- Wähle einen Hänger aus ---", required=true) }}
|
||||
{% if not loggedin_user %}{{ macros::select(label='Reserviert von', data=user, name='user_id_applicant') }}{% endif %}
|
||||
{{ macros::input(label='Beginn', name='start_date', type='date', required=true, wrapper_class='col-span-4') }}
|
||||
{{ macros::input(label='Ende', name='end_date', type='date', required=true, wrapper_class='col-span-4') }}
|
||||
{{ macros::input(label='Uhrzeit (zB ab 14:00 Uhr, ganztägig, ...)', name='time_desc', type='text', required=true, wrapper_class='col-span-4') }}
|
||||
{{ macros::input(label='Zweck (Wanderfahrt, ...)', name='usage', type='text', required=true, wrapper_class='col-span-4') }}
|
||||
<input type="submit"
|
||||
class="btn btn-primary w-full col-span-4"
|
||||
value="Reservierung eintragen" />
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
<div class="search-wrapper">
|
||||
<label for="name" class="sr-only">Suche</label>
|
||||
<input type="search"
|
||||
name="name"
|
||||
id="filter-js"
|
||||
class="search-bar"
|
||||
placeholder="Suchen nach Namen...">
|
||||
</div>
|
||||
<div id="filter-result-js" class="search-result"></div>
|
||||
{% for reservation in trailerreservations %}
|
||||
{% set allowed_to_edit = false %}
|
||||
{% if loggedin_user %}
|
||||
{% if loggedin_user.id == reservation.user_applicant.id or "admin" in loggedin_user.roles %}
|
||||
{% set allowed_to_edit = true %}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
<div data-filterable="true"
|
||||
data-filter="{{ reservation.user_applicant.name }} {{ reservation.trailer.name }}"
|
||||
class="w-full border-t bg-white dark:bg-primary-900 text-black dark:text-white p-3">
|
||||
<div class="w-full">
|
||||
<strong>Hänger:</strong>
|
||||
{{ reservation.trailer.name }}
|
||||
<br />
|
||||
<strong>Reservierung:</strong>
|
||||
{{ reservation.user_applicant.name }}
|
||||
<br />
|
||||
<strong>Datum:</strong>
|
||||
{{ reservation.start_date }}
|
||||
{% if reservation.end_date != reservation.start_date %}
|
||||
-
|
||||
{{ reservation.end_date }}
|
||||
{% endif %}
|
||||
<br />
|
||||
{% if not allowed_to_edit %}
|
||||
<strong>Uhrzeit:</strong>
|
||||
{{ reservation.time_desc }}
|
||||
<br />
|
||||
<strong>Zweck:</strong>
|
||||
{{ reservation.usage }}
|
||||
{% endif %}
|
||||
{% if allowed_to_edit %}
|
||||
<form action="/trailerreservation"
|
||||
method="post"
|
||||
class="bg-white dark:bg-primary-900 pt-3 rounded-md w-full">
|
||||
<div class="w-full grid gap-3">
|
||||
<input type="hidden" name="id" value="{{ reservation.id }}" />
|
||||
{{ macros::input(label='Uhrzeit', name='time_desc', id=loop.index, type="text", value=reservation.time_desc, readonly=false) }}
|
||||
{{ macros::input(label='Zweck', name='usage', id=loop.index, type="text", value=reservation.usage, readonly=false) }}
|
||||
</div>
|
||||
<div class="mt-3 text-right">
|
||||
<a href="/trailerreservation/{{ reservation.id }}/delete"
|
||||
class="w-28 btn btn-alert"
|
||||
onclick="return confirm('Willst du diese Reservierung wirklich löschen?');">
|
||||
{% include "includes/delete-icon" %}
|
||||
Löschen
|
||||
</a>
|
||||
<input value="Ändern" type="submit" class="w-28 btn btn-primary ml-1" />
|
||||
</div>
|
||||
</form>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
{% endblock content %}
|
Reference in New Issue
Block a user