Error with imagemagick overlay (watermark)

joncup - June 20, 2008 - 20:57
Project:Imagecache Actions
Version:6.x-1.4
Component:Miscellaneous
Category:bug report
Priority:normal
Assigned:Unassigned
Status:needs review
Description

I set up an overlay, Overlay: file image to canvas (watermark) lone_pine_logo_1.jpg x:center, y:center alpha:75%
I got the same error with a text overlay.

call_user_func_array() [<a href='function.call-user-func-array'>function.call-user-func-array</a>]: First argument is expected to be a valid callback, 'imageapi_imagemagick_image_overlay' was given in /homepages/9/d229203311/htdocs/website.com/sites/all/modules/imagecache_actions/imagecache_canvasactions.module on line 113.

#1

dman - June 21, 2008 - 02:59

Imagemagic is not fully supported for a few custom actions that were added only for this utility :-(
I don't have imagemagick available for testing and development.

We can probably update the thing to give a better error - for a start.
I also don't imagine it would be too hard to port the imageapi_image_overlay() function to imagemagick ... but I've never coded for imagemagick is all. Any imagemagick fans want to try?

#2

joncup - June 21, 2008 - 03:34

thanks for the speedy reply, i just switched to gd, works great, im happy with gd, thanks again

#3

wad - July 20, 2008 - 17:14
Title:Error with overlay» Error with imagemagick overlay (watermark)
Priority:critical» normal

I also hit this bug and had to switch to GD, however that uncovered another problem. My server runs Ubuntu, but because PHP bundles its own forked version of the GD libraries, and Debian being the anal retentive package nazis that they are, the PHP package that Ubuntu syncs from Debian is built without the bundled GD library. This means we need to install the official libs which are missing several features such as Image Filtering and Image Rotation.

Fortunately the module has a workaround for them, but I'd really like to see an ImageMagick version of overlay so I can ditch GD again.

In the mean time, please fix that error message so it's meaningful.

#4

OnkelTem - August 3, 2008 - 03:55

IMHO, ImageActions overlaying GD algorithm is the nice training exercise in PHP coding, having no practical value. Applying 4 small round corners to a 600x400 image takes about 3-4 seconds on my Ubuntu 8.04 with AMD 64 4000+.

I added ImageMagick overlaying support to [backwarded] ImageAPI [which uses 'convert' instead of right API calls of IMagick PHP module] and the same task completes in 100-150ms.

I haven't tested my modifications enough and don't like them. I had to edit imageapi_imagemagick_convert() function so I can't guarantee it will work in other cases. Its too simple to act like an full functioning interface to IM and can be used exactly for 4 actions it does atm: desature, crop, resize, rotate and nothing more.

This is my mod of imagemagick_imageapi.module:

<?php
function _imageapi_imagemagick_convert($source, $dest, $args) {
 
$args['quality'] = '-quality '. escapeshellarg(variable_get('imageapi_imagemagick_quality', 75));
 
$source_in_beginning = false;
  foreach (
$args as $k => $arg) {
      if (
strpos($arg, $source) === 0) {
         
$args[$k] = substr($arg, strlen($source));
         
$source_in_beginning = true;
      }
  }
  if (
$source_in_beginning)
     
$args[0] = escapeshellarg($source).' '.$args[0];
  else
     
$args[] = escapeshellarg($source);
 
$args[] = escapeshellarg($dest);

 
$command = implode(' ', $args);

  if (
0 != _imageapi_imagemagick_convert_exec($command, $output, $errors)) {
    return
false;
  }
  return
file_exists($dest);
}
?>

And this is dirty imageapi_imagemagick_image_overlay() implementation in imagecache_canvasactions.module:

<?php
function imageapi_imagemagick_image_overlay(&$image, $overlay, $x, $y, $alpha) {
  static
$source_is_set = false;
  switch (
$x) {
      case
'left': $x = 'West'; break;
      case
'right': $x = 'East'; break;
  }
  switch (
$y) {
      case
'top': $y = 'North'; break;
      case
'bottom': $y = 'South'; break;
  }
 
$image->ops[] .= ($source_is_set ? '' : $image->source.' ').$overlay->source.' -gravity '.$y.$x.' -composite ';
 
$source_is_set = true;
  return
true;
}
?>

This is only valid for x=left,right and y=top,bottom. Nice parsing of X and Y is yet to be done.

#5

konsumer - August 14, 2008 - 04:52

it doesn't do the transformation, and doesn't log the error.

here is what my $image->ops looks like, in imageapi_imagemagick_image_overlay():

Array
(
    [0] => -resize 455x342!
    [1] => -crop 288x342+84+0!
    [2] => sites/default/files/images/sideimage/4th_floor_detail.jpg sites/default/files/gallery/gallerymask.png -gravity NorthWest -composite
)

Also, as a sidenote, I set the function to look like this (defaults to North&West, if it's a bad value)

<?php
function imageapi_imagemagick_image_overlay(&$image, $overlay, $x, $y, $alpha) {
  static
$source_is_set = false;
  switch (
$x) {
      case
'right': $x = 'East'; break;
      default:
$x='West';
  }
  switch (
$y) {
      case
'bottom': $y = 'South'; break;
      default:
$y = 'North';
  }
 
$image->ops[] .= ($source_is_set ? '' : $image->source.' ').$overlay->source.' -gravity '.$y.$x.' -composite ';
 
$source_is_set = true;
  return
true;
}
?>

Upon closer inspection, it's making double-copies of the files, named like this: filename-0.jpg, filename-1.jpg. 0 appears to apply the overlay (but be scaled wrong, in some cases) and 1 is just a copy of the original.

#6

a_c_m - November 20, 2008 - 14:33
Version:5.x-1.0» 6.x-1.1

would be very interested in seeing this work completed.

#7

dman - December 3, 2008 - 07:40
Status:active» needs review

I pasted that code, untested into the current dev release last week.
Anyone who uses imagemagick can give some feedback. I can't.

The gd algorithm has the practical value of actually working although we know it's inefficient. This is due to a limitation on the built-in gd library that was doing bad things with transparencies using the available image copy functions in whatever update was available with PHP last year.

Something that works is better than something that doesn't, so even if it takes 3 seconds out of your day, it only has to happen once per image.
Some hosts don't allow commandline executions at all, so imagemagick isn't always the only answer, although anyone is welcome to keep working on it. All our extra actions can and should be ported to imageMagick - by someone who wants it and can do it.

#8

miro_dietiker - December 15, 2008 - 02:25

Hi dman

I've just tested the above suggested two functions and they work perfectly. (Picked #5 by konsumer)
However keep in mind that it only works after patching imageapis _imageapi_imagemagick_convert as described.

Imagemagick ist really a big improvement to the gd thing if available...

#9

konsumer - December 21, 2008 - 02:27

I agree completely with dman, above. I use gd on any site that I have the option. It's slower, but it actually works.

#10

dman - December 21, 2008 - 02:44

There MAY be a combination of directives that get GD imagecopymerge to do the right thing with full alpha transparency without jaggies. I was unable to get consistent results with it - eg on already partially transparent PNGs, and hence used the borrowed algorithm where it was clear what was happening.
If anyone has the right magic words to make GD faster and use the native processes, please suggest what is needed.

#11

ChrisRut - September 23, 2009 - 06:07

Has this issue been resolved?
I much prefer to use imagemagick because of it's speed, and the fact that GD is a resource hog and I am on a shared server. When I check my status page while using GD I get:

ImageAPI GD Memory Limit 90M
It is highly recommended that you set you PHP memory_limit to 96M to use ImageAPI GD. A 1600x1200 images consumes ~45M of memory when decompressed and there are instances where ImageAPI GD is operating on two decompressed images at once.

Can someone help explain how I can apply the patch in #5?

#12

ChrisRut - September 23, 2009 - 06:25
Version:6.x-1.1» 6.x-1.4

#13

dman - September 23, 2009 - 09:40

the above code is available in the -dev release. Works.
However it does not support alpha transparency. Fixes are needed from someone that knows imagemagick or thinks it's worthy.

 
 

Drupal is a registered trademark of Dries Buytaert.