diff --git a/django_lostplaces/lostplaces/forms.py b/django_lostplaces/lostplaces/forms.py index 51fbe48..d36102c 100644 --- a/django_lostplaces/lostplaces/forms.py +++ b/django_lostplaces/lostplaces/forms.py @@ -8,6 +8,8 @@ from django.db import models from django.contrib.auth.forms import UserCreationForm, UserChangeForm from django.contrib.auth.models import User from django.utils.translation import ugettext_lazy as _ + +from lostplaces import widgets from lostplaces.models import Place, PlaceImage, Voucher, Explorer class SignupVoucherForm(UserCreationForm): @@ -68,6 +70,15 @@ class PlaceForm(forms.ModelForm): model = Place fields = '__all__' exclude = ['submitted_by'] + widgets = { + 'hero': widgets.SelectContent() + } + + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + if 'instance' in kwargs: + self.fields['hero'].queryset = PlaceImage.objects.filter(place=kwargs['instance']) + self.fields['hero'].widget.attrs['item_template'] = 'partials/select_place_image_item.html' latitude = forms.DecimalField( widget=forms.NumberInput(attrs={'min':-90,'max': 90,'type': 'number', 'step': 'any'}) @@ -89,9 +100,24 @@ class PlaceImageForm(forms.ModelForm): super().__init__(*args, **kwargs) self.fields['filename'].required = False + +class PlaceSetHeroForm(forms.ModelForm): + class Meta: + model = Place + fields = ['hero'] + widgets = { + 'hero': widgets.SelectContent() + } + + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + self.fields['hero'].queryset = PlaceImage.objects.filter(place=kwargs['instance']) + self.fields['hero'].widget.attrs['item_template'] = 'partials/select_place_image_item.html' + + class TagSubmitForm(forms.Form): - tag_list = forms.CharField( + tag_list = forms.CharField( max_length=500, required=False, widget=forms.TextInput(attrs={'autocomplete':'off'}) diff --git a/django_lostplaces/lostplaces/models/place.py b/django_lostplaces/lostplaces/models/place.py index 6114abd..3feb78b 100644 --- a/django_lostplaces/lostplaces/models/place.py +++ b/django_lostplaces/lostplaces/models/place.py @@ -11,6 +11,7 @@ from lostplaces.models.abstract_models import Submittable, Taggable, Mapable from easy_thumbnails.fields import ThumbnailerImageField from easy_thumbnails.files import get_thumbnailer + class Place(Submittable, Taggable, Mapable): """ Place defines a lost place (location, name, description etc.). @@ -25,8 +26,31 @@ class Place(Submittable, Taggable, Mapable): verbose_name=_('Description'), ) + hero = models.ForeignKey( + 'PlaceImage', + on_delete=models.SET_NULL, + null=True, + blank=True, + related_name='place_heros' + ) + + def get_hero_image(self): + if self.hero: + return self.hero + elif len(self.placeimages.all()) > 0: + return self.placeimages.first() + else: + return None + def get_absolute_url(self): return reverse('place_detail', kwargs={'pk': self.pk}) + + def get_hero_index_in_queryset(self): + for i in range(0, len(self.placeimages.all())): + image = self.placeimages.all()[i] + if image == self.hero: + return i + return None @classmethod @@ -89,7 +113,7 @@ class PlaceImage(PlaceAsset): upload_to=generate_place_image_filename, resize_source=dict(size=(2560, 2560), sharpen=True), - verbose_name=_('Filename(s)'), + verbose_name=_('Images'), help_text=_('Optional: One or more images to upload') ) place = models.ForeignKey( @@ -104,7 +128,7 @@ class PlaceImage(PlaceAsset): of this image as textual representation of this instance """ - return 'Image ' + str(self.pk) + return 'Image ' + str(self.place.name) # These two auto-delete files from filesystem when they are unneeded: diff --git a/django_lostplaces/lostplaces/templates/partials/place_teaser.html b/django_lostplaces/lostplaces/templates/partials/place_teaser.html index 659d3f6..436916c 100644 --- a/django_lostplaces/lostplaces/templates/partials/place_teaser.html +++ b/django_lostplaces/lostplaces/templates/partials/place_teaser.html @@ -2,8 +2,8 @@
- {% if place.placeimages.all|length > 0 %} - {% include 'partials/image.html' with source_url=place.placeimages.first.filename.thumbnail.url link_url=place.get_absolute_url%} + {% if place.get_hero_image %} + {% include 'partials/image.html' with source_url=place.get_hero_image.filename.thumbnail.url link_url=place.get_absolute_url%} {% else %} diff --git a/django_lostplaces/lostplaces/templates/partials/select_place_image_item.html b/django_lostplaces/lostplaces/templates/partials/select_place_image_item.html new file mode 100644 index 0000000..ac3410d --- /dev/null +++ b/django_lostplaces/lostplaces/templates/partials/select_place_image_item.html @@ -0,0 +1,3 @@ +{%load lostplaces %} + +{% include 'partials/image.html' with source_url=object.filename.thumbnail.url %} \ No newline at end of file diff --git a/django_lostplaces/lostplaces/templates/place/place_detail.html b/django_lostplaces/lostplaces/templates/place/place_detail.html index 38664b5..eeb77b2 100644 --- a/django_lostplaces/lostplaces/templates/place/place_detail.html +++ b/django_lostplaces/lostplaces/templates/place/place_detail.html @@ -22,13 +22,15 @@ {% block maincontent %}
-

{{ place.name }} {% include 'partials/icons/place_favorite.html' %} {% include 'partials/icons/place_visited.html' %}

- {% if place.placeimages.first.filename.hero.url %} + {% if place.get_hero_image %}
{% partial image %} - {% set source_url place.placeimages.first.filename.hero.url %} + {% set source_url place.get_hero_image.filename.hero.url %} + {% set link_url %} + {{"#image"|addstr:place.get_hero_index_in_queryset}} + {% endset %} {% endpartial %}
{% endif %} diff --git a/django_lostplaces/lostplaces/templates/place/place_update.html b/django_lostplaces/lostplaces/templates/place/place_update.html index 0299b50..f475f00 100644 --- a/django_lostplaces/lostplaces/templates/place/place_update.html +++ b/django_lostplaces/lostplaces/templates/place/place_update.html @@ -1,6 +1,7 @@ {% extends 'global.html'%} {% load static %} {% load i18n %} +{% load widget_tweaks %} # {% block title %}{% translate 'Edit place' %}{% endblock %} @@ -38,6 +39,15 @@ {% include 'partials/form/inputField.html' with field=form.filename %}
+ + {% if object.placeimages.all|length > 0 %} + {% translate 'Set Hero Image' %} +
+
+ {% render_field form.hero container_class='LP-ImageGrid__Container' item_class='LP-ImageGrid__Item LP-Select' current_selected_value=object.hero.id%} +
+
+ {% endif %} {% translate 'Update' as action %}