All pastes #648714 Raw Edit

Miscellany

public text v1 · immutable
#648714 ·published 2007-08-07 15:07 UTC
rendered paste body
<?php
//
// +----------------------------------------------------------------------+
// |Image Handler for zen-cart Open Source E-commerce                     |
// +----------------------------------------------------------------------+
// | Copyright (c) 2005 Tim Kroeger                                       |
// | http://www.breakmyzencart.com                                        |
// |                                                                      |
// |                                                                      |
// |                                                                      |
// +----------------------------------------------------------------------+
// | This source file is subject to version 2.0 of the GPL license,       |
// | that is bundled with this package in the file LICENSE.txt, and is    |
// | available through the world-wide-web at the following url:           |
// | http://www.gnu.org/licenses/gpl.txt                                  |
// | If you did not receive a copy of the license and are unable          |
// | to obtain it through the world-wide-web, please send a note to       |
// | tim@breakmyzencart.com so I can mail you a copy immediately.         |
// +----------------------------------------------------------------------+
// $Id: functions_images.php,v 1.1.2.18 2005/05/21 20:59:23 tim Exp $

/**
 * Manage resizing, retrieving and on-the-fly watermarking of
 * (product) images
 * @author      Tim Kroeger <tim@breakmyzencart.com>
 * @version     1.0-beta2
 */

/**
 * set the environment for a user-installed ImageMagick distribution
 */
function zen_imagemagick_setenv() {
        $success = true;
        if (zen_not_null(DIR_FS_IMAGE_MAGICK_LIB)) {
                $imagemagick_lib = ereg_replace(DIRECTORY_SEPARATOR . '$', '', DIR_FS_IMAGE_MAGICK_LIB);
                // update LD_LIBRARY_PATH if needed
                $saved_ld = getenv('LD_LIBRARY_PATH');
                $new_ld = $imagemagick_lib;
                if (zen_not_null($saved_ld) && (!strstr($saved_ld, $new_ld))) {
                        $new_ld .= ':' . $saved_ld;
                }
                $succes = putenv('LD_LIBRARY_PATH=' . $new_ld);
                $imagemagick_home = ereg_replace(DIRECTORY_SEPARATOR . 'lib$', '', $imagemagick_lib);
                $success = $success && putenv('MAGICK_HOME=' . $imagemagick_home);
        }
        return $success;
}

/**
 * get the environment for a user-installed ImageMagick distribution
 */
function zen_imagemagick_getenv() {
        $im_env = '';
        if (zen_not_null(DIR_FS_IMAGE_MAGICK_LIB)) {
                $imagemagick_lib = ereg_replace(DIRECTORY_SEPARATOR . '$', '', DIR_FS_IMAGE_MAGICK_LIB);
                // update LD_LIBRARY_PATH if needed
                $saved_ld = getenv('LD_LIBRARY_PATH');
                $new_ld = $imagemagick_lib;
                if (zen_not_null($saved_ld) && (!strstr($saved_ld, $new_ld))) {
                        $new_ld .= ':' . $saved_ld;
                }
                $imagemagick_home = ereg_replace(DIRECTORY_SEPARATOR . 'lib$', '', $imagemagick_lib);
                $im_env = 'LD_LIBRARY_PATH="' . $new_ld . '" MAGICK_HOME="' . $imagemagick_home . '" ';
        }
        return $im_env;
}

/**
 * return version information of the specified image handler
 */
function zen_get_imagehandler_version() {
        $info = '';
        if (IMAGE_MANAGER_HANDLER == 'GD') {
                $gd_info = @gd_info();
                $info = 'GD ' . $gd_info['GD Version'];
        } elseif (IMAGE_MANAGER_HANDLER == 'ImageMagick') {
                if ((is_file(DIR_FS_IMAGE_MAGICK . 'convert')) || (is_file(DIR_FS_IMAGE_MAGICK . 'convert.exe'))) {
                        zen_imagemagick_setenv();
                        $command = DIR_FS_IMAGE_MAGICK . 'convert -version 2>&1';
                        exec($command, $im_info);
                        $version = split(' ', implode(' ', $im_info));
                        $info = $version[1] . ' ' . $version[2] . ' ' . $version[3];
                        //$info = $command . '<br />' . implode('<br/>', $im_info);
                } else {
                        zen_add_message(ERROR_IMAGE_MAGICK_NOT_FOUND, 'error');
                }
        }
        return $info;
}

/**
 * Use GD library to resize image proportionally
 */
function zen_gd_resize_image($source_name, $destination_name, $background, $newwidth = -1, $newheight = -1, $quality = 75) {
        list($width, $height) = getimagesize($source_name);
        if (($newwidth > 0) && ($newheight > 0)) {
                $canvaswidth = $newwidth;
                $canvasheight = $newheight;
                $scale = max($height / $newheight, $width / $newwidth);
                $newwidth = round($width / $scale);
                $newheight = round($height / $scale);
                $startwidth = (($canvaswidth - $newwidth)/2);
                $startheight = (($canvasheight - $newheight)/2);
        } else {
                $canvaswidth  = $newwidth  = $width;
                $canvasheight = $newheight = $height;
        }
        $source = zen_load_gd_image($source_name);
        $destination = zen_create_gd_image($canvaswidth, $canvasheight, $background);
        imagealphablending($destination, true);
        $image_extension = strtolower(substr($destination_name, strrpos($destination_name, '.')));
        $transparent = ((!(strpos($background, 'transparent')) === FALSE)
                                                && (($image_extension == '.gif')
                                                || ($image_extension == '.png')));
        if ($transparent) {
                imagecopyresized($destination, $source, $startwidth, $startheight, 0, 0, $newwidth, $newheight, $width, $height);
                //imagecopyresampled gives strange results on transparent backgrounds/images.
                //imagecopyresampled($destination, $source, $startwidth, $startheight, 0, 0, $newwidth, $newheight, $width, $height);
        } else {
                imagecopyresampled($destination, $source, $startwidth, $startheight, 0, 0, $newwidth, $newheight, $width, $height);
        }
        imagedestroy($source);
        zen_save_gd_image($destination, $destination_name, $quality);
        imagedestroy($destination);

}

/**
 * Render image at specified dimensions
 */
function zen_imagemagick_render_image($source_name, $destination_name, $background, $size, $quality) {
        global $messageStack;
        zen_imagemagick_setenv();
        bmz_set_visible($source_name);
        bmz_set_visible($destination_name);
        $command  = DIR_FS_IMAGE_MAGICK . "convert -size " . $size . " xc:none -fill " . $background . " -draw 'color 0,0 reset' " . $source_name;
        $command .= " -compose Over -gravity Center -geometry " . $size . " -composite -quality " . $quality . " " . $destination_name;   
        exec($command . ' 2>&1', $message);
        if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
        $message = null;
        bmz_set_visible($destination_name);
}

/**
 * Use ImageMagick to resize image proportionally
 */
function zen_imagemagick_resize_image($source_name, $destination_name, $background, $size, $quality = 75) {
        $background = trim($background);
        // if $background string contains no 'transparent' substring 
        if (strpos($background, 'transparent') === FALSE) {
                zen_imagemagick_render_image($source_name, $destination_name, $background, $size, $quality);
        } else {
                $background = ereg_replace('transparent', '', $background);
                $background = trim($background);
                // special treatment for smooth transparent gif to background color rendering
                $destination_image_extension =  substr($destination_name, strrpos($destination_name, '.'));
                if ($destination_image_extension == '.gif') {
                        $background = ($background != '') ? $background : 'white';
                        $threshold = "20%"; // threshold where semitransparent pixels turn to background color.
                        zen_imagemagick_render_gif($source_name, $destination_name, $background, $size, $threshold);
                } else {
                        zen_imagemagick_render_image($source_name, $destination_name, 'transparent', $size, $quality);
                }
        }
}

/**
 * Calculate desired image size as set in admin->configuration->images.
 */
function zen_calculate_image_size($image_name, $pref_width, $pref_height = '') {
        list($width, $height) = @getimagesize($image_name);
        $width = intval($width);
        $height = intval($height);
        // default: nothing happens (preferred dimension = actual dimension)
        $newwidth = $width;
        $newheight = $height;
        if (($width > 0) && ($height > 0)) {
                if (!(strrpos($pref_width . $pref_height, '%') === FALSE)) {
                        // possible scaling to % of original size
                        // calculate new dimension in pixels
                        $scale = intval($pref_width . $pref_height) / 100;
                        $newwidth = floor($width * $scale);
                        $newheight = floor($height * $scale);
                } else {
                        $force_canvas_width = !(strrpos($pref_width . $pref_height, '!') === FALSE); 
                        // failsafe for old zen-cart configuration one image dimension set to 0
                        $pref_width = ($pref_width == '' || intval($pref_width) == 0) ? 0 : intval($pref_width);
                        $pref_height = ($pref_height == '' || intval($pref_height) == 0) ? 0 : intval($pref_height);
                        if ((!$force_canvas_width) && ($pref_width != 0) && ($pref_height != 0)) {
                                // if no '!' is appended to dimensions we don't force the canvas size to
                                // match the preferred size. the image will not have the exact specified size.
                                // (we're in fact forcing the old 0-dimension zen-magic trick)
                                $oldratio = $width / $height;
                                $pref_ratio = $pref_width / $pref_height;
                                if ($pref_ratio > $oldratio) {
                                        $pref_width = 0;
                                } else {
                                        $pref_height = 0;
                                }
                        }
                        // now deal with the calculated preferred sizes
                        if (($pref_width == 0) && ($pref_height > 0)) {
                                // image dimensions are calculated to fit the preferred height
                                $pref_width = floor($width / ($height / $pref_height));
                        } elseif (($pref_width > 0) && ($pref_height == 0)) {
                                // image dimensions are calculated to fit the preferred width
                                $pref_height = floor($height / ($width / $pref_width));
                        }
                        if ((($pref_width > 0) && ($pref_height > 0)) 
                                && (($pref_width < $width ) || ($pref_height < $height))) {
                                // only calculate new dimensions if image is larger than
                                // preferred size, do not calculate dimensions larger than original
                                $newwidth = $pref_width;
                                $newheight = $pref_height;
                        }
                }
        }
        $resize = (($newwidth != $width) || ($newheight != $height));
        return array($newwidth, $newheight, $resize);
}

/**
 * get image string for large images. honor wishes for watermarked images.
 * if no large image available, get medium.
 */
function zen_get_large_image($image_base, $image_extension) {
        $file_extension = ((LARGE_IMAGE_FILETYPE == 'no_change') ? $image_extension : '.' . LARGE_IMAGE_FILETYPE);
        if (WATERMARK_LARGE_IMAGES == 'True') {
                $image = DIR_WS_IMAGES . 'large/watermark/' . $image_base . IMAGE_SUFFIX_LARGE . $file_extension;
                $unmarked_image = DIR_WS_IMAGES . 'large/' . $image_base . IMAGE_SUFFIX_LARGE . $file_extension;
                if (!file_exists(DIR_FS_CATALOG . $image)) {
                        bmz_set_visible(DIR_FS_CATALOG . $unmarked_image);
                        if (!file_exists(DIR_FS_CATALOG . $unmarked_image)) {
                                $image = zen_get_medium_image($image_base, $image_extension);
                        } elseif (IMAGE_MANAGER_HANDLER && (IMAGE_MANAGER_HANDLER != 'none')) {
                                zen_create_marked_large_image($image_base, $file_extension);
                        } else {
                                $image = $unmarked_image;
                        }
                } else {
                        $marked_image_mtime = filemtime(DIR_FS_CATALOG . $image);
                        bmz_set_visible(DIR_FS_CATALOG . $unmarked_image);
                        if ((file_exists($unmarked_image))
                                        && ((@filemtime(DIR_FS_CATALOG . $unmarked_image) > $marked_image_mtime)
                                        || (@filemtime(DIR_FS_CATALOG . DIR_WS_IMAGES . 'large/watermark_LRG.png') > $marked_image_mtime))) {
                                zen_create_marked_large_image($image_base, $file_extension);
                        } 
                        bmz_set_invisible(DIR_FS_CATALOG . $unmarked_image);
                }
        } else {
                $image = DIR_WS_IMAGES . 'large/' . $image_base . IMAGE_SUFFIX_LARGE . $file_extension;
                bmz_set_visible(DIR_FS_CATALOG . $image);
                if (!file_exists(DIR_FS_CATALOG . $image)) {
                        $image = zen_get_medium_image($image_base, $image_extension);
                }
        }
        return $image;
}

/**
 * get image string for medium images. honor wishes for watermarked images.
 * if no medium image available, get small.
 */
function zen_get_medium_image($image_base, $image_extension) {
        $file_extension = ((MEDIUM_IMAGE_FILETYPE == 'no_change') ? $image_extension : '.' . MEDIUM_IMAGE_FILETYPE);
        if (WATERMARK_MEDIUM_IMAGES == 'True') {
                $image = DIR_WS_IMAGES . 'medium/watermark/' . $image_base . IMAGE_SUFFIX_MEDIUM . $file_extension;
                $unmarked_image = DIR_WS_IMAGES . 'medium/' . $image_base . IMAGE_SUFFIX_MEDIUM . $file_extension; 
                if (!file_exists(DIR_FS_CATALOG . $image)) {
                        bmz_set_visible(DIR_FS_CATALOG . $unmarked_image);
                        if (!file_exists(DIR_FS_CATALOG . $unmarked_image)) {
                                $image = zen_get_small_image($image_base . $image_extension);
                        } elseif (IMAGE_MANAGER_HANDLER && (IMAGE_MANAGER_HANDLER != 'none')) {
                                zen_create_marked_medium_image($image_base, $file_extension);
                        } else {
                                $image = $unmarked_image;
                        }
                } else {
                        $marked_image_mtime = filemtime(DIR_FS_CATALOG . $image);
                        bmz_set_visible(DIR_FS_CATALOG . $unmarked_image);
                        if ((file_exists($unmarked_image))
                                        && ((@filemtime(DIR_FS_CATALOG . $unmarked_image) > $marked_image_mtime)
                                        || (@filemtime(DIR_FS_CATALOG . DIR_WS_IMAGES . 'medium/watermark_MED.png') > $marked_image_mtime))) {
                                zen_create_marked_medium_image($image_base, $file_extension);
                        } 
                        bmz_set_invisible(DIR_FS_CATALOG . $unmarked_image);
                }
        } else {
                $image = DIR_WS_IMAGES . 'medium/' . $image_base . IMAGE_SUFFIX_MEDIUM . $file_extension;
                bmz_set_visible(DIR_FS_CATALOG . $image);
                if (!file_exists(DIR_FS_CATALOG . $image)) {
                        $image = zen_get_small_image($image_base .$image_extension);
                }
        }
        return $image;
}

/**
 * get image string for small images. honor wishes for watermarked images.
 * if no small image available, return an empty string (maybe NULL is better?).
 */
function zen_get_small_image($image_name) {
        if (WATERMARK_SMALL_IMAGES == 'True') {
                $image = DIR_WS_IMAGES . 'watermark/' . $image_name;
                $unmarked_image = DIR_WS_IMAGES . $image_name; 
                if (!file_exists(DIR_FS_CATALOG . $image)) {
                        bmz_set_visible(DIR_FS_CATALOG . $unmarked_image);
                        if (!file_exists(DIR_FS_CATALOG . $unmarked_image)) {
                                $image = DIR_WS_IMAGES;
                        } elseif (IMAGE_MANAGER_HANDLER && (IMAGE_MANAGER_HANDLER != 'none')) {
                                zen_create_marked_small_image($image_name);
                        } else {
                                $image = $unmarked_image;
                        }
                } else {
                        $marked_image_mtime = filemtime(DIR_FS_CATALOG . $image);
                        bmz_set_visible(DIR_FS_CATALOG . $unmarked_image);
                        if ((file_exists($unmarked_image))
                                        && ((@filemtime(DIR_FS_CATALOG . $unmarked_image) > $marked_image_mtime)
                                        || (@filemtime(DIR_FS_CATALOG . DIR_WS_IMAGES . 'watermark.png') > $marked_image_mtime))) {
                                zen_create_marked_small_image($image_name);
                        } 
                        bmz_set_invisible(DIR_FS_CATALOG . $unmarked_image);
                }
        } else {
                $image = DIR_WS_IMAGES . $image_name;
                bmz_set_visible(DIR_FS_CATALOG . $image);
        }
        return $image;
}

/**
 * Use the appropriate GD function to create an image from filename.
 */
function zen_load_gd_image($source_name) {
        bmz_set_visible($source_name);
        $image_extension = substr($source_name, strrpos($source_name, '.'));
        switch (strtolower($image_extension)) {
                case '.gif':
                        // load and put into rgb colorspace 
                        list($width, $height) = getimagesize($source_name);
                        $gif_image = imagecreatefromgif($source_name);
                        $image = zen_create_gd_image($width, $height);
                        imagealphablending($image, true);
                        imagecopy($image, $gif_image, 0, 0, 0, 0, $width, $height);
                        break;
                case '.png':
                        $image = imagecreatefrompng($source_name);
                        break;
                case '.jpg':
                        $image = imagecreatefromjpeg($source_name);
                        break;
                case '.jpeg':
                        $image = imagecreatefromjpeg($source_name);
                        break;
        }
        return $image;
}

/**
 * Use the appropriate GD function to save an image to the filesystem
 */
function zen_save_gd_image($image, $destination_name, $quality = 75) {
        bmz_set_visible($destination_name);
        $image_extension = substr($destination_name, strrpos($destination_name, '.'));
        switch (strtolower($image_extension)) {
                case '.gif':
                        imagetruecolortopalette($image, false, 256);
                        imagegif($image, $destination_name);
                        break;
                case '.png': imagepng($image, $destination_name, $quality); break;
                case '.jpg': imagejpeg($image, $destination_name, $quality); break;
                case '.jpeg': imagejpeg($image, $destination_name, $quality); break;
        }
        bmz_set_visible($destination_name);
}

/**
 * Use GD library to create a transparent image.
 */
function zen_create_gd_image($width, $height, $background = 'transparent') {
        $image = imagecreatetruecolor($width, $height);

        // default to white as "background" -> better rendering on bright pages
        // when downsampling to gif with just boolean transparency
        $transparent = !(strpos($background, 'transparent') === FALSE);
        $background = trim(ereg_replace('transparent', '', $background));
        list($red, $green, $blue)= split('[, :]', $background);
        if (preg_match('/[0-9]+/', $red.$green.$blue)) {
                $background_color = imagecolorallocate($image, intval($red), intval($green), intval($blue));
        } else {
                $background_color = imagecolorallocate($image, 255, 255, 255);
        }
        imagefilledrectangle($image, 0, 0, $width - 1, $height - 1, $background_color);
        if ($transparent) {
                imagecolortransparent($image, $background_color);
        }
        return $image;
}
 
/**
 * Use GD library to overlay a source image with a watermark with given
 * opacity and save the composition to the filesystem.
 */
function zen_gd_watermark_image($source_name, $watermark_name, $destination_name, $quality = 75) {
        bmz_set_visible($source_name);
        $image = zen_load_gd_image($source_name);
        imagealphablending($image, true);
        $watermark = zen_load_gd_image($watermark_name);
        $imagewidth = imagesx($image);
        $imageheight = imagesy($image);
        $watermarkwidth =  imagesx($watermark);
        $watermarkheight =  imagesy($watermark);

        // Calculate watermark position from gravity setting. Center as default.
        $startheight = (($imageheight - $watermarkheight)/2);
        $startwidth = (($imagewidth - $watermarkwidth)/2);
        if (!(strpos(WATERMARK_GRAVITY, 'North') === FALSE)) {
                $startheight = 0;
        } elseif (!(strpos(WATERMARK_GRAVITY, 'South') === FALSE)) {
                $startheight = $imageheight - $watermarkheight;
        }
        if (!(strpos(WATERMARK_GRAVITY, 'West') === FALSE)) {
                $startwidth = 0;
        } elseif (!(strpos(WATERMARK_GRAVITY, 'East') === FALSE)) {
                $startwidth = $imagewidth - $watermarkwidth;
        }

        imagecopy($image, $watermark, $startwidth, $startheight, 0, 0, $watermarkwidth, $watermarkheight);
        imagedestroy($watermark); 
        zen_save_gd_image($image, $destination_name, $quality);
        imagedestroy($image);
        if (is_file($source_name)) bmz_set_invisible($source_name);
}

/**
 * If a combined background (like transparent white or transparent black) is given,
 * we are able to render the semitransparent pixels to what they would look
 * like on the given background-color. The threshold specifies the amount of
 * transparency that is needed, before the pixel is rendered completely transparent.
 * the lower the threshold (0%-100%) is, the more actual color is needed for the 
 * semitransparent pixel to be painted. 
 */
function zen_imagemagick_render_gif($source_name, $destination_name, $background, $size, $threshold) {
        global $messageStack;
        zen_imagemagick_setenv();
        bmz_set_visible($source_name);
        bmz_set_visible($destination_name);
        $image_extension = substr($source_name, strrpos($source_name, '.'));
        // get image base by stripping off image extension
        $source_base = ereg_replace($image_extension . '$', '', $source_name);
    $background_image = $source_base . "-BACKGROUND.png";
    // create background colored image with dimensions from source image
    $environment = zen_imagemagick_getenv() . ' ';  
        $command = DIR_FS_IMAGE_MAGICK . "convert -size " . $size . " " . $source_name . " -fill " . $background . " -draw 'color 0,0 reset' -geometry " . $size . " " . $background_image;
        exec($command . ' 2>&1', $message);
        if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
        $message = null;

        // cut out shape from background image and scale to specified .
        $command = DIR_FS_IMAGE_MAGICK . "convert " . $background_image . " -size " . $size . " " . $source_name . " -channel Alpha -threshold " . $threshold . " -compose CopyOpacity -geometry " . $size . " -composite " . $background_image; 
        exec($command . ' 2>&1', $message);
        if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
        $message = null;
        //overlay image onto background
        $command = DIR_FS_IMAGE_MAGICK . "composite -compose Atop -size " . $size . " " . $source_name . " " . $background_image . " -geometry " . $size . " " . $destination_name; 
        exec($command . ' 2>&1', $message);
        if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
        $message = null;
        // resize image canvas to specified size
        $command = DIR_FS_IMAGE_MAGICK . "montage -background transparent -size " . $size . " " . $destination_name . " -geometry " . $size . " " . $destination_name; 
        exec($command . ' 2>&1', $message);
        if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
        $message = null;
        bmz_set_visible($destination_name);
        // remove background image
    if (is_file($background_image)) {
            @unlink($background_image);
        }
}

/**
 * Use ImageMagic binaries to ovarlay a source image with a watermark
 * and save the composition to the filesystem.
 */
function zen_imagemagick_watermark_image($source_name, $watermark_name, $destination_name, $background, $quality='75') {
        zen_imagemagick_setenv();
        bmz_set_visible($source_name);
        bmz_set_visible($destination_name);
        list($width, $height) = getimagesize($source_name);
        $size = $width . 'x' . $height;
        $image_extension = substr($destination_name, strrpos($destination_name, '.'));
        $command = DIR_FS_IMAGE_MAGICK . 'convert -size ' . $size . ' ' . $source_name . ' -geometry ' . $size . ' -gravity ' . WATERMARK_GRAVITY . ' ' . $watermark_name . ' -compose Over -geometry 100% -composite ';
    $environment = zen_imagemagick_getenv() . ' ';  
        // if $background string contains no 'transparent' substring or image is no gif
        if (($image_extension != '.gif') || (strpos($background, 'transparent') === FALSE)) {
                        $command .= $destination_name;
                exec($command . ' 2>&1', $message);
                if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
                $message = null;
        } else {
                // special treatment for smooth transparent gif to background color rendering
                $background = trim(ereg_replace('transparent', '', $background));
                $image_base = ereg_replace($image_extension . '$', '', $destination_name);
                $temp_image = $image_base . '.png';
                $command .= $temp_image;
                exec($command . ' 2>&1', $message);
                if ($message) zen_add_message(sprintf(ERROR_EXECUTING_IMAGE_MAGICK, $command) . implode('<br/>', $message), 'error');
                $message = null;
                $background = ($background != '') ? $background : 'white';
                $threshold = "90%"; // threshold where semitransparent pixels turn to background color.
                zen_imagemagick_render_gif($temp_image, $destination_name, $background, $size, $threshold);
                if (($destination_name != $temp_image) && (is_file($temp_image))){
                        @unlink($temp_image);
                }
        }
        if (is_file($source_name)) bmz_set_invisible($source_name);
        bmz_set_visible($destination_name);
}

/**
 * create a new watermarked image composing the original image specified by
 * image_path, image_base and image_extension and the watermark itself
 */
function zen_create_marked_small_image($image_name) {
        $watermark_name = DIR_WS_IMAGES . 'watermark.png';
        $unmarked_image_name = DIR_WS_IMAGES . $image_name;
        $watermarked_image_name = DIR_WS_IMAGES . 'watermark/' . $image_name;
        $image_path = dirname($image_name);
        mkdirr(DIR_FS_CATALOG . DIR_WS_IMAGES . "watermark/" . $image_path);
        if (is_file(DIR_FS_CATALOG . $watermark_name)) {
                if (IMAGE_MANAGER_HANDLER == 'ImageMagick') {
                        zen_imagemagick_watermark_image(DIR_FS_CATALOG . $unmarked_image_name, DIR_FS_CATALOG . $watermark_name, DIR_FS_CATALOG . $watermarked_image_name, SMALL_IMAGE_BACKGROUND, SMALL_IMAGE_QUALITY);
                } elseif (IMAGE_MANAGER_HANDLER == 'GD') {
                        zen_gd_watermark_image(DIR_FS_CATALOG . $unmarked_image_name, DIR_FS_CATALOG . $watermark_name, DIR_FS_CATALOG . $watermarked_image_name, SMALL_IMAGE_QUALITY);
                }
                if (is_file(DIR_FS_CATALOG . $unmarked_image_name)) bmz_set_invisible(DIR_FS_CATALOG . $unmarked_image_name);
        }
}

/**
 * create a new watermarked image composing the original image specified by
 * image_path, image_base and image_extension and the watermark itself
 */
function zen_create_marked_medium_image($image_base, $image_extension) {
        $watermark_name = DIR_WS_IMAGES . 'medium/watermark' . IMAGE_SUFFIX_MEDIUM . '.png';
        $unmarked_image_name = DIR_WS_IMAGES . 'medium/' . $image_base . IMAGE_SUFFIX_MEDIUM . $image_extension;
        $watermarked_image_name = DIR_WS_IMAGES . 'medium/watermark/' . $image_base . IMAGE_SUFFIX_MEDIUM . $image_extension;
        $image_path = dirname($image_base);
        mkdirr(DIR_FS_CATALOG . DIR_WS_IMAGES . "medium/watermark/" . $image_path);
        if (is_file(DIR_FS_CATALOG . $watermark_name)) {
                if (IMAGE_MANAGER_HANDLER == 'ImageMagick') { 
                        zen_imagemagick_watermark_image(DIR_FS_CATALOG . $unmarked_image_name, DIR_FS_CATALOG . $watermark_name, DIR_FS_CATALOG . $watermarked_image_name, MEDIUM_IMAGE_BACKGROUND, MEDIUM_IMAGE_QUALITY);
                } elseif (IMAGE_MANAGER_HANDLER == 'GD') {
                        zen_gd_watermark_image(DIR_FS_CATALOG . $unmarked_image_name, DIR_FS_CATALOG . $watermark_name, DIR_FS_CATALOG . $watermarked_image_name, MEDIUM_IMAGE_QUALITY);
                }
                if (is_file(DIR_FS_CATALOG . $unmarked_image_name)) bmz_set_invisible(DIR_FS_CATALOG . $unmarked_image_name);
        }
}

/**
 * create a new watermarked image composing the original image specified by
 * image_path, image_base and image_extension and the watermark itself
 */
function zen_create_marked_large_image($image_base, $image_extension) {
        $watermark_name = DIR_WS_IMAGES . 'large/watermark' . IMAGE_SUFFIX_LARGE . '.png';
        $unmarked_image_name = DIR_WS_IMAGES . 'large/' . $image_base . IMAGE_SUFFIX_LARGE . $image_extension;
        $watermarked_image_name = DIR_WS_IMAGES . 'large/watermark/' . $image_base . IMAGE_SUFFIX_LARGE . $image_extension;
        $image_path = dirname($image_base);
        mkdirr(DIR_FS_CATALOG . DIR_WS_IMAGES . "large/watermark/" . $image_path);
        if (is_file(DIR_FS_CATALOG . $watermark_name)) {
                if (IMAGE_MANAGER_HANDLER == 'ImageMagick') { 
                        zen_imagemagick_watermark_image(DIR_FS_CATALOG . $unmarked_image_name, DIR_FS_CATALOG . $watermark_name, DIR_FS_CATALOG . $watermarked_image_name, LARGE_IMAGE_BACKGROUND, LARGE_IMAGE_QUALITY);
                } elseif (IMAGE_MANAGER_HANDLER == 'GD') {
                        zen_gd_watermark_image(DIR_FS_CATALOG . $unmarked_image_name, DIR_FS_CATALOG . $watermark_name, DIR_FS_CATALOG . $watermarked_image_name, LARGE_IMAGE_QUALITY);
                }
                if (is_file(DIR_FS_CATALOG . $unmarked_image_name)) bmz_set_invisible(DIR_FS_CATALOG . $unmarked_image_name);
        }
}


function zen_add_message($message, $message_type) {
        global $messageStack;
//      if ($this->message_location == 'direct') {
                $messageStack->add($message, $message_type);
//      } else {
//              $messageStack->add_session($message, $message_type);
//      }
}

function bmz_set_visible($filename) {
        // permissions are taken from images folder. if you want to override:
        // set $perms to 0777 or 0666 if your scripts are running as e.g. 'apache', 'www' or 'nobody' instead of your own username.
        // set $perms to 0755 or 0644 if your scripts are running as your own user instead of e.g. 'nobody'.
        $perms = fileperms(DIR_FS_CATALOG . DIR_WS_IMAGES);
        $perms &= 00777; //remove sticky bits
        //Now transform x to r for files
        $perms |= (($perms & 00001) == 00001) ? 00004 : 00000;
        $perms |= (($perms & 00010) == 00010) ? 00040 : 00000;
        $perms |= (($perms & 00100) == 00100) ? 00400 : 00000;

        @chmod($filename, $perms);
        if (CLONE_IMAGE_DIR_OWNER == 'true') {
                $owner = fileowner(DIR_FS_CATALOG . DIR_WS_IMAGES);
//              echo 'Change owner of ' . $filename . ' to ' . $owner . ': ';
                @chown($filename, $owner);
        }
}

function bmz_set_invisible($filename) {
        $perms = 0000;
        @chmod($filename, $perms);
}

        /**
         * Create a directory structure recursively
         *
         * @author      Aidan Lister <aidan@php.net>
         * @version     1.0.0
         * @param       string   $pathname    The directory structure to create
         * @return      bool     Returns TRUE on success, FALSE on failure
         */
        // permissions are taken from images folder. if you want to override:
        // set $mode to 0777 if your scripts are run as e.g. 'apache', 'www' or 'nobody' instead of your own username.
        // set $mode to 0755 or 0711 if your scripts are run as your own user instead of e.g. 'nobody'.
        function mkdirr($pathname, $mode = null, $owner = null)
        {
                if ($mode == null) {
                        $mode = fileperms(DIR_FS_CATALOG . DIR_WS_IMAGES);
                        $mode &= 00777; //remove sticky bits

                }
                if (($owner == null) && (CLONE_IMAGE_DIR_OWNER == 'true')) {
                        $owner = fileowner(DIR_FS_CATALOG . DIR_WS_IMAGES);
                }

            // Check if directory already exists
            if (is_dir($pathname) || empty($pathname)) {
                return true;
            }

            // Ensure a file does not already exist with the same name
            if (is_file($pathname)) {
                trigger_error('mkdirr() File exists', E_USER_WARNING);
                return false;
            }

            // Crawl up the directory tree
            $next_pathname = substr($pathname, 0, strrpos($pathname, DIRECTORY_SEPARATOR));
            if (mkdirr($next_pathname, $mode, $owner)) {
                if (!file_exists($pathname)) {
                    $error = mkdir($pathname, $mode);
                                if (CLONE_IMAGE_DIR_OWNER == 'true') {
                                        @chown($pathname, $owner);
                                }
                                return $error;
                }
            }

            return false;
        }