Fred's ImageMagick Scripts



 

 

DOWNSIZE


Downsizes (reduces) an image to a specified file size.

Download Script

last modified: December 24, 2009



USAGE: downsize [-s size] [-t toler] [-c copy] infile outfile
USAGE: downsize [-help]

-s .... size ........ desired output file size in kilobytes; float>0;
..................... default=200 -t .... toler ....... tolerance or allowed size of result greater than
..................... desired size expressed as percent of desired size;
..................... float>=0; default=1
-c .... copy ........ copy to output when not downsizing if no image
..................... format change; yes (y) or no (n); default=yes

PURPOSE: To downsize (reduce) an image to a specified file size.

DESCRIPTION: DOWNSIZE reduces an image's dimensions to achieve a specified file size. Typically the process results in a file size that is slightly larger than desired. So the process is iterated until some tolerance is achieved. From limited experience, the first pass will usually be within 10% of the desired size and the second pass will get to within 1%. If the input image is smaller than the desired filesize, then the user may choose to copy the input to the output or just skip processing the input image.

ARGUMENTS:

-s size ... SIZE is the desired output image size in kilobytes. Values are floats>0. The default=200

-t toler ... TOLER is allowed size of the result greater than the desire size expressed as a percent of the desired size. Values are floats>=0. The default=1. Processing will iterate until the resulting image size is less than the desired size plus the tolerance. If the tolerance is 0, then iteration continues until the output size is actually less the desired size, but this may take many iterations and thus longer processing times. From limited experience, the first pass will usually be within 10% of the desired size and the second pass will usually be within 1%.

-c copy ... COPY will copy the input to the output when the desired size is not less than the input size for input and output have the same file format; Values are either: yes (y) or no (n); default=yes

CAVEAT: No guarantee that this script will work on all platforms, nor that trapping of inconsistent parameters is complete and foolproof. Use At Your Own Risk.


EXAMPLES


Original:
(756 x 572; 726.153 KB)

Arguments:
-s 200 -t 1 -c yes
(default)
(404 x 305; 200.249 KB)



What the script does is as follows:

  • copies the image to the same file type (format)
    in case IM has different compression
  • computes the size of copied image
  • computes the resize ratio between the copied image size
    and the desired size
  • resizes the copied image
  • iterates if the resized image is larger than the desired
    size by the tolerance amount.

This is equivalent to the following IM commands for the default case

  • convert -quiet -regard-warnings "$infile" -strip +repage "$tmpA1"
  • fullsize=`convert $tmpA1 ${ftype}:- | convert - -ping -format "%b" info:`
  • size2=`convert xc: -format "%[fx:$size*1000]" info:`
  • i=1
  • diffsize=0
  • iterate=1
  • while [ $iterate -eq 1 ]; do
    size2=`convert xc: -format "%[fx:$size2-($diffsize*1000)]" info:`
    pratio=`convert xc: -format "%[fx:100*sqrt($size2/$fullsize)]" info:`
    convert $tmpA1 -resize ${pratio}% ${ftype}:$outfile
    newsize=`convert $outfile -ping -format "%b" info:`
    newsize=`convert xc: -format "%[fx:$newsize/1000]" info:`
    echo "i=$i; newsize=${newsize}kB"
    diffsize=`convert xc: -format "%[fx:($newsize-$size)]" info:`
    iterate=`convert xc: -format "%[fx:$diffsize>($toler*$size/100)?1:0]" info:`
    i=$(($i+1))
    done