Resizing Images On The Fly in Smarty

July 22, 2009

When I started working at New Media Campaigns last month, I immediately set about learning our custom-made content management system. Although it is generally very well-made and easy to use, I did find that there were things I missed from the other CMSs I have used in my freelance career. High among those was the ability to resize images to particular dimensions within templates. It seemed silly to be creating thumbnails manually for every photo gallery, or explaining to clients that their sidebar images must be 300 pixels wide or the layout would break. Expression Engine has a wonderful Image Sizer plugin. Wordpress and Radiant let you specify a couple of thumbnail sizes per-site that will automatically be created. Why coudn't we do the same thing?

Our CMS uses the Smarty templating system, which I had never used before starting at NMC. This seemed like a good opportunity to dig into the Smarty plugin structure and create a custom function that would take an image file and the desired dimensions and would resize and cache the image.

If there are other options you would find useful leave your requests in the comments section...I will incorporate them if possible. And, of course, if you find any bugs please let me know.

Usage

{imagesize src=$imageUrl [width=200] [height=100] [crop=true] [bw=true] [colorize="#ff0000"] [radius=10] [forcepng=true] [background='#000000'] [alt='Alternate Text'] [title='Image Title'] [class='className'] [id='idName'] [style='inline styles']}

The only required attribute is src. This is the absolute or relative url to the original image file that you want to use. You can optionally pass in alt, id, class, or title attributes, which will be output as they would in a normal image tag.

Finally you will want to give it either a width or a height (if you don't, it will just output the image at its original size). If you specify only one of the two dimensions, the image will be resized proportionally. If you specify both the width and the height it will be resized to fit within those dimensions. Additionally, if you include crop=true the image will be cropped to the exact size you specify. This last option is very handy for creating square thumbnails, for instance. Update: You can now use bw=true to convert the image to black and white, or colorize="#ff0000" to output a monochrome colorized image. radius=x will round the corners with a radius of x. If you give it rounded corners and the file is a JPEG or GIF, you can also use background='#ff0000' to specify the background color, or you can use forcepng=true to ensure the image is saved as a 24-bit PNG with full transparency.

Installation

Download the plugin file and put it in the plugins folder inside your copy of Smarty. That's all you need to do!

Caveats

This is still beta software! I have tested it on several systems, but if it deletes all the images on your server and sends an insulting email to your mother we are not responsible. Please backup before you install.

  • You will need to be running the most recent version of Smarty to use this plugin. The plugin interface changed recently to allow plugins to access the $_SERVER variables we need to figure out the path to the cache folder.
  • In some cases when you are using mod_rewrite on your server and a relative image url you will get an error because it can't calculate the cache folder. If this happens, try using relative urls.
  • Depending on how your server is set up, you may have to manually create a cache folder in the same folder as the image you are trying to access.

Changelog

  • 0.9: Initial public release. (7/22/09)
  • 0.91: New crop attribute, no longer caches images that don't need resizing, code is better commented. (7/23/09)
  • 0.92: Fixed the issues Ron reported in the comments. (7/24/09)
  • 0.93: Added style attribute. Better handling of backslashes. (8/25/09)
  • 1.0: Added bw, radius, and background attributes. (10/27/09)
  • 1.0.1: Added forcepng attribute. (2/3/09)
  • 1.0.2: Added colorize attribute. Better error reporting: errors are now written as html comments, so as not to break your design if an image is missing. (2/3/09)
  • 1.0.3: Fixed bugs introducted in previous update. (2/4/09)

Comments

Dennis de Best's avatar
Dennis de Best
Hey thanks for the plugin, I'm a bit late to the party but I could get it working by removing the call by reference line 527 and 528
(Changed to :
imageSmoothArc ( $img, $cx, $cy, $w, $h, $color, $start, 2*M_PI);
imageSmoothArc ( $img, $cx, $cy, $w, $h, $color, 0, $stop);
)

And to get passe the Smarty _supers does not exist error change every
$smarty->_supers['servers']
to
$_SERVER

still getting a couple of notices I will update my comment if I have any further news
Sridhar's avatar
Sridhar
This plugin was supposed to solve my problems, but it does. This probably is due to my ignorance in using it. Here is what I did.

I created a folder named plugins inside the smarty directory
In the php file, I had added this line:
$smarty->setPluginsDir('/home/www/public_html/smarty/plugins');
I created a folder named cache in the folder where images are uploaded
I assigned the following variable in php file:
$smarty->assign('foto1', $file_url); (where $file_url contains the url of the uploaded file)
In the template file, I included the following:
{imagesize src=$foto1 [width=700] [height=400] [crop=true]}

Despite all this, nothing happens. Files get uploaded, data inserted into tables but page remains blank.

Where am I going wrong? Please help me.
Sridhar's avatar
Sridhar
Please provide a working example and installation steps. For newbies, it is a steep learning curve.
Evan's avatar
Evan
You mention an image will be cropped if we specify both height and width but where does it crop? Does it take off right and bottom or equally fro all sides?

Thanks
Batuhan Küçükali's avatar
Batuhan Küçükali
This plugin smarty thumbnail plugin ?

How to use a simple ?
sham's avatar
sham
I am getting blank page.. Please help me out...

This is my code,.

{assign var="imageurl" value="assets/bg1.jpg"}
{imagesize src=$imageurl width="200" height="100"}

Please correct the code if any mistake.

Thanks
John's avatar
John
Interesting but il doens't work with smarty 3.x for me.
I got "template property '_supers' does not exist." message

I guess syntax is different.

I'would be very interested to learn how to adapt the plugin for Smarty 3.x ...
Antonio's avatar
Antonio
Great Works!
Meloman's avatar
Meloman
Hi,

Sometimes with crop=true for example the image made is "black". Is it a known issue ? Have you got a patch ?

Regards
cristian's avatar
cristian
The same problem:

Fatal error: Uncaught exception 'SmartyException' with message 'template property '_supers' does not exist
Andrey's avatar
Andrey
I have error
Fatal error: Uncaught exception 'SmartyException' with message 'template property '_supers' does not exist.' in S:\home\shop\www\smarty\sysplugins\smarty_internal_template.php:668

Can you hrlp me?
Aart's avatar
Aart
Thanks a lot for this plugin. Had the same issue with the $smarty->_supers and some errors with handling an image object (with seperated file, folder and other information) but got it going and it's working like a spin.
Tihomir's avatar
Tihomir

Hi, there!
I made the plugin working. The problem was that somehow $smarty->_supers did not work and I changed them directly with the php server vars.

Tihomir's avatar
Tihomir

Hello there,

The plugin is great and probably one of fewest in the net!
I installed it in smarty (I am new to the templating engine). I cannot make the plugin to see the image. It says
"Could not find the file" and the file is there, I tried to use relative and absolute paths (src="images/layout/logo.png"), but nothing.
I am using wamp in windows. the smarty is configured and working fine.
I might be probably doing sth wrong. But could you give me an advice, please?

griffin1987's avatar
griffin1987

Hi there,

Nice plug you got there, but i think you should mention if you use GD, IM or some other type of image library, which you probably do.

Also, Arnaldo's syntax is wrong, it should be:
{imagesize src='`$emp_dest[i].logo`' width=200 height=100}
if you do it correctly. The backticks are for using variables with dot in them as function parameters.

Best Regards

Eli Van Zoeren's avatar
Eli Van Zoeren

Arnaldo- Did you create the cache folder under the folder containing the image you want to resize, or under your main images folder? It needs to the former (if the two folders are different). Are you on a linux or Windows server? If you can give me a link to the page you are using it on I will take a look and see what I can figure out.

Arnaldo's avatar
Arnaldo

Hi Eli,

I installed the plugin inside plugins directory and called it using:

{imagesize src=$emp_dest[i].logo width=200 height=100} (without brackets in width and height because I get a blank page with them)

When I load the page, in the place of the images, appears: "Could not create a cache directory under your image directory. Create it manually and try again. "

I've already created a "cache" directory inside my images directory, but nothing happens.

Could you help me?

Justin Jones's avatar
Justin Jones

Hey Eli, thanks for such a great plugin!

I'm using it in conjunction with CodeIgniter, but my reason for posting isn't exclusive to CI.

I use this scheme when it comes to URLs and path names:

"/images/file.jpg"

I'm working on a way to check for this, and modify paths correctly.

Helge Johnsen's avatar
Helge Johnsen

Thanks Eli. Now it works perfect :-)

Greg's avatar
Greg

Great plugin! I need to access images from a directory outside of the parent Smarty directory, but my '../' is stripped from the file path. I assume this is for security purposes, but is there a workaround for this (or an obvious method I'm oblivious to)?

 Eli Van Zoeren's avatar
Eli Van Zoeren

Helge: Are you using a Windows server? I added some code to try and handle Windows-style paths (with backslashes) better, but without access to a Windows box to test it, I am not sure how well my fix works. If you dont mind, can you give it another try and let me know what happens?

 Helge johnsen's avatar
Helge johnsen

Hi Eli

What a fanastic plugin. I have tried to play with it and have one problem. I suppose it's not a bug, but still I can't get it to work.

Some of the "/" backslash becomes ordinary "\" slashes in the url to my pictures.

 Eli Van Zoeren's avatar
Eli Van Zoeren

@Ron: Good catches, both! I just updated the plugin to fix those issues. The second thing you mentioned was due to $pathInfo['filename'] only being added in PHP 5.2. I am now checking and getting the file name in a different way if the first fails.

Keep the bug reports coming, everyone!

 Ron's avatar
Ron

This is awesome! I was rewriting some ancient mixed PHP/HTML code in Smarty this evening and thought it'd be nice if a plugin like this existed. Apparently my timing was perfect since you just released this yesterday.

I had to make two changes to get it to work on my system:

1) on line 43, I added a strtolower() call to lower-case the file extension because my users had uploaded files with extensions like .JPG, etc

2) pathinfo() on line 47 was not returning the base filename (that element was blank) so I replaced "$paths['fileBasename'] = $pathInfo['filename'];" with " $paths['fileBasename'] = basename($filePath);". I suspect this isn't exactly what you intended as it seems to include the extension still, but it works fine.

Leave a comment