From c63f02a12cd1d1dcc0cfce02d93e3bfec0afa694 Mon Sep 17 00:00:00 2001 From: webchick Date: Wed, 30 Sep 2015 14:20:56 -0700 Subject: [PATCH] Issue #2348255 by Jelle_S, attiks, mdrummond, Wim Leers, giupenni, jnettik, Lukas von Blarer, SaltPacket: Provide option to use srcset and/or sizes attributes on img tag instead of the picture element --- .../responsive_image/responsive_image.module | 42 +++++++++++----- .../Tests/ResponsiveImageFieldDisplayTest.php | 48 +++++++++++++++++++ .../templates/responsive-image.html.twig | 34 +++++++------ 3 files changed, 99 insertions(+), 25 deletions(-) diff --git a/core/modules/responsive_image/responsive_image.module b/core/modules/responsive_image/responsive_image.module index 9c818ca001c2..e4a0c9f396e1 100644 --- a/core/modules/responsive_image/responsive_image.module +++ b/core/modules/responsive_image/responsive_image.module @@ -178,18 +178,38 @@ function template_preprocess_responsive_image(&$variables) { $variables['sources'][] = responsive_image_build_source_attributes($image, $variables, $breakpoints[$breakpoint_id], $multipliers); } } - // Prepare the fallback image. Use srcset in the fallback image to avoid - // unnecessary preloading of images in older browsers. See - // http://scottjehl.github.io/picturefill/#using-picture and - // http://scottjehl.github.io/picturefill/#gotchas for more information. - $variables['img_element'] = array( - '#theme' => 'image', - '#srcset' => array( - array( - 'uri' => _responsive_image_image_style_url($responsive_image_style->getFallbackImageStyle(), $image->getSource()), + + if (isset($variables['sources']) && count($variables['sources']) === 1 && !isset($variables['sources'][0]['media'])) { + // There is only one source tag with an empty media attribute. This means + // we can output an image tag with the srcset attribute in stead of a + // picture tag. + $variables['output_image_tag'] = TRUE; + foreach ($variables['sources'][0] as $attribute => $value) { + if ($attribute != 'type') { + $variables['attributes'][$attribute] = $value; + } + } + $variables['img_element'] = array( + '#theme' => 'image', + '#uri' => _responsive_image_image_style_url($responsive_image_style->getFallbackImageStyle(), $image->getSource()), + ); + } + else { + $variables['output_image_tag'] = FALSE; + // Prepare the fallback image. Use srcset in the fallback image to avoid + // unnecessary preloading of images in older browsers. See + // http://scottjehl.github.io/picturefill/#using-picture and + // http://scottjehl.github.io/picturefill/#gotchas for more information. + $variables['img_element'] = array( + '#theme' => 'image', + '#srcset' => array( + array( + 'uri' => _responsive_image_image_style_url($responsive_image_style->getFallbackImageStyle(), $image->getSource()), + ), ), - ), - ); + ); + } + if (isset($variables['attributes'])) { if (isset($variables['attributes']['alt'])) { $variables['img_element']['#alt'] = $variables['attributes']['alt']; diff --git a/core/modules/responsive_image/src/Tests/ResponsiveImageFieldDisplayTest.php b/core/modules/responsive_image/src/Tests/ResponsiveImageFieldDisplayTest.php index 06fd86234659..112caebec65a 100644 --- a/core/modules/responsive_image/src/Tests/ResponsiveImageFieldDisplayTest.php +++ b/core/modules/responsive_image/src/Tests/ResponsiveImageFieldDisplayTest.php @@ -244,6 +244,7 @@ class ResponsiveImageFieldDisplayTest extends ImageFieldTestBase { $cache_tags_header = $this->drupalGetHeader('X-Drupal-Cache-Tags'); $this->assertTrue(!preg_match('/ image_style\:/', $cache_tags_header), 'No image style cache tag found.'); + $this->removeWhiteSpace(); $this->assertRaw($default_output, 'Image linked to file formatter displaying correctly on full node view.'); // Verify that the image can be downloaded. $this->assertEqual(file_get_contents($test_image->uri), $this->drupalGet(file_create_url($image_uri)), 'File was downloaded successfully.'); @@ -398,6 +399,52 @@ class ResponsiveImageFieldDisplayTest extends ImageFieldTestBase { $this->assertPattern('/srcset="' . preg_quote($thumbnail_style->buildUrl($image_uri), '/') . ' 1x".+?media="\(min-width: 0px\)"/'); } + /** + * Tests responsive image formatter on node display with one source. + */ + public function testResponsiveImageFieldFormattersOneSource() { + $this->responsiveImgStyle + // Test the output of an empty media query. + ->addImageStyleMapping('responsive_image_test_module.empty', '1x', array( + 'image_mapping_type' => 'image_style', + 'image_mapping' => 'medium', + )) + ->addImageStyleMapping('responsive_image_test_module.empty', '2x', array( + 'image_mapping_type' => 'image_style', + 'image_mapping' => 'large', + )) + ->save(); + $node_storage = $this->container->get('entity.manager')->getStorage('node'); + $field_name = Unicode::strtolower($this->randomMachineName()); + $this->createImageField($field_name, 'article', array('uri_scheme' => 'public')); + // Create a new node with an image attached. + $test_image = current($this->drupalGetTestFiles('image')); + $nid = $this->uploadNodeImage($test_image, $field_name, 'article', $this->randomMachineName()); + $node_storage->resetCache(array($nid)); + + // Use the responsive image formatter linked to file formatter. + $display_options = array( + 'type' => 'responsive_image', + 'settings' => array( + 'image_link' => '', + 'responsive_image_style' => 'style_one', + ), + ); + $display = entity_get_display('node', 'article', 'default'); + $display->setComponent($field_name, $display_options) + ->save(); + + // View the node. + $this->drupalGet('node/' . $nid); + + // Assert the media attribute is present if it has a value. + $large_style = ImageStyle::load('large'); + $medium_style = ImageStyle::load('medium'); + $node = $node_storage->load($nid); + $image_uri = File::load($node->{$field_name}->target_id)->getFileUri(); + $this->assertRaw('drupalGet('node/' . $nid); + $this->removeWhiteSpace(); switch ($link_type) { case 'file': // Make sure the link to the file is present. diff --git a/core/modules/responsive_image/templates/responsive-image.html.twig b/core/modules/responsive_image/templates/responsive-image.html.twig index a3a51a666b11..99fca6b8cfc8 100644 --- a/core/modules/responsive_image/templates/responsive-image.html.twig +++ b/core/modules/responsive_image/templates/responsive-image.html.twig @@ -6,6 +6,8 @@ * Available variables: * - sources: The attributes of the tags for this tag. * - img_element: The controlling image, with the fallback image in srcset. + * - output_image_tag: Whether or not to output an tag instead of a + * tag. * * @see template_preprocess() * @see template_preprocess_responsive_image() @@ -13,18 +15,22 @@ * @ingroup themeable */ #} - - {% if sources %} - {# - Internet Explorer 9 doesn't recognise source elements that are wrapped in - picture tags. See http://scottjehl.github.io/picturefill/#ie9 - #} - - {% for source_attributes in sources %} - - {% endfor %} - - {% endif %} - {# The controlling image, with the fallback image in srcset. #} +{% if output_image_tag %} {{ img_element }} - +{% else %} + + {% if sources %} + {# + Internet Explorer 9 doesn't recognise source elements that are wrapped in + picture tags. See http://scottjehl.github.io/picturefill/#ie9 + #} + + {% for source_attributes in sources %} + + {% endfor %} + + {% endif %} + {# The controlling image, with the fallback image in srcset. #} + {{ img_element }} + +{% endif %}