87 lines
		
	
	
		
			1.9 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable file
		
	
	
	
	
			
		
		
	
	
			87 lines
		
	
	
		
			1.9 KiB
		
	
	
	
		
			Bash
		
	
	
		
			Executable file
		
	
	
	
	
| #!/usr/bin/env zsh
 | |
| 
 | |
| # Optimize image files (losslessly by default)
 | |
| #
 | |
| # Examples:
 | |
| #   imgoptim image.jpg image.png image.gif
 | |
| #   imgoptim directory_of_images/
 | |
| #   imgoptim directory_of_images/*.png
 | |
| #
 | |
| # Requires:
 | |
| #   PNGs: optipng, pngquant (lossy)
 | |
| #   JPGs: jpegtran, jpegoptim (lossy)
 | |
| #   GIFs: gifsicle
 | |
| #
 | |
| # Packages (same name on homebrew & arch linux)
 | |
| #   optipng [pngquant] libjpeg-turbo [jpegoptim] gifsicle
 | |
| 
 | |
| set -e
 | |
| unset CDPATH
 | |
| 
 | |
| _usage() {
 | |
|   cat <<EOL
 | |
| Usage: ${0:A:t} [-lh] IMAGE [IMAGE2 [IMAGE3 [...]]]
 | |
| 
 | |
|   -l    enable lossy compression
 | |
|   -h    this help
 | |
| EOL
 | |
| }
 | |
| 
 | |
| _filesize() {
 | |
|   case $OSTYPE in
 | |
|     darwin*) stat -c%s "$1" ;;
 | |
|     *) stat --printf="%s" "$1" ;;
 | |
|   esac
 | |
| }
 | |
| 
 | |
| #
 | |
| while getopts hl opt; do
 | |
|   case $opt in
 | |
|     h) _usage; exit;;
 | |
|     l) lossy=1;;
 | |
|     :) >&2 echo "$OPTARG requires an argument"; _usage; exit 1;;
 | |
|     *) >&2 echo "Not a valid arg: $opt";        _usage; exit 1;;
 | |
|   esac
 | |
| done
 | |
| shift $((OPTIND-1))
 | |
| 
 | |
| cmds=( optipng jpegtran gifsicle )
 | |
| [[ -n $lossy ]] && cmds=( $cmds pngquant jpegoptim )
 | |
| for cmd in ${cmds[@]}; do
 | |
|   if ! command -v $cmd >/dev/null; then
 | |
|     >&2 echo "$cmd isn't installed"
 | |
|     error=1
 | |
|   fi
 | |
| done
 | |
| if [[ -n $error ]]; then
 | |
|   >&2 echo "There were errors, aborting"
 | |
|   exit 1
 | |
| fi
 | |
| 
 | |
| for file in $@; do
 | |
|   if [[ -d $file ]]; then
 | |
|     imgoptim $file/*
 | |
|   elif [[ -f $file ]]; then
 | |
|     pre_size=$(_filesize "$file")
 | |
|     case ${file##*.} in
 | |
|       png)
 | |
|         [[ -n $lossy ]] && pngquant $file
 | |
|         optipng -nc -nb -o7 $file
 | |
|         ;;
 | |
|       gif)
 | |
|         gifsicle --batch --optimize=3 "$file"
 | |
|         ;;
 | |
|       jpg|jpeg)
 | |
|         [[ -n $lossy ]] && jpegoptim --max=90 "$file"
 | |
|         jpegtran -copy none -optimize -progressive -outfile "$file" "$file"
 | |
|         ;;
 | |
|       *)
 | |
|         printf "Unrecognized file '$file': ignored"
 | |
|         ;;
 | |
|     esac
 | |
|     post_size=$(_filesize "$file")
 | |
|     perc=$(echo "((${pre_size} - ${post_size}) / ${pre_size}) * 100" | bc -l)
 | |
|     printf "* %s: %d => %d (%.2f%% reduction)\n" "$file" "${pre_size}" "${post_size}" "$perc"
 | |
|   fi
 | |
| done
 |