Best way to add auto-resize feature to images in "content" block?

Permalink
Hi all,

I need your lights on this one:
I am working on a website with a blog part. I want to keep it simple for my customer and I have restrict the editable area to one "content" block. But the fact you can't limit the size of an image in the "content" block is a problem (I really don't want 2000 px images to be loaded in a 600 px width row).
I want to create a custom template for the content block which generates automatically a smaller image (with thumbnail function) for images with an exceeding width.

For now, I resize in my custom template the large images before the rendering with PHP core functions:

<?php 
   defined('C5_EXECUTE') or die("Access Denied.");
   $content = $controller->getContent();
   $content = DOMDocument::loadHTML($content);
   foreach($content->getElementsByTagName('img') as $image){
      $w = $image->getAttribute('width');
      $h = $image->getAttribute('height');
      $maxw = 638;
      if($w > $maxw){
         $image->setAttribute("width", $maxw);
         $image->setAttribute("height", round($h/$w*$maxw));
      }
   }
   echo $content->saveHTML();
?>


But that's not the best way to do that since the image stays at its original resolution and I want to work with the thumbnail function and the C5 cache.
The problem is the fact that "$content = $controller->getContent();" don't keep the fID of the image in the rendering (which is needed to use the C5 thumbnail function). I have 2 ideas to change this behavior:

1. Extending the controller to create an image fID array which is accessible in the view. Then it's easy to replace images with a regex expression. But I really don't know how to extend the class.
2. Is there already a way to access the images array (especially the fID) in the view?

Thank you a lot in advance!
marc

marcsublet
View Replies: View Best Answer
jordanlev replied on at Permalink Reply
jordanlev
It might be easier (for both you and your users) to create a custom content block with Designer Content:
http://www.concrete5.org/marketplace/addons/designer-content...

You can make a field specifically for the image, and set max width/height to have it resized or cropped. And you can put whatever html you need to around it so it aligns properly (without the user having to do anything).
Of course the user could just add another image to the WYSIWYG area, but hopefully if you provide them with an easier way (the separate image field) they'll just use that as you intended.
marcsublet replied on at Permalink Reply
marcsublet
It's a good idea (and a good package by the way :-) ) but it isn't enough flexible since the number and the placement of the images are variable.
marcsublet replied on at Permalink Reply 1 Attachment
marcsublet
I have read the "manual" (RTFM… why I don't have do that before?)
getThumbnail accepts fID or string path… then I have no problem to generate thumbnail.
Then now I have a beautiful "auto-resize" template for the content block :-)

<?php 
   defined('C5_EXECUTE') or die("Access Denied.");   
   $im = Loader::helper('image');
   $maxw = 638;   
   $content = $controller->getContent();   
   $content = DOMDocument::loadHTML($content);
   foreach($content->getElementsByTagName('img') as $image){
      $w = $image->getAttribute('width');
      $h = $image->getAttribute('height');
      if($w > $maxw){
         $src = '.'.DIR_REL.$image->getAttribute('src');
         $ni = $im->getThumbnail($src, $maxw, round($h/$w*$maxw));
         $image->setAttribute("src", $ni->src);
         $image->setAttribute("width", $ni->width);
         $image->setAttribute("height", $ni->height);
marcsublet replied on at Permalink Best Answer Reply 1 Attachment
marcsublet
Updated version.
If you work with UTF-8 content, you have to inject a meta tag to specify the charset and remove it before printing it, otherwise your content output isn't correct.

<?php 
defined('C5_EXECUTE') or die("Access Denied.");   
$im = Loader::helper('image');
$maxw = 636;
$content = $controller->getContent();
$domdoc = new DOMDocument();
$domdoc->loadHTML('<head><meta http-equiv="Content-Type" content="text/html; charset=utf-8"/></head>' . $content);
foreach($domdoc->getElementsByTagName('img') as $image){
  $w = $image->getAttribute('width');
  $h = $image->getAttribute('height');
  if($w > $maxw){
    $src = '.'.DIR_REL.$image->getAttribute('src'); 
    $ni = $im->getThumbnail($src, $maxw, ceil($h/$w*$maxw));
    $image->setAttribute("src", $ni->src);
    $image->setAttribute("width", $ni->width);
wyso replied on at Permalink Reply
wyso
Where do I put it?
marcsublet replied on at Permalink Reply
marcsublet
[SERVER_ROOT]/blocks/content/templates/image-resize.php
if you want to use it as a Custom Template

or

[SERVER_ROOT]/blocks/content/view.php
if you want to use it as the default view for the content block

Perhaps you have to "play" a little with $src prefixes if nothing is outputted since the path have to be a relative one and match your server configuration.