diff --git a/district/blocks.py b/district/blocks.py index f17fee7a69f0b661191a65be9926a1099e8b4d58..85ddbfc65ec439c61d11090ab9a4a1285784be65 100644 --- a/district/blocks.py +++ b/district/blocks.py @@ -1,4 +1,3 @@ -from django.db import models from django.forms.utils import ErrorList from wagtail import blocks from wagtail.blocks import ( @@ -16,10 +15,8 @@ from wagtail.blocks.struct_block import StructBlockValidationError from wagtail.images.blocks import ImageChooserBlock from shared.blocks import ( - ButtonBlock, CardLinkBlockMixin, CardLinkWithHeadlineBlockMixin, - ChartBlock, ProgramItemBlock, ) @@ -296,3 +293,49 @@ class RedmineProgramBlock(StructBlock): template = "district/blocks/program_block.html" icon = "site" label = "Blok programu stahovaný z Redmine" + + +class HeroBannerBlock(StructBlock): + sm_banner = ImageChooserBlock( + label="Obrázek pro zobrazení menší než 640px", required=True + ) + md_banner = ImageChooserBlock( + label="Obrázek pro zobrazení větší než 768px", required=True + ) + lg_banner = ImageChooserBlock( + label="Obrázek pro zobrazení větší než 1024px", required=True + ) + xl_banner = ImageChooserBlock( + label="Obrázek pro zobrazení větší než 1280px", required=True + ) + xxl_banner = ImageChooserBlock( + label="Obrázek pro zobrazení větší než 1536px", required=True + ) + + title = CharBlock(label="Titulek bloku", required=False) + subtitle = CharBlock(label="Podtitulek", required=False) + button_text = CharBlock(label="Text tlačítka", required=False) + button_link = URLBlock(label="Odkaz tlačítka", required=False) + + def clean(self, value): + errors = {} + + if value["button_link"] and not value["button_text"]: + errors["button_text"] = ErrorList( + ["Zadejte prosím text tlačítka, nebo smažte odkaz v tlačítku"] + ) + + if not value["button_link"] and value["button_text"]: + errors["button_link"] = ErrorList( + ["Zadejte prosím odkaz tlačítka, nebo smažte text v tlačítku"] + ) + + if errors: + raise StructBlockValidationError(errors) + + return super().clean(value) + + class Meta: + template = "district/blocks/hero_banner_block.html" + icon = "image" + label = "Hero banner" diff --git a/district/migrations/0109_alter_districthomepage_subheader.py b/district/migrations/0109_alter_districthomepage_subheader.py new file mode 100644 index 0000000000000000000000000000000000000000..6753b6d770ebc1100ad0d10782d9e36ddd4b4fc4 --- /dev/null +++ b/district/migrations/0109_alter_districthomepage_subheader.py @@ -0,0 +1,257 @@ +# Generated by Django 4.1.8 on 2023-04-24 22:33 + +import wagtail.blocks +import wagtail.fields +import wagtail.images.blocks +from django.db import migrations + + +class Migration(migrations.Migration): + dependencies = [ + ("district", "0108_alter_districtcenterpage_content_and_more"), + ] + + operations = [ + migrations.AlterField( + model_name="districthomepage", + name="subheader", + field=wagtail.fields.StreamField( + [ + ( + "header_full_size", + wagtail.blocks.StructBlock( + [ + ( + "title", + wagtail.blocks.CharBlock( + label="Titulek", required=True + ), + ), + ( + "image_background", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek v pozadí", required=True + ), + ), + ( + "image_foreground", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek v popředí", required=False + ), + ), + ( + "button_group", + wagtail.blocks.ListBlock( + wagtail.blocks.StructBlock( + [ + ( + "title", + wagtail.blocks.CharBlock( + label="Titulek", + max_length=128, + required=True, + ), + ), + ( + "icon", + wagtail.blocks.CharBlock( + help_text="Identifikátor ikonky ze styleguide (https://styleguide.pirati.cz/latest/?p=viewall-atoms-icons), např. ico--key.", + label="Ikonka", + max_length=128, + required=False, + ), + ), + ( + "size", + wagtail.blocks.ChoiceBlock( + choices=[ + ("sm", "Malá"), + ("base", "Střední"), + ("lg", "Velká"), + ], + label="Velikost", + ), + ), + ( + "color", + wagtail.blocks.ChoiceBlock( + choices=[ + ("black", "Černá"), + ("white", "Bílá"), + ("grey-125", "Světle šedá"), + ("blue-300", "Modrá"), + ("cyan-200", "Tyrkysová"), + ("green-400", "Zelené"), + ("violet-400", "Vínová"), + ("red-600", "Červená"), + ], + label="Barva", + ), + ), + ( + "hoveractive", + wagtail.blocks.BooleanBlock( + default=True, + help_text="Pokud je zapnuto, tlačítko mění barvu, když na něj uživatel najede myší.", + label="Animovat na hover", + required=False, + ), + ), + ( + "mobile_fullwidth", + wagtail.blocks.BooleanBlock( + default=True, + help_text="Pokud je zapnuto, tlačítko se na mobilních zařízeních roztáhne na plnou šířku.", + label="Plná šířka na mobilních zařízeních", + required=False, + ), + ), + ( + "page", + wagtail.blocks.PageChooserBlock( + label="Stránka", required=False + ), + ), + ( + "link", + wagtail.blocks.URLBlock( + label="Odkaz", required=False + ), + ), + ( + "align", + wagtail.blocks.ChoiceBlock( + choices=[ + ("auto", "Automaticky"), + ("center", "Na střed"), + ], + label="Zarovnání", + ), + ), + ] + ), + label="Tlačítka", + ), + ), + ] + ), + ), + ( + "header_simple", + wagtail.blocks.StructBlock( + [ + ( + "title", + wagtail.blocks.CharBlock( + label="Titulek", required=False + ), + ), + ( + "subtitle", + wagtail.blocks.CharBlock( + label="Podtitulek", required=False + ), + ), + ("image", wagtail.images.blocks.ImageChooserBlock()), + ] + ), + ), + ( + "header", + wagtail.blocks.StructBlock( + [ + ( + "title", + wagtail.blocks.CharBlock( + help_text="Nap", label="Titulek", required=False + ), + ), + ("image", wagtail.images.blocks.ImageChooserBlock()), + ( + "button_text", + wagtail.blocks.CharBlock( + label="Text tlačítka", required=False + ), + ), + ( + "button_link", + wagtail.blocks.URLBlock( + label="Odkaz tlačítka", required=False + ), + ), + ] + ), + ), + ( + "hero_banner", + wagtail.blocks.StructBlock( + [ + ( + "sm_banner", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek pro zobrazení menší než 640px", + required=True, + ), + ), + ( + "md_banner", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek pro zobrazení větší než 768px", + required=True, + ), + ), + ( + "lg_banner", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek pro zobrazení větší než 1024px", + required=True, + ), + ), + ( + "xl_banner", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek pro zobrazení větší než 1280px", + required=True, + ), + ), + ( + "xxl_banner", + wagtail.images.blocks.ImageChooserBlock( + label="Obrázek pro zobrazení větší než 1536px", + required=True, + ), + ), + ( + "title", + wagtail.blocks.CharBlock( + label="Titulek bloku", required=False + ), + ), + ( + "subtitle", + wagtail.blocks.CharBlock( + label="Podtitulek", required=False + ), + ), + ( + "button_text", + wagtail.blocks.CharBlock( + label="Text tlačítka", required=False + ), + ), + ( + "button_link", + wagtail.blocks.URLBlock( + label="Odkaz tlačítka", required=False + ), + ), + ] + ), + ), + ], + blank=True, + use_json_field=True, + verbose_name="Blok pod headerem", + ), + ), + ] diff --git a/district/models.py b/district/models.py index 2892ad900dac41f70e9b0f9b2c93dcffc515dea8..cca91b598f0a4c1cbb87272aa93afd68c1309d36 100644 --- a/district/models.py +++ b/district/models.py @@ -59,7 +59,7 @@ from . import blocks from .forms import JekyllImportForm CONTENT_BLOCKS = DEFAULT_CONTENT_BLOCKS + [ - ("chart", ChartBlock(template="district/blocks/chart.html")), + ("chart", ChartBlock(template="district/blocks/chart.html")) ] @@ -81,6 +81,7 @@ class DistrictHomePage( ("header_full_size", FullSizeHeaderBlock()), ("header_simple", blocks.HomepageSimpleHeaderBlock()), ("header", blocks.HomepageHeaderBlock()), + ("hero_banner", blocks.HeroBannerBlock()), ], verbose_name="Blok pod headerem", blank=True, @@ -426,6 +427,10 @@ class DistrictArticlePage( ) return context + @property + def articles_page(self): + return self.get_parent() + class DistrictArticlesPage( RoutablePageMixin, ExtendedMetadataPageMixin, SubpageMixin, MetadataPageMixin, Page @@ -1086,7 +1091,11 @@ class DistrictElectionRootPage(RoutablePageMixin, Page): ### RELATIONS - parent_page_types = ["district.DistrictHomePage"] + parent_page_types = [ + "district.DistrictHomePage", + "district.DistrictCustomPage", + "district.DistrictCrossroadPage", + ] subpage_types = [ "district.DistrictElectionCampaignPage", "district.DistrictGeoFeatureCollectionPage", @@ -1413,7 +1422,7 @@ class DistrictCustomPage( ### RELATIONS parent_page_types = ["district.DistrictHomePage", "district.DistrictCrossroadPage"] - subpage_types = [] + subpage_types = ["district.DistrictElectionRootPage"] ### OTHERS diff --git a/district/templates/district/blocks/hero_banner_block.html b/district/templates/district/blocks/hero_banner_block.html new file mode 100644 index 0000000000000000000000000000000000000000..a321a60206f8af1f13260297b6ba004349601d3f --- /dev/null +++ b/district/templates/district/blocks/hero_banner_block.html @@ -0,0 +1,41 @@ +{% load wagtailimages_tags %} + +<div class="relative hero hero--image p-0 text-center md:text-left"> + <picture aria-hidden="true"> + {% image self.xxl_banner min-1280x1 as xxl_image %} + {% image self.xl_banner max-1280x2000 as xl_image %} + {% image self.lg_banner max-1024x2000 as lg_image %} + {% image self.md_banner max-768x2000 as md_image %} + {% image self.sm_banner max-640x2000 as sm_image %} + + <source media="(min-width:1536px)" srcset="{{ xxl_image.full_url }}"> + <source media="(min-width:1280px)" srcset="{{ xl_image.full_url }}"> + <source media="(min-width:1024px)" srcset="{{ lg_image.full_url }}"> + <source media="(min-width:768px)" srcset="{{ md_image.full_url }}"> + + <img src="{{ sm_image.full_url }}" width="auto" class="w-full"> + </picture> + <div class="absolute h-full w-full md:w-1/2" style="bottom: 0">{# TODO: Update style guide #} + <div class="flex h-full items-end md:items-center justify-center text-center lg:text-left"> + <div class="mx-2 mb-10"> + <h1 class="head-alt-lg md:head-alt-xl text-shadow-lg max-w-2xl mx-auto lg:mx-0"> + {% firstof self.title page.title %} + </h1> + {% if self.subtitle %} + <h2 class="head-xs mt-2 text-shadow-lg"> + {{ self.subtitle }} + </h2> + {% endif %} + {% if self.button_link and self.button_text %} + <div class="mt-4 md:mt-8 space-y-4"> + <div class="w-100"> + <a href="{{ self.button_link }}" class="btn btn--white btn--hoveractive text-base btn--fullwidth md:btn--autowidth"> + <div class="btn__body ">{{ self.button_text }}</div> + </a> + </div> + </div> + {% endif %} + </div> + </div> + </div> +</div> diff --git a/main/templates/main/includes/layout/footer.html b/main/templates/main/includes/layout/footer.html index 48df48bdf800f8434caec64f83f50676c89be5b4..1953c1c3a95467cc74609b548864c4a07a0c09b0 100644 --- a/main/templates/main/includes/layout/footer.html +++ b/main/templates/main/includes/layout/footer.html @@ -63,7 +63,8 @@ {% endif %} <div class="max-w-xs"> <span class="text-xs text-grey-350 "> - <span class="-scale-x-100 inline-block">©</span> Piráti, 2022. Všechna práva vyhlazena. Sdílejte a nechte ostatní sdílet za stejných podmínek.<br><br> + <span class="-scale-x-100 inline-block">©</span> Piráti, {% now 'Y' %}. + Všechna práva vyhlazena. Sdílejte a nechte ostatní sdílet za stejných podmínek.<br><br> <a href="{{ page.root_page.gdpr_and_cookies_url }}">Zásady ochrany osobních údajů</a> </span> </div> diff --git a/shared/templates/shared/calendar_current_events_snippet.html b/shared/templates/shared/calendar_current_events_snippet.html index a54faa6f425ebe13f3e7a34c93240fec70ae627e..ac7bb00967ef2b0a8491082df32747552c851046 100644 --- a/shared/templates/shared/calendar_current_events_snippet.html +++ b/shared/templates/shared/calendar_current_events_snippet.html @@ -25,8 +25,14 @@ </div> <div class="col-span-8 grid grid-cols-3 col-gap-4 calendar-table-row__col calendar-table-row__col--norborder"> <div class="col-span-3 md:col-span-1"> - <strong class="block">{{ event.start|date:"l j. E"|capfirst }}</strong> - <p class="font-light text-sm mt-1">{{ event.duration }}</p></div> + <strong class="block"> + <time datetime="{{ event.start|date:"Y-m-d H:m"|capfirst }}"> + {{ event.start|date:"l j. E"|capfirst }} + </time> + </strong> + <p class="font-light text-sm mt-1" aria-hidden="true">{{ event.start|date:"G:i" }}</p> + <p class="font-light text-sm mt-1">{{ event.duration }}</p> + </div> <div class="col-span-3 md:col-span-2 mt-4 md:mt-0 overflow-hidden"> <span class="font-bold block"> {{ event.summary }} diff --git a/shared/templates/shared/more_articles_snippet.html b/shared/templates/shared/more_articles_snippet.html index f5033712a6a0c2665e76b06e21beaf9719232bf9..59644a43559548bfe9eea55540bfb329421cfb6f 100644 --- a/shared/templates/shared/more_articles_snippet.html +++ b/shared/templates/shared/more_articles_snippet.html @@ -1,5 +1,5 @@ <nav class="text-center mb-3"> - <a href="{{ page.root_page.articles_page.url }}" class="btn btn--icon text-xl pt-8" rel="next" > + <a href="{{ page.articles_page.url }}" class="btn btn--icon text-xl pt-8" rel="next" > <div class="btn__body-wrap"> <div class="btn__body ">Další články</div> <div class="btn__icon ">