Index: image.imagemagick.inc
===================================================================
RCS file: /cvs/drupal-contrib/contributions/modules/image/image.imagemagick.inc,v
retrieving revision 1.15
diff -u -p -u -r1.15 image.imagemagick.inc
--- image.imagemagick.inc	19 Aug 2007 19:01:54 -0000	1.15
+++ image.imagemagick.inc	22 Aug 2007 18:41:54 -0000
@@ -64,20 +64,22 @@ function _image_imagemagick_check_path($
 /**
  * Invoke hook_imagemagick_alter().
  *
- * Implementors of hook_imagemagick_alter() should accept two parameters: $op
- * and &$args (passed by reference), which are described below.
+ * Implementors of hook_imagemagick_alter() should accept three parameters: $op,
+ * $filepath and &$args (passed by reference), which are described below.
  *
  * @param $op
  *   String with the operation: 'resize', 'crop', 'rotate'.
+ * @param $filepath
+ *   String containing the path to the image that is being processed.
  * @param $args
  *   Array containing ImageMagick options.
  * @return
  *   Array of modified arguments.
  */
-function _image_imagemagick_alter_invoke($op, $args) {
+function _image_imagemagick_alter_invoke($op, $filepath, $args) {
   foreach (module_implements('imagemagick_alter') as $module) {
     $function = $module .'_imagemagick_alter'; 
-    $function($op, $args);
+    $function($op, $filepath, $args);
   }
   return $args;
 }
@@ -87,7 +89,7 @@ function _image_imagemagick_alter_invoke
  */
 function image_imagemagick_resize($source, $dest, $width, $height) {
   $args = array('resize' => '-resize '. $width .'x'. $height .'!');
-  $args = _image_imagemagick_alter_invoke('resize', $args);
+  $args = _image_imagemagick_alter_invoke('resize', $source, $args);
   return _image_imagemagick_convert($source, $dest, $args);
 }
 
@@ -99,7 +101,7 @@ function image_imagemagick_rotate($sourc
     'rotate' => '-rotate '. (float) $degrees,
     'background' => '-background #'. str_pad(dechex($bg_color), 6, 0),
   );
-  $args = _image_imagemagick_alter_invoke('rotate', $args);
+  $args = _image_imagemagick_alter_invoke('rotate', $source, $args);
   return _image_imagemagick_convert($source, $dest, $args);
 }
 
@@ -108,7 +110,7 @@ function image_imagemagick_rotate($sourc
  */
 function image_imagemagick_crop($source, $dest, $x, $y, $width, $height) {
   $args = array('crop' => '-crop '. $width .'x'. $height .'+'. $x .'+'. $y);
-  $args = _image_imagemagick_alter_invoke('crop', $args);
+  $args = _image_imagemagick_alter_invoke('crop', $source, $args);
   return _image_imagemagick_convert($source, $dest, $args);
 }
 
--- D:/drupal/drupal5/sites/all/modules/image/contrib/image_im_advanced/image_im_advanced.info
+++ D:/drupal/drupal5/sites/all/modules/image/contrib/image_im_advanced/image_im_advanced.info
@@ -0,0 +1,4 @@
+; $Id$
+name = ImageMagick Advanced Options
+description = Adds advanced options to the ImageMagick image toolkit.
+package = Image

--- D:/drupal/drupal5/sites/all/modules/image/contrib/image_im_advanced/image_im_advanced.module
+++ D:/drupal/drupal5/sites/all/modules/image/contrib/image_im_advanced/image_im_advanced.module
@@ -0,0 +1,209 @@
+<?php
+// $Id$
+
+/**
+ * Retrieve the settings array.
+ */
+function image_im_advanced_options() {
+  $defaults = array(
+    'jpeg_quality' => 75,
+    'strip' => '150x150',
+    'colorspace' => 'rgb',
+    'density' => 1,
+    'unsharp' => array(
+      'radius' => 0.9,
+      'amount' => 0,
+    ), 
+    'profile' => array('path' => ''),
+  );
+  return variable_get('image_im_advanced_options', $defaults);
+}
+
+/**
+ * Implementation of hook_form_alter().
+ *
+ * Add options to the Image toolkit settings form.
+ */
+function image_im_advanced_form_alter($form_id, &$form) {
+  if ($form_id == 'system_image_toolkit_settings' && 'imagemagick' == image_get_toolkit()) {
+    $options = image_im_advanced_options();
+
+    $form['image_im_advanced_options'] = array(
+      '#type' => 'fieldset',
+      '#title' => t('ImageMagick Advanced Options'),
+      '#collapsible' => FALSE,
+      '#description' => t("These settings let you control some of ImageMagick's more advanced options."),
+      '#validate' => array('image_im_advanced_settings_validate' => array()),
+      '#tree' => TRUE,
+    );
+    $form['image_im_advanced_options']['jpeg_quality'] = array(
+      '#type' => 'textfield',
+      '#title' => t('JPEG quality'),
+      '#size' => 10,
+      '#maxlength' => 3,
+      '#default_value' => $options['jpeg_quality'],
+      '#field_suffix' => t('%'),
+      '#description' => t('Define the image quality for JPEG manipulations. Ranges from 0 to 100. Higher values mean better image quality but bigger files. <a href="!link">More information on -quality</a>', array('!link' => url('http://www.imagemagick.org/script/command-line-options.php#quality'))),
+    );
+    $form['image_im_advanced_options']['strip'] = array(
+      '#type' => 'textfield',
+      '#title' => t('Strip metadata from images at this size and below'),
+      '#default_value' => $options['strip'],
+      '#description' => t('You may choose to strip all metadata, such as camera information and color profiles, from the processed images in order to reduce their file size. Please choose at what maximum size you want images to be stripped of their metadata. Example: "150x150". Enter "0x0" to disable this feature. <a href="!link">More information on -strip</a>', array('!link' => url('http://www.imagemagick.org/script/command-line-options.php#strip'))),
+    );
+    $form['image_im_advanced_options']['colorspace'] = array(
+      '#type' => 'select',
+      '#title' => t('Convert colorspace'),
+      '#default_value' => $options['colorspace'],
+      '#options' => array(0 => '<None>', 'RGB' => 'RGB', 'Gray' => 'Gray'),
+      '#description' => t('This option lets you convert images to the specified colorspace. <a href="!link">More information on -colorspace</a>', array('!link' => url('http://www.imagemagick.org/script/command-line-options.php#colorspace'))),
+    );
+    $form['image_im_advanced_options']['density'] = array(
+      '#type' => 'checkbox',
+      '#title' => t('Change image resolution to 72 ppi'),
+      '#default_value' => $options['density'],
+      '#description' => t('If checked, this option will set the print resolution of the image to 72 pixels per inch, which is suitable for web use. This does not affect the pixel size or quality of the image.  <a href="!link">More information on -density</a>', array('!link' => url('http://www.imagemagick.org/script/command-line-options.php#density'))),
+    );
+
+    $form['image_im_advanced_options']['unsharp'] = array(
+      '#type' => 'fieldset',
+      '#title' => t('Sharpening filter'),
+      '#collapsible' => TRUE,
+      '#collapsed' => ($options['unsharp']['amount'] == 0),
+      '#description' => t('The sharpness filter is used to regain some of the sharpness that is always lost when a digital photograph is scaled down. This is equivalent to the commonly used "Unsharp Mask" filter. It is important that these values are not set too high as it can easily make the images look artificial. <a href="!link">More information on -unsharp</a>', array('!link' => url('http://www.imagemagick.org/script/command-line-options.php#unsharp'))),
+    );
+    $form['image_im_advanced_options']['unsharp']['amount'] = array(
+      '#type' => 'textfield',
+      '#title' => t('Sharpness filter strength'),
+      '#size' => 4,
+      '#maxlength' => 3,
+      '#default_value' => $options['unsharp']['amount'],
+      '#field_suffix' => t('%'),
+      '#description' => t('Apply this percentage of sharpness when scaling. 90 is recommended, although values higher than 100 are also valid. Set to 0 to disable this feature.'),
+    );
+    $form['image_im_advanced_options']['unsharp']['radius'] = array(
+      '#type' => 'textfield',
+      '#title' => t('Sharpness filter radius'),
+      '#default_value' => $options['unsharp']['radius'],
+      '#size' => 4,
+      '#maxlength' => 4,
+      '#description' => t('Use this pixel radius for the sharpness filter. 0.9 is recommended.'),
+    );
+
+    $form['image_im_advanced_options']['profile'] = array(
+      '#type' => 'fieldset',
+      '#title' => t('Color profile'),
+      '#collapsible' => TRUE,
+      '#collapsed' => empty($options['profile']['path']),
+      '#description' => t('Processed images may be converted to a color profile specified here. This is especially important when working with images that use a wide-gamut color profile such as ColorMatch or Adobe RGB, which is often the case with professional photography. sRGB (which may be downloaded from <a href="http://www.color.org/profiles.html">ICC</a>) is recommended since it is likely to look good on most displays.<br />Note that this conversion is still useful even if you choose to strip all metadata from your images (see above). This is because the conversion happens first and changes the actual image data before the profile is stripped.'),
+    );
+    $form['image_im_advanced_options']['profile']['path'] = array(
+      '#type' => 'textfield',
+      '#title' => t('Path to color profile'),
+      '#default_value' => $options['profile']['path'],
+      '#description' => t('The path to a color profile file that all scaled down images will be converted to. Leave empty to disable.'),
+    );
+
+    // Move the buttons below our additions.
+    $form['buttons']['#weight'] = 10;    
+  } 
+}
+
+
+/**
+ * Validate settings form.
+ */
+function image_im_advanced_settings_validate($form) {
+  $options = $form['#post']['image_im_advanced_options'];
+  
+  // Check that the JPEG quality is a valid number.
+  if (!is_numeric($options['jpeg_quality']) || $options['jpeg_quality'] < 1 || $options['jpeg_quality'] > 100) {
+    form_set_error('image_im_advanced_options][jpeg_quality', t('The JPEG quality must be a positive number between 1 and 100.'));
+  }
+
+  // Check that the strip dimensions are valid.
+  if (!preg_match('/^\d+x\d+$/', $options['strip'])) {
+    form_set_error('image_im_advanced_options][strip', t('The strip metadata threshold must be specified in the form <em>NxN</em>. Example: <em>150x150</em>.'));
+  }
+
+  // Check the unsharp mask values.
+  if (!empty($options['unsharp']['amount'])) {
+    if (!is_numeric($options['unsharp']['amount']) || $options['unsharp']['amount'] < 0) {
+      form_set_error('image_im_advanced_options][unsharp][amount', t('The sharpness amount must be specified as a positive number.'));
+    }
+    if (!is_numeric($options['unsharp']['radius']) || $options['unsharp']['radius'] < 0) {
+      form_set_error('image_im_advanced_options][unsharp][radius', t('The sharpness radius must be specified as a positive value.'));
+    }
+  }
+  
+  // Check that if the color profile is provided that it's a readable file.
+  if (!empty($options['profile']['path']) && (!is_file($options['profile']['path']) || !is_readable($options['profile']['path']))) {
+    form_set_error('image_im_advanced_options][profile][path', t('The ICC profile could not be read.'));
+  }
+}
+
+/**
+ * Implementation of hook_imagemagick_alter().
+ */
+function image_im_advanced_imagemagick_alter($op, $filepath, &$args) {
+  drupal_set_message('Before: <pre>' . var_export($args, TRUE) . '</pre>');
+  $options = image_im_advanced_options();
+  $image = image_get_info($filepath);
+
+  switch ($op) {
+    case 'resize':
+      // Examine the 'resize' argument to determine the new target size.
+      $size = preg_replace('/[^\d]*(\d+x\d+)[^\d]*/', '$1', $args['resize']);
+      list($width, $height) = explode('x', $size);
+
+      // Add sharpening filter.
+      if ($options['unsharp']['amount'] && $options['unsharp']['radius']) {
+        // 0.7 and 0.02 are reasonable values for Sigma and Threshold.
+        $args['unsharp'] = '-unsharp ' . $options['unsharp']['radius'] . 'x0.7+' . round($options['unsharp']['amount'] / 100, 2) . '+0.02';
+      }
+
+      // Convert to specified color profile.
+      if (!empty($options['profile']['path']) && is_readable($options['profile']['path'])) {
+        $args['profile'] = '-profile ' . $options['profile']['path'];
+      }
+      break;
+
+    case 'crop':
+      // Examine the 'crop' argument to determine the new target size.
+      $size = preg_replace('/[^\d]*(\d+x\d+)[^\d]*/', '$1', $args['crop']);
+      list($width, $height) = explode('x', $size);
+      break;
+      
+    case 'rotate':
+      // Get image size:
+      $width = $image['width'];
+      $height = $image['height'];
+      break;
+  }
+
+  // Determine if the -strip parameter should be used.
+  list($strip_width, $strip_height) = explode('x', $options['strip']);
+  if ((int) $width <= (int) $strip_width && (int) $height <= (int) $strip_height) {
+    $args['strip'] = '-strip';
+  }
+
+  if ($image['mime_type'] == 'image/jpeg') {
+    // Set JPEG quality.
+    if (empty($args['quality']) && $options['jpeg_quality']) {
+      $args['quality'] = '-quality ' . $options['jpeg_quality'];
+    }
+  }
+
+  // Convert to RGB.
+  if ($options['colorspace']) {
+    $args['colorspace'] = '-colorspace RGB';
+  }
+
+  // Change image density (this doesn't affect the image dimensions/resolution):
+  if ($options['density']) {
+    $args['density'] = '-density 72 -units PixelsPerInch';
+  }
+
+  drupal_set_message('After:<pre>' . var_export($args, TRUE) . '</pre>');
+}
+


