Handle responsive images
authorThierry Florac <thierry.florac@onf.fr>
Tue, 15 Nov 2016 10:22:36 +0100
changeset 18 3d81c3b94605
parent 17 3f879876f7a6
child 19 f4462709ee4d
Handle responsive images
src/pyams_portal/portlets/image/__init__.py
src/pyams_portal/portlets/image/image.pt
--- a/src/pyams_portal/portlets/image/__init__.py	Tue Oct 11 16:06:12 2016 +0200
+++ b/src/pyams_portal/portlets/image/__init__.py	Tue Nov 15 10:22:36 2016 +0100
@@ -17,7 +17,8 @@
 
 # import interfaces
 from .interfaces import IImagePortletSettings
-from pyams_portal.interfaces import IPortalContext, IPortletRenderer
+from pyams_file.interfaces import IResponsiveImage, DELETED_FILE
+from pyams_portal.interfaces import IPortalContext, IPortletRenderer, IPortalPage, IPortalTemplateConfiguration
 from pyams_skin.layer import IPyAMSLayer
 from pyams_utils.interfaces import PUBLIC_PERMISSION
 
@@ -26,7 +27,7 @@
 from pyams_portal.portlet import portlet_config, Portlet, PortletSettings, PortletRenderer
 from pyams_template.template import template_config
 from pyams_utils.adapter import adapter_config
-from zope.interface import implementer, Interface
+from zope.interface import implementer, Interface, alsoProvides
 
 from pyams_portal import _
 
@@ -38,7 +39,17 @@
 class ImagePortletSettings(PortletSettings):
     """Image portlet settings"""
 
-    image = FileProperty(IImagePortletSettings['image'])
+    _image = FileProperty(IImagePortletSettings['image'])
+
+    @property
+    def image(self):
+        return self._image
+
+    @image.setter
+    def image(self, value):
+        self._image = value
+        if (value is not None) and (value is not DELETED_FILE):
+            alsoProvides(self._image, IResponsiveImage)
 
 
 @portlet_config(permission=PUBLIC_PERMISSION)
@@ -58,3 +69,10 @@
 @template_config(template='image.pt', layer=IPyAMSLayer)
 class ImagePortletRenderer(PortletRenderer):
     """Image portlet renderer"""
+
+    @property
+    def slot_configuration(self):
+        template = IPortalPage(self.context).template
+        config = IPortalTemplateConfiguration(template)
+        slot_id, slot_name = config.get_portlet_slot(self.settings.configuration.portlet_id)
+        return config.get_slot_configuration(slot_name)
--- a/src/pyams_portal/portlets/image/image.pt	Tue Oct 11 16:06:12 2016 +0200
+++ b/src/pyams_portal/portlets/image/image.pt	Tue Nov 15 10:22:36 2016 +0100
@@ -0,0 +1,50 @@
+<tal:if condition="view.settings.image">
+	<picture
+		tal:define="image view.settings.image;
+					image_url extension:absolute_url(image);
+					slot_config view.slot_configuration;
+					slot_width slot_config.get_width();
+					base_width 100 / 12;">
+		<tal:var define="width slot_width['lg']">
+			<source media="(min-width: 1200px)"
+					tal:condition="width"
+					tal:attributes="srcset string:${image_url}/++thumb++lg:w1200 1200w, ${image_url}/++thumb++lg:w512 512w, ${image_url}/++thumb++lg:w256 256w, ${image_url}/++thumb++lg:w128 128w;
+									sizes string:${round(base_width * width)}vw" />
+			<source media="(min-width: 1200px)"
+					srcset="/--static--/pyams_default_theme/img/dot.png"
+					tal:condition="not:width"
+					tal:attributes="sizes string:${round(base_width * width)}vw" />
+		</tal:var>
+		<tal:var define="width slot_width['md']">
+			<source media="(min-width: 992px)"
+					tal:condition="width"
+					tal:attributes="srcset string:${image_url}/++thumb++md:w992 992w, ${image_url}/++thumb++md:w512 512w, ${image_url}/++thumb++md:w256 256w, ${image_url}/++thumb++md:w128 128w;
+									sizes string:${round(base_width * width)}vw" />
+			<source media="(min-width: 992px)"
+					srcset="/--static--/pyams_default_theme/img/dot.png"
+					tal:condition="not:width"
+					tal:attributes="sizes string:${round(base_width * width)}vw" />
+		</tal:var>
+		<tal:var define="width slot_width['sm']">
+			<source media="(min-width: 768px)"
+					tal:condition="width"
+					tal:attributes="srcset string:${image_url}/++thumb++sm:w768 768w, ${image_url}/++thumb++sm:w512 512w, ${image_url}/++thumb++sm:w256 256w, ${image_url}/++thumb++sm:w128 128w;
+									sizes string:${round(base_width * width)}vw" />
+			<source media="(min-width: 768px)"
+					srcset="/--static--/pyams_default_theme/img/dot.png"
+					tal:condition="not:width"
+					tal:attributes="sizes string:${round(base_width * width)}vw" />
+		</tal:var>
+		<tal:var define="width slot_width['xs']">
+			<source media="(max-width: 767px)"
+					tal:condition="width"
+					tal:attributes="srcset string:${image_url}/++thumb++xs:w768 768w, ${image_url}/++thumb++xs:w512 512w, ${image_url}/++thumb++xs:w256 256w, ${image_url}/++thumb++xs:w128 128w;
+									sizes string:${round(base_width * width)}vw" />
+			<source media="(max-width: 767px)"
+					srcset="/--static--/pyams_default_theme/img/dot.png"
+					tal:condition="not:width"
+					tal:attributes="sizes string:${round(base_width * width)}vw" />
+		</tal:var>
+		<img style="width: 100%;" tal:attributes="src image_url" />
+	</picture>
+</tal:if>