diff --git a/changelog.d/+polish-profiles-page.changed.md b/changelog.d/+polish-profiles-page.changed.md new file mode 100644 index 000000000..9dca50bc3 --- /dev/null +++ b/changelog.d/+polish-profiles-page.changed.md @@ -0,0 +1 @@ +Polished the looks of the profiles page. diff --git a/src/argus/htmx/notificationprofile/views.py b/src/argus/htmx/notificationprofile/views.py index 6662458d0..9d8f0c98f 100644 --- a/src/argus/htmx/notificationprofile/views.py +++ b/src/argus/htmx/notificationprofile/views.py @@ -5,16 +5,26 @@ """ from django import forms +from django.shortcuts import redirect from django.urls import reverse from django.views.generic import CreateView, DeleteView, DetailView, ListView, UpdateView from argus.notificationprofile.models import NotificationProfile, Timeslot, Filter, DestinationConfig -class NotificationProfileForm(forms.ModelForm): +class NoColonMixin: + def __init__(self, *args, **kwargs): + kwargs.setdefault("label_suffix", "") + super().__init__(*args, **kwargs) + + +class NotificationProfileForm(NoColonMixin, forms.ModelForm): class Meta: model = NotificationProfile fields = ["name", "timeslot", "filters", "active", "destinations"] + widgets = { + "timeslot": forms.Select(attrs={"class": "select input-bordered w-full max-w-xs"}), + } def __init__(self, *args, **kwargs): user = kwargs.pop("user") @@ -22,6 +32,8 @@ def __init__(self, *args, **kwargs): self.fields["timeslot"].queryset = Timeslot.objects.filter(user=user) self.fields["filters"].queryset = Filter.objects.filter(user=user) self.fields["destinations"].queryset = DestinationConfig.objects.filter(user=user) + self.fields["active"].widget.attrs["class"] = "checkbox checkbox-sm checkbox-accent border" + self.fields["name"].widget.attrs["class"] = "input input-bordered" class NotificationProfileMixin: @@ -78,11 +90,20 @@ def form_valid(self, form): class NotificationProfileListView(NotificationProfileMixin, ListView): - pass + def get_context_data(self, **kwargs): + context = super().get_context_data(**kwargs) + forms = [] + for obj in self.get_queryset(): + form = NotificationProfileForm(None, user=self.request.user, instance=obj) + forms.append(form) + context["form_list"] = forms + return context class NotificationProfileDetailView(NotificationProfileMixin, DetailView): - pass + def dispatch(self, request, *args, **kwargs): + object = self.get_object() + return redirect("htmx:notificationprofile-update", pk=object.pk) class NotificationProfileCreateView(ChangeMixin, NotificationProfileMixin, CreateView): diff --git a/src/argus/htmx/static/styles.css b/src/argus/htmx/static/styles.css index ae4a92895..a9b3e5010 100644 --- a/src/argus/htmx/static/styles.css +++ b/src/argus/htmx/static/styles.css @@ -4160,6 +4160,11 @@ details.collapse summary::-webkit-details-marker { margin-bottom: 0.25rem; } +.my-4 { + margin-top: 1rem; + margin-bottom: 1rem; +} + .-ml-2 { margin-left: -0.5rem; } @@ -4374,6 +4379,10 @@ details.collapse summary::-webkit-details-marker { justify-content: flex-start; } +.justify-end { + justify-content: flex-end; +} + .justify-center { justify-content: center; } @@ -4544,6 +4553,10 @@ details.collapse summary::-webkit-details-marker { padding-bottom: 0.5rem; } +.text-center { + text-align: center; +} + .text-start { text-align: start; } @@ -4576,6 +4589,10 @@ details.collapse summary::-webkit-details-marker { font-weight: 500; } +.font-semibold { + font-weight: 600; +} + .capitalize { text-transform: capitalize; } @@ -4645,6 +4662,12 @@ details.collapse summary::-webkit-details-marker { box-shadow: var(--tw-ring-offset-shadow, 0 0 #0000), var(--tw-ring-shadow, 0 0 #0000), var(--tw-shadow); } +.shadow-2xl { + --tw-shadow: 0 25px 50px -12px rgb(0 0 0 / 0.25); + --tw-shadow-colored: 0 25px 50px -12px var(--tw-shadow-color); + box-shadow: var(--tw-ring-offset-shadow, 0 0 #0000), var(--tw-ring-shadow, 0 0 #0000), var(--tw-shadow); +} + .shadow-xl { --tw-shadow: 0 20px 25px -5px rgb(0 0 0 / 0.1), 0 8px 10px -6px rgb(0 0 0 / 0.1); --tw-shadow-colored: 0 20px 25px -5px var(--tw-shadow-color), 0 8px 10px -6px var(--tw-shadow-color); diff --git a/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_buttons.html b/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_buttons.html index 478b5b256..3c3208622 100644 --- a/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_buttons.html +++ b/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_buttons.html @@ -1,16 +1,7 @@ -
- {% if show_view %} -

- View -

- {% endif %} -

- Update -

-

+

+ +
diff --git a/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_detail.html b/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_detail.html deleted file mode 100644 index 4f1b03082..000000000 --- a/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_detail.html +++ /dev/null @@ -1,16 +0,0 @@ -
-

{{ object.name|default:object.timeslot.name }}

-
-

Active? {{ object.active }}

-

Timeslot: {{ object.timeslot }}

-

- Filters: - {% for filter_obj in object.filters.all %}{{ filter_obj }}{% endfor %} -

-

- Destinations: - {% for destination in object.destinations.all %}{{ destination }}{% endfor %} -

- {% include "./_notificationprofile_buttons.html" %} -
-
diff --git a/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_form.html b/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_form.html new file mode 100644 index 000000000..14f189ee6 --- /dev/null +++ b/src/argus/htmx/templates/htmx/notificationprofile/_notificationprofile_form.html @@ -0,0 +1,9 @@ +
+
+ {% csrf_token %} + {{ form.as_div }} + {% include "./_notificationprofile_buttons.html" with object=form.instance %} +
+
diff --git a/src/argus/htmx/templates/htmx/notificationprofile/base.html b/src/argus/htmx/templates/htmx/notificationprofile/base.html index c542f25e0..7a56355cb 100644 --- a/src/argus/htmx/templates/htmx/notificationprofile/base.html +++ b/src/argus/htmx/templates/htmx/notificationprofile/base.html @@ -1,5 +1,8 @@ {% extends "htmx/base.html" %} {% block main %} - {% block profile_main %} - {% endblock profile_main %} +

Profiles

+
+ {% block profile_main %} + {% endblock profile_main %} +
{% endblock main %} diff --git a/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_detail.html b/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_detail.html deleted file mode 100644 index 563599800..000000000 --- a/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_detail.html +++ /dev/null @@ -1,6 +0,0 @@ -{% extends "./base.html" %} -{% block profile_main %} - {% with show_buttons=True %} - {% include "./_notificationprofile_detail.html" %} - {% endwith %} -{% endblock profile_main %} diff --git a/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_form.html b/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_form.html index fd6476f92..5ed69ebe9 100644 --- a/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_form.html +++ b/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_form.html @@ -1,8 +1,6 @@ {% extends "./base.html" %} {% block profile_main %} -
- {% csrf_token %} - {{ form.as_div }} - -
+
+ {% include "./_notificationprofile_form.html" %} +
{% endblock profile_main %} diff --git a/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_list.html b/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_list.html index e9c32e361..cc2452cc6 100644 --- a/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_list.html +++ b/src/argus/htmx/templates/htmx/notificationprofile/notificationprofile_list.html @@ -1,12 +1,12 @@ {% extends "./base.html" %} {% block profile_main %}
-

+ + {% for form in form_list %} +

{% include "./_notificationprofile_form.html" %}
{% endfor %}
{% endblock profile_main %} diff --git a/src/argus/htmx/widgets.py b/src/argus/htmx/widgets.py index a33abf51c..e038995fe 100644 --- a/src/argus/htmx/widgets.py +++ b/src/argus/htmx/widgets.py @@ -22,6 +22,19 @@ class DropdownMultiSelect(ExtraWidgetMixin, forms.CheckboxSelectMultiple): template_name = "htmx/forms/dropdown_select_multiple.html" option_template_name = "htmx/forms/checkbox_select_multiple.html" + def get_context(self, name, value, attrs): + context = super().get_context(name, value, attrs) + widget_value = context["widget"]["value"] + context["widget"]["has_selected"] = self.has_selected(name, widget_value, attrs) + return context + + def has_selected(self, name, value, attrs): + for _, options, _ in self.optgroups(name, value, attrs): + for option in options: + if option.get("selected", False): + return option.get("selected", False) + return False + class BadgeDropdownMultiSelect(DropdownMultiSelect): template_name = "htmx/forms/badge_dropdown_select_multiple.html"