ADD: dav_event_office: start work on an optimized interface for the
office.
This commit is contained in:
1
dav_event_office/__init__.py
Normal file
1
dav_event_office/__init__.py
Normal file
@@ -0,0 +1 @@
|
||||
default_app_config = 'dav_event_office.apps.AppConfig'
|
||||
9
dav_event_office/apps.py
Normal file
9
dav_event_office/apps.py
Normal file
@@ -0,0 +1,9 @@
|
||||
from dav_base.config.apps import AppConfig as _AppConfig
|
||||
|
||||
DEFAULT_SETTINGS = ()
|
||||
|
||||
|
||||
class AppConfig(_AppConfig):
|
||||
name = 'dav_event_office'
|
||||
verbose_name = u'DAV Touren- & Kursreferat'
|
||||
default_settings = DEFAULT_SETTINGS
|
||||
@@ -0,0 +1 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
3
dav_event_office/module.json
Normal file
3
dav_event_office/module.json
Normal file
@@ -0,0 +1,3 @@
|
||||
{
|
||||
"url_prefix": "office/events"
|
||||
}
|
||||
3
dav_event_office/templates/dav_event_office/base.html
Normal file
3
dav_event_office/templates/dav_event_office/base.html
Normal file
@@ -0,0 +1,3 @@
|
||||
{% extends "dav_base/base.html" %}
|
||||
|
||||
{% block head-title %}Touren- & Kursreferat - {{ block.super }}{% endblock %}
|
||||
@@ -0,0 +1,59 @@
|
||||
{% extends 'dav_event_office/base.html' %}
|
||||
{% load bootstrap3 %}
|
||||
{% load i18n %}
|
||||
|
||||
{% block head-title %}{{ event }} - {{ block.super }}{% endblock head-title %}
|
||||
|
||||
{% block page-container-fluid %}
|
||||
<div class="action-tabs top-most">
|
||||
<ul class="nav nav-tabs" role="tablist">
|
||||
<li>
|
||||
<a class="btn"
|
||||
href="{% url 'dav_event_office:event-list' %}">{% trans 'Veranstaltungsliste' %}</a>
|
||||
</li>
|
||||
<li class="active">
|
||||
<a class="btn"
|
||||
href="{% url 'dav_event_office:event-detail' event.pk %}">{% trans 'Details' %}</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div class="row">
|
||||
<div class="col-sm-12">
|
||||
{{ event.render_as_html }}
|
||||
<div class="panel panel-default">
|
||||
<div class="panel-body">
|
||||
<div class="row">
|
||||
<div class="col-sm-7">
|
||||
<h5>Status-Log</h5>
|
||||
{% for flag in event.flags.all %}
|
||||
<div class="row">
|
||||
<div class="col-sm-5">
|
||||
<span class="text-{{ flag.status.bootstrap_context|default:'default' }}">{% bootstrap_icon 'check' %}</span>
|
||||
<strong>{{ flag.status.label }}:</strong>
|
||||
</div>
|
||||
<div class="col-sm-7">
|
||||
{{ flag.timestamp|date:'l, d. F Y, H:i' }} {% trans 'Uhr' %}<br />
|
||||
{% trans 'von' %} {{ flag.user.get_full_name|default:flag.user }}
|
||||
</div>
|
||||
</div>
|
||||
{% endfor %}
|
||||
</div>
|
||||
<div class="col-sm-5">
|
||||
<h5>{% trans 'Veröffentlichung' %}</h5>
|
||||
{% if event.planned_publication_date %}
|
||||
{{ event.planned_publication_date|date:'l, d. F Y' }}
|
||||
{% else %}
|
||||
{% trans 'Unverzüglich' %}
|
||||
{% endif %}
|
||||
{% if event.internal_note %}
|
||||
<h5 style="margin-top: 1em;">{% trans 'Bearbeitungshinweis' %}</h5>
|
||||
<div class="well well-sm"><small>{{ event.internal_note|linebreaksbr }}</small></div>
|
||||
{% endif %}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
{% endblock page-container-fluid %}
|
||||
101
dav_event_office/templates/dav_event_office/event_list.html
Normal file
101
dav_event_office/templates/dav_event_office/event_list.html
Normal file
@@ -0,0 +1,101 @@
|
||||
{% extends 'dav_event_office/base.html' %}
|
||||
{% load bootstrap3 %}
|
||||
{% load i18n %}
|
||||
{% load dav_events %}
|
||||
|
||||
{% block page-container-fluid %}
|
||||
<div class="action-tabs top-most">
|
||||
<div class="pull-right">
|
||||
<!--
|
||||
<a id="btn-event-create" class="btn btn-primary"
|
||||
href="{% url 'dav_events:create' %}">
|
||||
{% bootstrap_icon 'plus' %}
|
||||
{% trans 'Neue Veranstaltung anlegen' %}
|
||||
</a>
|
||||
-->
|
||||
</div>
|
||||
<ul class="nav nav-tabs" role="tablist">
|
||||
<li class="active">
|
||||
<a href="{% url 'dav_event_office:event-list' %}">{% trans 'Veranstaltungsliste' %}</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div>
|
||||
<table id="objects_table" class="table table-striped">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>{% trans 'Nummer' %}</th>
|
||||
<th>{% trans 'Titel' %}</th>
|
||||
<th>{% trans 'Trainer' %}</th>
|
||||
<th>{% trans 'Datum' %}</th>
|
||||
<th>{% trans 'Status' %}</th>
|
||||
</tr>
|
||||
<tr>
|
||||
<th><input type="text" placeholder="{% trans 'Filter' %}" /></th>
|
||||
<th><input type="text" placeholder="{% trans 'Filter' %}" /></th>
|
||||
<th><input type="text" placeholder="{% trans 'Filter' %}" /></th>
|
||||
<th><input type="text" placeholder="{% trans 'Filter' %}" /></th>
|
||||
<th><input type="text" placeholder="{% trans 'Filter' %}" /></th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
{% for event in event_list %}
|
||||
<tr>
|
||||
{% with number=event.get_number %}
|
||||
<td data-order="{{ number|slice:':1' }}{{ number|slice:'-2:' }}{{ number|slice:'1:-2'|cut:'/' }}"
|
||||
data-search="{{ number }} ({{ event.get_sport_display }})">
|
||||
<a href="{% url 'dav_event_office:event-detail' event.pk %}">{{ number }}</a><br />
|
||||
<small>({{ event.get_sport_display }})</small>
|
||||
</td>
|
||||
{% endwith %}
|
||||
<td>
|
||||
<a href="{% url 'dav_event_office:event-detail' event.pk %}">{{ event.title }}</a>
|
||||
</td>
|
||||
<td>
|
||||
{{ event.get_trainer_full_name }}
|
||||
{% if event.trainer_email %}
|
||||
<br />{{ event.trainer_email}}
|
||||
{% elif event.trainer_phone %}
|
||||
<br />{{ event.trainer_phone}}
|
||||
{% else %}
|
||||
<br /><span class="text-danger">{% trans 'Weder E-Mail-Adresse noch Telefonnummer!' %}</span>
|
||||
{% endif %}
|
||||
</td>
|
||||
<td data-order="{{ event.first_day|date:'U' }}">
|
||||
{{ event.get_numeric_date }}
|
||||
</td>
|
||||
<td>
|
||||
{% render_event_status event %}
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
</tbody>
|
||||
</table>
|
||||
<script type="text/javascript">
|
||||
$(document).ready( function () {
|
||||
var table = $("#objects_table").DataTable( {
|
||||
orderCellsTop: true,
|
||||
paging: false,
|
||||
language: {
|
||||
search: "{% trans 'Filter' %}:",
|
||||
info: "{% trans 'Zeige _TOTAL_ Einträge' %}",
|
||||
infoFiltered: "{% trans 'aus insgesamt _MAX_ Einträgen' %}",
|
||||
infoEmpty: "{% trans 'Zeige 0 Einträge' %}",
|
||||
infoPostFix: ".",
|
||||
emptyTable: "{% trans 'Keine Daten vorhanden.' %}",
|
||||
zeroRecords: "{% trans 'Keine passenden Einträge.' %}",
|
||||
|
||||
}
|
||||
} );
|
||||
$("#objects_table thead input").on( "keyup change", function() {
|
||||
table
|
||||
.column( $(this).parent().index() )
|
||||
.search( this.value )
|
||||
.draw();
|
||||
} );
|
||||
$("#objects_table_filter").hide();
|
||||
} );
|
||||
</script>
|
||||
</div>
|
||||
{% endblock page-container-fluid %}
|
||||
8
dav_event_office/templates/dav_event_office/home.html
Normal file
8
dav_event_office/templates/dav_event_office/home.html
Normal file
@@ -0,0 +1,8 @@
|
||||
{% extends "dav_event_office/base.html" %}
|
||||
{% load bootstrap3 %}
|
||||
{% load i18n %}
|
||||
|
||||
{% block page-container-fluid %}
|
||||
<h3 class="top-most">{% trans 'Touren- & Kursreferat' %}</h3>
|
||||
{% include './includes/home_tiles.html' %}
|
||||
{% endblock page-container-fluid %}
|
||||
@@ -0,0 +1,38 @@
|
||||
{% load bootstrap3 %}
|
||||
{% load i18n %}
|
||||
|
||||
<div class="row">
|
||||
<div class="col-sm-6">
|
||||
<div class="well">
|
||||
<p class="lead">Veranstaltungen</p>
|
||||
<p>
|
||||
Blah.
|
||||
<span class="glyphicon glyphicon-question-sign" title="
|
||||
Du wirst durch eine Reihe von Eingabemasken geführt, die alles Mögliche abfragen, was wir bezüglich deiner Tour / deines Kurses wissen müssen.
|
||||
|
||||
Am Ende dieses Prozesses bekommst du noch einmal eine Zusammenfassung der Daten angezeigt.
|
||||
Wenn du dann auf "Einsenden" klickst, wird alles an den Tourenreferenten und sein Team weitergeleitet.
|
||||
Du wirst dann per E-Mail auf dem laufenden gehalten.
|
||||
"></span>
|
||||
</p>
|
||||
<p>
|
||||
<a class="btn btn-success" href="{% url 'dav_event_office:event-list' %}">Veranstaltungen</a>
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div class="col-sm-6">
|
||||
<div class="well">
|
||||
<p class="lead">Teilnehmer</p>
|
||||
<p>
|
||||
Fasel.
|
||||
<span class="glyphicon glyphicon-question-sign" title="
|
||||
Als Tourenleiter kannst du hier die Anmeldungen und Teilnehmerlisten zu deinen Touren verwalten.
|
||||
Tourenreferenten und Redakteure können hier Veranstaltungen freigeben und Programmlisten herunterladen.
|
||||
"></span>
|
||||
</p>
|
||||
<p>
|
||||
<a class="btn btn-success" href="{% url 'dav_event_office:event-list' %}">Teilnehmer</a>
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
0
dav_event_office/tests/__init__.py
Normal file
0
dav_event_office/tests/__init__.py
Normal file
9
dav_event_office/urls.py
Normal file
9
dav_event_office/urls.py
Normal file
@@ -0,0 +1,9 @@
|
||||
from django.conf.urls import url
|
||||
|
||||
from . import views
|
||||
|
||||
urlpatterns = [
|
||||
url(r'^home$', views.HomeView.as_view(), name='root'),
|
||||
url(r'^$', views.EventListView.as_view(), name='event-list'),
|
||||
url(r'^(?P<pk>\d+)/', views.EventDetailView.as_view(), name='event-detail'),
|
||||
]
|
||||
44
dav_event_office/views.py
Normal file
44
dav_event_office/views.py
Normal file
@@ -0,0 +1,44 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
from django.contrib.auth.decorators import login_required
|
||||
from django.core.exceptions import PermissionDenied
|
||||
from django.utils.decorators import method_decorator
|
||||
from django.views import generic
|
||||
|
||||
from dav_events.models import Event
|
||||
from dav_events.roles import has_role
|
||||
|
||||
|
||||
class HomeView(generic.TemplateView):
|
||||
template_name = 'dav_event_office/home.html'
|
||||
|
||||
|
||||
class OfficePermissionMixin(object):
|
||||
def enforce_permission(self, request):
|
||||
user = request.user
|
||||
if user.is_superuser:
|
||||
return None
|
||||
elif has_role(user, 'manager_super'):
|
||||
return None
|
||||
elif has_role(user, 'event_office'):
|
||||
return None
|
||||
raise PermissionDenied('event_office')
|
||||
|
||||
|
||||
class EventListView(OfficePermissionMixin, generic.ListView):
|
||||
model = Event
|
||||
template_name = 'dav_event_office/event_list.html'
|
||||
|
||||
@method_decorator(login_required)
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
self.enforce_permission(request)
|
||||
return super(EventListView, self).dispatch(request, *args, **kwargs)
|
||||
|
||||
|
||||
class EventDetailView(OfficePermissionMixin, generic.DetailView):
|
||||
model = Event
|
||||
template_name = 'dav_event_office/event_detail.html'
|
||||
|
||||
@method_decorator(login_required)
|
||||
def dispatch(self, request, *args, **kwargs):
|
||||
self.enforce_permission(request)
|
||||
return super(EventDetailView, self).dispatch(request, *args, **kwargs)
|
||||
Reference in New Issue
Block a user