#!/bin/bash
#
# Compress png files before inclusion to repo.
# By default, checks only change png files, but you may
# want to run it once a full-time for all files to ensure
# everything is compressed.
#

# Commit hooks disallow STDIN by default. This fixes that.
exec < /dev/tty;

_mainFn () {
  declare _reply _file_list _optipng_exe _compressed_list _is_error \
    _png_file  _size1_int _size2_int;

  _reply='';
  while ! [[ "${_reply:-}" =~ ^[CcAa] ]]; do
    read -rp 'Compress [C]hanged or [a]ll PNG files? > ' _reply;
    [ -z "${_reply:-}" ] && _reply='c';
  done

  if [[ "${_reply:-c}" =~ ^[Cc] ]]; then
    readarray -t _file_list < <(
      git diff --cached --name-only |grep '.png$'
    );
  else
    mapfile -t _file_list < <(find ./ -type f -name '*.png');
  fi

  if [ "${#_file_list[@]}" = 0 ]; then
    read -rp 'No files found. Press ENTER to continue. > ';
    exit 0;
  fi

  ( IFS=$'\n'; echo -e "Files to process: \n${_file_list[*]}\n"; )
  read -rp 'Does this list look correct? [Y/n] > ' _reply;

  if [[ "${_reply:-y}" =~ ^[Nn] ]]; then
    echo "ABORT: Per user request";
    exit 1;
  fi

  _optipng_exe="$(command -v optipng)";
  if [ -z "${_optipng_exe}" ]; then
    echo "optping does not appear installed or available.";
    echo "Please install (sudo apt install optping) or ";
    echo "adjust paths and try again.";
    echo;
    echo "ABORT: Cannot compress PNG files.";
    exit 2;
  fi

  _compressed_list=();
  _is_error='n';
  for _png_file in "${_file_list[@]}"; do
    if ! [ -e "${_png_file}" ]; then continue; fi
    _size1_int="$(stat --printf '%s' "${_png_file}")";
    if "${_optipng_exe}" -o 2 "${_png_file}"; then
      echo "ok   |${_png_file}| compressed";
      _size2_int="$(stat --printf '%s' "${_png_file}")";
      if (( _size1_int != _size2_int )); then
        _compressed_list+=( "${_png_file}" );
      fi
    else
      echo "ERR  |${_png_file}| could not compress";
      _is_error='y';
    fi
  done

  if [ "${_is_error}" = 'y' ]; then
    echo "ABORT: Cannot compress PNG files.";
    exit 3;
  fi

  if (( "${#_compressed_list[@]}" > 0 )); then
    echo;
    echo;
    echo "SOME FILES HAVE BEEN COMPRESSED:";
    (IFS=$'\n'; echo -e "${_compressed_list[*]}";)
    echo;
    echo "A git commit has NOT been made. Please review the "
    echo "changes and TRY YOUR COMMIT AGAIN.";
    exit 4;
  fi
  exit 0;
}

_mainFn;

## End
