Skip to content
Snippets Groups Projects
Commit b955cdd3 authored by Tom Teichler's avatar Tom Teichler :beers:
Browse files

Fix frontend for displays and dispay groups

parent 5e0b67c8
Branches 3-implement-basic-frontend
No related tags found
No related merge requests found
Showing
with 242 additions and 53 deletions
from django_filters import FilterSet
from .models.base import Display
class DisplaysFilter(FilterSet):
class Meta:
model = Display
fields = ["hostname"]
from django import forms
from django.utils.translation import gettext_lazy as _
from material import Fieldset, Layout, Row
from aleksis.core.mixins import ExtensibleForm
from .models.base import Display, DisplayGroup, Slide
from .models.slides import ForeignURLSlide, StaticContentSlide, UploadedFileSlide
class EditDisplayGroupForm(ExtensibleForm):
layout = Layout("name", "slug")
class Meta:
model = DisplayGroup
exclude = []
class EditDisplayForm(ExtensibleForm):
layout = Layout("hostname", "display_group")
class Meta:
model = Display
exclude = []
......@@ -3,9 +3,9 @@ from django.utils.translation import gettext_lazy as _
MENUS = {
"NAV_MENU_CORE": [
{
"name": _("Bülleten"),
"url": "empty",
"name": _("Digital signage"),
"root": True,
"url": "#",
"validators": [
"menu_generator.validators.is_authenticated",
"aleksis.core.util.core_helpers.has_person",
......@@ -21,16 +21,6 @@ MENUS = {
),
],
},
{
"name": _("Displays"),
"url": "displays",
"validators": [
(
"aleksis.core.util.predicates.permission_validator",
"buelleten.view_displays_rule",
),
],
},
],
}
]
......
# Generated by Django 3.2.13 on 2022-06-25 19:58
import aleksis.core.mixins
import ckeditor.fields
import django.contrib.sites.managers
import django.core.validators
from django.db import migrations, models
import django.db.models.deletion
class Migration(migrations.Migration):
initial = True
dependencies = [
('contenttypes', '0002_remove_content_type_name'),
('sites', '0002_alter_domain_unique'),
]
operations = [
migrations.CreateModel(
name='DisplayGroup',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('extended_data', models.JSONField(default=dict, editable=False)),
('name', models.CharField(max_length=255, verbose_name='Name')),
('slug', models.SlugField(max_length=255, verbose_name='Slug')),
('site', models.ForeignKey(default=1, editable=False, on_delete=django.db.models.deletion.CASCADE, to='sites.site')),
],
options={
'abstract': False,
},
managers=[
('objects', django.contrib.sites.managers.CurrentSiteManager()),
],
),
migrations.CreateModel(
name='Slide',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('display_group', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='buelleten.displaygroup', verbose_name='Display group')),
('polymorphic_ctype', models.ForeignKey(editable=False, null=True, on_delete=django.db.models.deletion.CASCADE, related_name='polymorphic_buelleten.slide_set+', to='contenttypes.contenttype')),
],
options={
'abstract': False,
'base_manager_name': 'objects',
},
bases=(models.Model, aleksis.core.mixins.PureDjangoModel),
),
migrations.CreateModel(
name='ForeignURLSlide',
fields=[
('slide_ptr', models.OneToOneField(auto_created=True, on_delete=django.db.models.deletion.CASCADE, parent_link=True, primary_key=True, serialize=False, to='buelleten.slide')),
('url', models.URLField(max_length=255, verbose_name='URL')),
],
options={
'abstract': False,
'base_manager_name': 'objects',
},
bases=('buelleten.slide',),
),
migrations.CreateModel(
name='StaticContentSlide',
fields=[
('slide_ptr', models.OneToOneField(auto_created=True, on_delete=django.db.models.deletion.CASCADE, parent_link=True, primary_key=True, serialize=False, to='buelleten.slide')),
('content', ckeditor.fields.RichTextField(verbose_name='Content')),
],
options={
'abstract': False,
'base_manager_name': 'objects',
},
bases=('buelleten.slide',),
),
migrations.CreateModel(
name='UploadedFileSlide',
fields=[
('slide_ptr', models.OneToOneField(auto_created=True, on_delete=django.db.models.deletion.CASCADE, parent_link=True, primary_key=True, serialize=False, to='buelleten.slide')),
('file', models.FileField(upload_to='paweljong/uploaded_file_slides/', validators=[django.core.validators.FileExtensionValidator(allowed_extensions=['pdf', 'jpg', 'jpeg', 'png', 'tif', 'bmp', 'ppm', 'avi', 'mov', 'mp4', 'mkv', 'webm', 'ogv', 'mpg', 'mpeg', 'ts', 'flv'])])),
],
options={
'abstract': False,
'base_manager_name': 'objects',
},
bases=('buelleten.slide',),
),
migrations.CreateModel(
name='Display',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('extended_data', models.JSONField(default=dict, editable=False)),
('hostname', models.CharField(max_length=255, verbose_name='Hostname')),
('display_group', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='buelleten.displaygroup', verbose_name='Display group')),
('site', models.ForeignKey(default=1, editable=False, on_delete=django.db.models.deletion.CASCADE, to='sites.site')),
],
options={
'abstract': False,
},
managers=[
('objects', django.contrib.sites.managers.CurrentSiteManager()),
],
),
]
from django.db import models
from django.utils.translation import gettext_lazy as _
from polymorphic.models import PolymorphicModel
from aleksis.core.mixins import ExtensibleModel
from aleksis.core.mixins import ExtensibleModel, PureDjangoModel
class DisplayGroup(ExtensibleModel):
......@@ -10,13 +11,23 @@ class DisplayGroup(ExtensibleModel):
name = models.CharField(max_length=255, verbose_name=_("Name"))
slug = models.SlugField(max_length=255, verbose_name=_("Slug"))
def __str__(self) -> str:
return self.name
class Display(ExtensibleModel):
display_group = models.ForeignKey(DisplayGroup, verbose_name=_("Display group"))
display_group = models.ForeignKey(
DisplayGroup, verbose_name=_("Display group"), on_delete=models.CASCADE
)
hostname = models.CharField(max_length=255, verbose_name=_("Hostname"))
def __str__(self) -> str:
return self.hostname
class Slide(PolymorphicModel, PureDjangoModel):
display_group = models.ForeignKey(DisplayGroup, verbose_name=_("Display group"))
display_group = models.ForeignKey(
DisplayGroup, verbose_name=_("Display group"), on_delete=models.CASCADE
)
......@@ -36,7 +36,7 @@ class UploadedFileSlide(Slide):
file = models.FileField(
upload_to="paweljong/uploaded_file_slides/",
validators=[FileExtensionValidator(allowed_extensions=self.TYPES)],
validators=[FileExtensionValidator(allowed_extensions=TYPES)],
)
......
......@@ -19,9 +19,7 @@ rules.add_perm("paweljong.view_displays_rule", view_displays_predicate)
# View display
view_display_predicate = has_person & (
is_own_display
| has_global_perm("paweljong.view_display")
| has_object_perm("paweljong.view_display")
has_global_perm("paweljong.view_display") | has_object_perm("paweljong.view_display")
)
rules.add_perm("paweljong.view_display_rule", view_display_predicate)
......@@ -54,8 +52,7 @@ rules.add_perm("paweljong.view_display_groups_rule", view_display_groups_predica
# View display_group
view_display_group_predicate = has_person & (
is_own_display_group
| has_global_perm("paweljong.view_display_group")
has_global_perm("paweljong.view_display_group")
| has_object_perm("paweljong.view_display_group")
)
rules.add_perm("paweljong.view_display_group_rule", view_display_group_predicate)
......
......@@ -4,11 +4,11 @@ import django_tables2 as tables
from django_tables2.utils import A
class DisplayGroupTable(tables.Table):
class DisplayGroupsTable(tables.Table):
class Meta:
attrs = {"class": "highlight"}
name = tables.LinkColumn("edit_display_group", args=[A("id")])
name = tables.LinkColumn("display_group_by_id", args=[A("id")])
slug = tables.Column()
edit = tables.LinkColumn(
"edit_display_group",
......@@ -19,7 +19,7 @@ class DisplayGroupTable(tables.Table):
)
class DisplayTable(tables.Table):
class DisplaysTable(tables.Table):
class Meta:
attrs = {"class": "highlight"}
......
{# -*- engine:django -*- #}
{% extends "core/base.html" %}
{% load i18n rules %}
{% load render_table from django_tables2 %}
{% block browser_title %}{% blocktrans %}Displays{% endblocktrans %}{% endblock %}
{% block page_title %}{% blocktrans %}Displays{% endblocktrans %}{% endblock %}
{% block content %}
{% has_perm 'core.create_display_rule' user displaygroup as can_create_display %}
{% if can_create_display %}
<a class="btn green waves-effect waves-light" href="{% url 'create_display' %}">
<i class="material-icons iconify left" data-icon="mdi:add"></i>
{% trans "Create display" %}
</a>
{% endif %}
<h2>{% trans "Displays" %}</h2>
{% render_table table %}
{% endblock %}
{# -*- engine:django -*- #}
{% extends "core/base.html" %}
{% load i18n rules material_form %}
{% load render_table from django_tables2 %}
{% block browser_title %}{% blocktrans %}Display group{% endblocktrans %} {{ object }}{% endblock %}
{% block page_title %}{% blocktrans %}Display group{% endblocktrans %} {{ object }}{% endblock %}
{% block content %}
{% has_perm 'core.create_display_rule' user displaygroup as can_create_display %}
<h5>{% trans "Connected displays" %}</h5>
<form method="get">
{% form form=displays_filter.form %}{% endform %}
{% trans "Search" as caption %}
{% include "core/partials/save_button.html" with caption=caption icon="search" %}
<button type="reset" class="btn red waves-effect waves-light">
<i class="material-icons left">clear</i>
{% trans "Clear" %}
</button>
{% if can_create_display %}
<a class="btn green waves-effect waves-light" href="{% url 'create_display' %}">
<i class="material-icons iconify left" data-icon="mdi:add"></i>
{% trans "Create display" %}
</a>
{% endif %}
</form>
{% render_table displays_table %}
{% endblock %}
......@@ -18,6 +18,5 @@
</a>
{% endif %}
<h2>{% trans "Display groups" %}</h2>
{% render_table table %}
{% endblock %}
......@@ -10,7 +10,12 @@ urlpatterns = [
name="create_display_group",
),
path(
"display_groups/<int:pk>/", views.DisplayGroupEditView.as_view(), name="edit_display_group"
"display_groups/<int:pk>/edit",
views.DisplayGroupEditView.as_view(),
name="edit_display_group",
),
path(
"display_groups/<int:pk>/", views.DisplayGroupFullView.as_view(), name="display_group_by_id"
),
path("displays/", views.DisplayListView.as_view(), name="displays"),
path("displays/create/", views.DisplayCreateView.as_view(), name="create_display"),
......
from django.urls import reverse_lazy
from django.utils.decorators import method_decorator
from django.utils.translation import gettext_lazy as _
from django.views.decorators.cache import never_cache
from django.views.generic.detail import DetailView
from django_tables2 import RequestConfig, SingleTableView
from rules.contrib.views import PermissionRequiredMixin
from aleksis.core.mixins import (
AdvancedCreateView,
AdvancedDeleteView,
AdvancedEditView,
SuccessNextMixin,
)
from .filters import DisplaysFilter
from .forms import EditDisplayForm, EditDisplayGroupForm
from .models.base import Display, DisplayGroup, Slide
from .models.slides import ForeignURLSlide, StaticContentSlide, UploadedFileSlide
from .tables import DisplayGroupsTable, DisplaysTable
class DisplayListView(PermissionRequ0iredMixin, SingleTableView):
class DisplayListView(PermissionRequiredMixin, SingleTableView):
"""Table of all displays."""
model = Displays
model = Display
table_class = DisplaysTable
permission_required = "buelleten.view_displays_rule"
template_name = "buelleten/display/list.html"
......@@ -45,10 +64,30 @@ class DisplayDeleteView(PermissionRequiredMixin, AdvancedDeleteView):
success_message = _("The display has been deleted.")
class DisplayGroupListView(PermissionRequ0iredMixin, SingleTableView):
class DisplayGroupFullView(PermissionRequiredMixin, DetailView):
model = DisplayGroup
template_name = "buelleten/display_group/full.html"
permission_required = "buelleten.view_display_group_rule"
def get_context_data(self, *args, **kwargs):
context = super().get_context_data(*args, **kwargs)
displays = Display.objects.filter(display_group=self.get_object())
displays_filter = DisplaysFilter(self.request.GET, queryset=displays)
context["displays_filter"] = displays_filter
displays_table = DisplaysTable(displays_filter.qs)
RequestConfig(self.request).configure(displays_table)
context["displays_table"] = displays_table
return context
class DisplayGroupListView(PermissionRequiredMixin, SingleTableView):
"""Table of all display groups."""
model = DisplayGroups
model = DisplayGroup
table_class = DisplayGroupsTable
permission_required = "buelleten.view_display_groups_rule"
template_name = "buelleten/display_group/list.html"
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment