Skip to content
Snippets Groups Projects
Commit 9afafa02 authored by jan.bednarik's avatar jan.bednarik
Browse files

donate: Targeted donations

parent 31e660dc
No related branches found
No related tags found
2 merge requests!49donate: Targeted donations,!48donate: Targeted donations
Pipeline #899 passed
......@@ -12,6 +12,7 @@ class DonateForm(forms.Form):
amount = forms.IntegerField()
custom_amount = forms.IntegerField(required=False)
periodicity = forms.IntegerField()
portal_project_id = forms.IntegerField()
def clean_periodicity(self):
value = self.cleaned_data["periodicity"]
......@@ -27,9 +28,10 @@ class DonateForm(forms.Form):
)
return amount
def get_redirect_url(self, portal_project_id):
def get_redirect_url(self):
amount = self.get_amount()
periodicity = self.cleaned_data["periodicity"]
portal_project_id = self.cleaned_data["portal_project_id"]
query = urllib.parse.urlencode(
{
"amount": amount,
......
# Generated by Django 3.0.8 on 2020-07-15 12:15
import django.db.models.deletion
import wagtail.core.blocks
import wagtail.core.fields
import wagtailmetadata.models
from django.db import migrations, models
import donate.models
class Migration(migrations.Migration):
dependencies = [
("wagtailcore", "0045_assign_unlock_grouppagepermission"),
("wagtailimages", "0022_uploadedimage"),
("donate", "0004_auto_20200621_2349"),
]
operations = [
migrations.RemoveField(model_name="donateregionpage", name="perex",),
migrations.CreateModel(
name="DonateTargetedDonationsPage",
fields=[
(
"page_ptr",
models.OneToOneField(
auto_created=True,
on_delete=django.db.models.deletion.CASCADE,
parent_link=True,
primary_key=True,
serialize=False,
to="wagtailcore.Page",
),
),
(
"targeted_donations",
wagtail.core.fields.StreamField(
[
(
"item",
wagtail.core.blocks.StructBlock(
[
(
"title",
wagtail.core.blocks.CharBlock(
label="název"
),
),
(
"description",
wagtail.core.blocks.CharBlock(
label="popis", required=False
),
),
(
"portal_project_id",
wagtail.core.blocks.IntegerBlock(
label="ID projektu v darovacím portálu",
required=False,
),
),
]
),
)
],
blank=True,
verbose_name="adresné dary",
),
),
(
"search_image",
models.ForeignKey(
blank=True,
null=True,
on_delete=django.db.models.deletion.SET_NULL,
related_name="+",
to="wagtailimages.Image",
verbose_name="Search image",
),
),
],
options={"abstract": False,},
bases=(
"wagtailcore.page",
donate.models.SubpageMixin,
wagtailmetadata.models.MetadataMixin,
models.Model,
),
),
]
......@@ -7,6 +7,7 @@ from wagtail.admin.edit_handlers import (
MultiFieldPanel,
StreamFieldPanel,
)
from wagtail.core import blocks
from wagtail.core.fields import RichTextField, StreamField
from wagtail.core.models import Page
from wagtail.images.blocks import ImageChooserBlock
......@@ -21,10 +22,13 @@ from .forms import DonateForm
class SubpageMixin:
"""Must be used in class definition before MetadataPageMixin!"""
# flag for rendering anchor links in menu
is_home = False
@property
def root_page(self):
if not hasattr(self, "_root_page"):
self._root_page = self.get_parent().specific
self._root_page = self.get_ancestors().type(DonateHomePage).specific().get()
return self._root_page
def get_meta_image(self):
......@@ -45,7 +49,7 @@ class DonateFormMixin(models.Model):
if request.method == "POST":
form = DonateForm(request.POST)
if form.is_valid():
url = form.get_redirect_url(self.portal_project_id)
url = form.get_redirect_url()
return redirect(url)
return super().serve(request)
......@@ -62,6 +66,8 @@ def get_url(page, dest_page_type):
class DonateHomePage(DonateFormMixin, Page, MetadataPageMixin):
### FIELDS
# lead section
lead_title = models.CharField("hlavní nadpis", max_length=250, blank=True)
lead_body = models.TextField("hlavní popis", blank=True)
......@@ -93,6 +99,8 @@ class DonateHomePage(DonateFormMixin, Page, MetadataPageMixin):
"Matomo ID pro sledování návštěvnosti", blank=True, null=True
)
### PANELS
content_panels = Page.content_panels + [
MultiFieldPanel(
[
......@@ -140,6 +148,8 @@ class DonateHomePage(DonateFormMixin, Page, MetadataPageMixin):
FieldPanel("portal_project_id"),
]
### RELATIONS
subpage_types = [
"donate.DonateRegionIndexPage",
"donate.DonateProjectIndexPage",
......@@ -147,6 +157,8 @@ class DonateHomePage(DonateFormMixin, Page, MetadataPageMixin):
"donate.DonateCookiesPage",
]
### OTHERS
# flag for rendering anchor links in menu
is_home = True
......@@ -196,6 +208,8 @@ class DonateHomePage(DonateFormMixin, Page, MetadataPageMixin):
class DonateRegionIndexPage(Page, SubpageMixin, MetadataPageMixin):
### PANELS
promote_panels = [
MultiFieldPanel(
[
......@@ -211,11 +225,12 @@ class DonateRegionIndexPage(Page, SubpageMixin, MetadataPageMixin):
settings_panels = []
### RELATIONS
parent_page_types = ["donate.DonateHomePage"]
subpage_types = ["donate.DonateRegionPage"]
# flag for rendering anchor links in menu
is_home = False
### OTHERS
class Meta:
verbose_name = "Přehled krajů"
......@@ -227,11 +242,13 @@ class DonateRegionIndexPage(Page, SubpageMixin, MetadataPageMixin):
class DonateRegionPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
# TODO remove if not needed anymore
perex = models.TextField("krátký popis do přehledu krajů")
### FIELDS
main_title = models.CharField("hlavní nadpis na stránce", max_length=250)
body = RichTextField("obsah")
### PANELS
content_panels = Page.content_panels + [
FieldPanel("main_title"),
FieldPanel("body", classname="full"),
......@@ -258,31 +275,31 @@ class DonateRegionPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
settings_panels = [FieldPanel("portal_project_id")]
### RELATIONS
parent_page_types = ["donate.DonateRegionIndexPage"]
subpage_types = []
subpage_types = ["donate.DonateTargetedDonationsPage"]
# flag for rendering anchor links in menu
is_home = False
### OTHERS
class Meta:
verbose_name = "Kraj"
@property
def root_page(self):
if not hasattr(self, "_root_page"):
self._root_page = self.get_ancestors().type(DonateHomePage).specific().get()
return self._root_page
def get_meta_title(self):
return self.seo_title or self.main_title
def get_context(self, request):
context = super().get_context(request)
context["other_regions"] = self.get_siblings(inclusive=False).live()
return context
@property
def targeted_donations_page_url(self):
return get_url(self, DonateTargetedDonationsPage)
@property
def has_targeted_donations(self):
return self.get_descendants().type(DonateTargetedDonationsPage).live().exists()
class DonateProjectIndexPage(Page, SubpageMixin, MetadataPageMixin):
### PANELS
promote_panels = [
MultiFieldPanel(
[
......@@ -298,11 +315,12 @@ class DonateProjectIndexPage(Page, SubpageMixin, MetadataPageMixin):
settings_panels = []
### RELATIONS
parent_page_types = ["donate.DonateHomePage"]
subpage_types = ["donate.DonateProjectPage"]
# flag for rendering anchor links in menu
is_home = False
### OTHERS
class Meta:
verbose_name = "Přehled projektů"
......@@ -316,6 +334,8 @@ class DonateProjectIndexPage(Page, SubpageMixin, MetadataPageMixin):
class DonateProjectPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
### FIELDS
date = models.DateField("běží od")
perex = models.TextField("krátký popis")
body = RichTextField("obsah")
......@@ -335,6 +355,8 @@ class DonateProjectPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
# we will use photo as search image
search_image = None
### PANELS
content_panels = Page.content_panels + [
MultiFieldPanel(
[FieldPanel("is_new"), FieldPanel("perex"), ImageChooserPanel("photo")],
......@@ -366,21 +388,16 @@ class DonateProjectPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
settings_panels = Page.settings_panels + [FieldPanel("portal_project_id")]
### RELATIONS
parent_page_types = ["donate.DonateProjectIndexPage"]
subpage_types = []
# flag for rendering anchor links in menu
is_home = False
### OTHERS
class Meta:
verbose_name = "Projekt"
@property
def root_page(self):
if not hasattr(self, "_root_page"):
self._root_page = self.get_ancestors().type(DonateHomePage).specific().get()
return self._root_page
def get_meta_image(self):
return self.photo
......@@ -406,8 +423,12 @@ class DonateProjectPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
class DonateCookiesPage(Page, SubpageMixin, MetadataPageMixin):
### FIELDS
body = RichTextField("obsah", blank=True)
### PANELS
content_panels = Page.content_panels + [
FieldPanel("body", classname="full"),
]
......@@ -427,19 +448,24 @@ class DonateCookiesPage(Page, SubpageMixin, MetadataPageMixin):
settings_panels = []
### RELATIONS
parent_page_types = ["donate.DonateHomePage"]
subpage_types = []
# flag for rendering anchor links in menu
is_home = False
### OTHERS
class Meta:
verbose_name = "Cookies"
class DonateInfoPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
### FIELDS
body = RichTextField("obsah", blank=True)
### PANELS
content_panels = Page.content_panels + [
FieldPanel("body", classname="full"),
]
......@@ -459,11 +485,12 @@ class DonateInfoPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
settings_panels = []
### RELATIONS
parent_page_types = ["donate.DonateHomePage"]
subpage_types = []
# flag for rendering anchor links in menu
is_home = False
### OTHERS
class Meta:
verbose_name = "Info"
......@@ -472,3 +499,64 @@ class DonateInfoPage(DonateFormMixin, Page, SubpageMixin, MetadataPageMixin):
@property
def portal_project_id(self):
return self.get_parent().specific.portal_project_id
class TargetedDonationBlock(blocks.StructBlock):
title = blocks.CharBlock(label="název")
description = blocks.CharBlock(label="popis", required=False)
portal_project_id = blocks.IntegerBlock(
label="ID projektu v darovacím portálu",
required=False,
help_text="Pokud není zadáno ID projektu, tak se adresný dar nezobrazí.",
)
class Meta:
label = "adresný dar"
class DonateTargetedDonationsPage(
DonateFormMixin, Page, SubpageMixin, MetadataPageMixin
):
### FIELDS
targeted_donations = StreamField(
[("item", TargetedDonationBlock())], verbose_name="adresné dary", blank=True
)
# page does not have specific portal_project_id
portal_project_id = None
### PANELS
content_panels = Page.content_panels + [
StreamFieldPanel("targeted_donations"),
]
promote_panels = [
MultiFieldPanel(
[
FieldPanel("slug"),
FieldPanel("seo_title"),
FieldPanel("search_description"),
ImageChooserPanel("search_image"),
HelpPanel(help.build(help.NO_SEO_TITLE, help.NO_SEARCH_IMAGE)),
],
gettext_lazy("Common page configuration"),
),
]
settings_panels = []
### RELATIONS
parent_page_types = ["donate.DonateRegionPage"]
subpage_types = []
### OTHERS
class Meta:
verbose_name = "Adresné dary"
@property
def show_donate_form(self):
return bool(self.targeted_donations)
......@@ -227,6 +227,10 @@ section {
padding-bottom: 0rem;
}
.section--form {
padding-top: 2rem;
}
@media screen and (max-width: 991px) {
section {
padding: 3.5rem 0rem;
......@@ -729,6 +733,11 @@ footer h1, footer h2, footer h3, footer h4, footer h5, footer h6 {
box-shadow: 0 0 0 .2rem rgba(0, 255, 147, 0.25);
}
.custom-control-label {
line-height: 1.2;
padding-top: .7rem;
}
.custom-control-label::after {
top: .5rem;
left: -2.5rem;
......
......@@ -48,6 +48,7 @@
<div class="donate-form__right">
<form id="js-donate-form" method="post">
{% csrf_token %}
<input type="hidden" name="portal_project_id" value="{{ page.portal_project_id }}">
<div class="form-group row mb-4 align-items-center">
<legend class="col-form-label col-md-4 col-form-label-lg">Částka</legend>
<div class="col-md-8">
......
......@@ -33,6 +33,7 @@
{% if page.show_donate_form %}
<form id="js-donate-form" method="post">
{% csrf_token %}
<input type="hidden" name="portal_project_id" value="{{ page.portal_project_id }}">
<div class="form-group row mb-2 align-items-center">
<legend class="col-form-label col-md-12 col-form-label-lg">Částka</legend>
<div class="col-md-12">
......
......@@ -71,6 +71,7 @@
{% if page.show_donate_form %}
<form id="js-donate-form" method="post">
{% csrf_token %}
<input type="hidden" name="portal_project_id" value="{{ page.portal_project_id }}">
<div class="form-group row mb-2 align-items-center">
<legend class="col-form-label col-md-12 col-form-label-lg">Částka</legend>
<div class="col-md-12">
......
......@@ -17,7 +17,14 @@
<div class="row">
<div class="col-12 col-lg-7 mb-5 mb-lg-0 richtext">
<div class="row">
{{ page.body|richtext }}
</div>
{% if page.has_targeted_donations %}
<div class="row my-4">
<a href="{{ page.targeted_donations_page_url }}" class="btn btn-dark btn-lg my-2">Adresné dary pro kraj <i class="icon-chevron-right ml-2"></i></a>
</div>
{% endif %}
</div><!-- /column -->
<div class="col-12 col-lg-5 col-xl-4 offset-xl-1"><!-- /column -->
......@@ -33,6 +40,7 @@
{% if page.show_donate_form %}
<form id="js-donate-form" method="post">
{% csrf_token %}
<input type="hidden" name="portal_project_id" value="{{ page.portal_project_id }}">
<div class="form-group row mb-2 align-items-center">
<legend class="col-form-label col-md-12 col-form-label-lg">Částka</legend>
<div class="col-md-12">
......
{% extends "donate/base.html" %}
{% load wagtailcore_tags %}
{% block content %}
<!-- CONTENT -->
<main role="main">
<section class="section--alternate region__header">
<div class="container">
<h1 class="lead heading">{{ page.title }}</h1>
</div> <!-- /container -->
</section>
<section class="section--primary section--form">
<div class="container">
{% if page.show_donate_form %}
<form id="js-donate-form" method="post">
{% csrf_token %}
<div class="form-group row mb-4 align-items-center">
<div class="col-12">
{% for target in page.targeted_donations %}
{% if target.value.portal_project_id %}
<div class="custom-control custom-radio my-3">
<input type="radio" id="target{{ forloop.counter }}" name="portal_project_id" value="{{ target.value.portal_project_id }}" class="custom-control-input"{% if forloop.first %} checked required{% endif %}>
<label class="custom-control-label col-form-label-lg" for="target{{ forloop.counter }}">{{ target.value.title }}<br> <span class="small">{{ target.value.description }}</span></label>
</div>
{% endif %}
{% endfor %}
</div>
</div>
<div class="form-group row mb-4 align-items-center">
<legend class="col-form-label col-md-3 col-form-label-lg">Částka</legend>
<div class="col-md-9">
<div class="custom-control custom-radio custom-control-inline">
<input type="radio" id="amount1" name="amount" value="100" class="custom-control-input" checked required>
<label class="custom-control-label col-form-label-lg" for="amount1">100 Kč</label>
</div>
<div class="custom-control custom-radio custom-control-inline">
<input type="radio" id="amount2" name="amount" value="200" class="custom-control-input">
<label class="custom-control-label col-form-label-lg" for="amount2">200 Kč</label>
</div>
<div class="custom-control custom-radio custom-control-inline">
<input type="radio" id="amount3" name="amount" value="500" class="custom-control-input">
<label class="custom-control-label col-form-label-lg" for="amount3">500 Kč</label>
</div>
<div class="custom-control custom-radio custom-control-inline">
<input type="radio" id="amount4" name="amount" value="-1" class="custom-control-input">
<label class="custom-control-label col-form-label-lg" for="amount4">Jiná částka</label>
</div>
</div>
</div>
<div class="form-group row mb-4 align-items-center" id="js-custom-amount-input" style="display: none;">
<div class="offset-md-3 col-md-9">
<div class="input-group input-group-lg mb-3 custom-amount">
<input type="number" class="form-control" id="customamount" name="custom_amount" placeholder="1000" aria-describedby="customamount-currency">
<div class="input-group-append">
<span class="input-group-text" id="customamount-currency"></span>
</div>
</div>
</div>
</div>
<div class="form-group row mb-4 align-items-center">
<legend class="col-form-label col-md-3 col-form-label-lg">Typ příspěvku</legend>
<div class="col-md-9">
<div class="custom-control custom-radio custom-control-inline">
<input type="radio" id="periodicity1" name="periodicity" value="730" class="custom-control-input" checked required>
<label class="custom-control-label col-form-label-lg" for="periodicity1">Měsíční</label>
</div>
<div class="custom-control custom-radio custom-control-inline">
<input type="radio" id="periodicity2" name="periodicity" value="99999" class="custom-control-input">
<label class="custom-control-label col-form-label-lg" for="periodicity2">Jednorázový</label>
</div>
</div>
</div>
<div class="form-group row mb-0">
<div class="col-12">
<button type="submit" class="btn btn-danger btn-lg">Darovat</button>
</div>
</div>
</form>
{% else %}
<div class="row mb-4 donate-form">
<p>Krajské sdružení momentálně nepřijímá adresné dary. Místo toho <a href="{% pageurl page.get_parent %}">podpořte celý kraj!</a></p>
</div>
{% endif %}
</div> <!-- /container -->
</section>
</main>
<!-- /CONTENT -->
{% endblock %}
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment