Source code for shuup.front.apps.carousel.models

# -*- coding: utf-8 -*-
# This file is part of Shuup.
#
# Copyright (c) 2012-2017, Shoop Commerce Ltd. All rights reserved.
#
# This source code is licensed under the OSL-3.0 license found in the
# LICENSE file in the root directory of this source tree.
from django.conf import settings
from django.core.urlresolvers import reverse
from django.db import models
from django.db.models import Q
from django.utils.encoding import python_2_unicode_compatible
from django.utils.timezone import now
from django.utils.translation import ugettext_lazy as _
from easy_thumbnails.files import get_thumbnailer
from enumfields import Enum, EnumIntegerField
from filer.fields.image import FilerImageField
from parler.managers import TranslatableQuerySet
from parler.models import TranslatedFields

from shuup.core.models import Category, Product
from shuup.core.models._base import ShuupModel, TranslatableShuupModel
from shuup.simple_cms.models import Page


[docs]class CarouselMode(Enum): SLIDE = 0 FADE = 1 class Labels: SLIDE = _("Slide") FADE = _("Fade")
[docs]class LinkTargetType(Enum): CURRENT = 0 NEW = 1 class Labels: CURRENT = _("Current") FADE = _("New")
[docs]class SlideQuerySet(TranslatableQuerySet):
[docs] def visible(self, dt=None): """ Get slides that should be publicly visible. This does not do permission checking. :param dt: Datetime for visibility check :type dt: datetime.datetime :return: QuerySet of slides. :rtype: QuerySet[Slide] """ if not dt: dt = now() q = Q(available_from__lte=dt) & (Q(available_to__gte=dt) | Q(available_to__isnull=True)) qs = self.filter(q) return qs
@python_2_unicode_compatible @python_2_unicode_compatible
[docs]class Slide(TranslatableShuupModel): carousel = models.ForeignKey(Carousel, related_name="slides", on_delete=models.CASCADE) name = models.CharField( max_length=50, blank=True, null=True, verbose_name=_("name"), help_text=_("Name is only used to configure slides.") ) product_link = models.ForeignKey( Product, related_name="+", blank=True, null=True, verbose_name=_("product link"), help_text=_( "Set the product detail page that should be shown when this slide is clicked, if any." )) category_link = models.ForeignKey( Category, related_name="+", blank=True, null=True, verbose_name=_("category link"), help_text=_( "Set the product category page that should be shown when this slide is clicked, if any." )) cms_page_link = models.ForeignKey( Page, related_name="+", verbose_name=_("cms page link"), blank=True, null=True, help_text=_( "Set the web page that should be shown when the slide is clicked, if any." )) ordering = models.IntegerField(default=0, blank=True, null=True, verbose_name=_("ordering"), help_text=_( "Set the numeric order in which this slide should appear relative to other slides in this carousel." )) target = EnumIntegerField( LinkTargetType, default=LinkTargetType.CURRENT, verbose_name=_("link target"), help_text=_( "Set this to current if clicking on this slide should open a new browser tab." ) ) available_from = models.DateTimeField(null=True, blank=True, verbose_name=_('available from'), help_text=_( "Set the date and time from which this slide should be visible in the carousel. " "This is useful to advertise sales campaigns or other time-sensitive marketing." )) available_to = models.DateTimeField(null=True, blank=True, verbose_name=_('available to'), help_text=_( "Set the date and time from which this slide should be visible in the carousel. " "This is useful to advertise sales campaigns or other time-sensitive marketing." )) translations = TranslatedFields( caption=models.CharField( max_length=80, blank=True, null=True, verbose_name=_("caption"), help_text=_( "Text that describes the image. Used for search engine purposes." ) ), caption_text=models.TextField( blank=True, null=True, verbose_name=_("caption text"), help_text=_("When displayed in banner box mode, caption text is shown as a tooltip"), ), external_link=models.CharField( max_length=160, blank=True, null=True, verbose_name=_("external link"), help_text=_( "Set the external site that should be shown when this slide is clicked, if any." )), image=FilerImageField( blank=True, null=True, related_name="+", verbose_name=_("image"), on_delete=models.PROTECT, help_text=_( "The slide image to show." )) ) def __str__(self): return "%s %s" % (_("Slide"), self.pk) class Meta: verbose_name = _("Slide") verbose_name_plural = _("Slides") ordering = ("ordering", "id")
[docs] def get_translated_field(self, attr): if not self.safe_translation_getter(attr): return self.safe_translation_getter(attr, language_code=settings.PARLER_DEFAULT_LANGUAGE_CODE) return getattr(self, attr)
[docs] def is_visible(self, dt=None): """ Get slides that should be publicly visible. This does not do permission checking. :param dt: Datetime for visibility check :type dt: datetime.datetime :return: Public visibility status :rtype: bool """ if not dt: dt = now() return ( (self.available_from and self.available_from <= dt) and (self.available_to is None or self.available_to >= dt) )
@property def easy_thumbnails_thumbnailer(self): """ Get Thumbnailer instance for the translated image. Will return None if file cannot be thumbnailed. :rtype:easy_thumbnails.files.Thumbnailer|None """ image = self.get_translated_field("image") if not image: return try: return get_thumbnailer(image) except ValueError: return get_thumbnailer(image.filer_image_file) except: return None
[docs] def get_thumbnail(self, **kwargs): """ Get thumbnail for the translated image This will return None if there is no file :rtype: easy_thumbnails.files.ThumbnailFile|None """ kwargs.setdefault("size", (self.carousel.image_width, self.carousel.image_height)) kwargs.setdefault("crop", True) # sane defaults kwargs.setdefault("upscale", True) # sane defaults if kwargs["size"] is (0, 0): return None thumbnailer = self.easy_thumbnails_thumbnailer if not thumbnailer: return None return thumbnailer.get_thumbnail(thumbnail_options=kwargs)
objects = SlideQuerySet.as_manager()