#!/usr/bin/env bash
#
#==============================================================================
# FILE: dimswitch
# USAGE: dimswitch [-v] [-h] [-i [application]] [-t theme name] dark/light
#
# DESCRIPTION:
# Toggle alacritty terminal, and between dark
# or light mode (if correctly set up in the alacritty.yml file), see REQUIREMENTS
# The default action is to toggle between light and dark mode.
#
# OPTIONS: see function ’usage’ below
#
# REQUIREMENTS:
# The alacritty.yml file needs to have the various color-schemes set up as yaml
# anchors. The script itself will then switch the referenced anchor in the actual
# `color` key of the file. For an example alacritty.yml refer to its wiki, or
# this file: https://gitlab.com/marty-oehme/dotfiles/blob/master/.config/alacritty/alacritty.yml
#
# NOTES:  This script is in active development and its functionality and options
#         are very much undergoing changes. For now, do not rely on its options
#         staying stable.
#
# AUTHOR:
# Marty Oehme
#
# VERSION:
ld_version="0.1.1"
#==============================================================================

#=== environment variables ====================================================
# DESCRIPTION:  Environment variables to configure the script
#==============================================================================

# Sets the programs to be dimmed
if [ -z "$DIM_PROGRAMS" ]; then DIM_PROGRAMS=(alacritty); fi

# Sets the path(s) to the alacritty configuration file
if [ -z "$DIM_ALACRITTY_CONF" ]; then DIM_ALACRITTY_CONF="$HOME/.config/alacritty/alacritty.yml:$HOME/.alacritty.yml"; fi

#=== main function ============================================================
# NAME:         main
# DESCRIPTION:  Display usage information for this script.
# PARAMETERS:   see usage function
#==============================================================================
main() {
  local cmd=""
  local ret=0

  case "$1" in
  -v | --version)
    cmd="version"
    ;;
  -h | --help)
    cmd="usage"
    ;;
  -i | --info)
    cmd="printinfo"
    ;;
  "")
    cmd="toggle"
    ;;
  esac
  shift

  $cmd "$@"
  ret=$((ret + $?))
  exit $ret
}

#=== usage function ===========================================================
# NAME:         usage
# DESCRIPTION:  Display usage information for this script.
#==============================================================================
usage() {
  local name
  name=$(basename "$0")
  cat <<EOF
$name is a command line tool to toggle alacritty terminal themes.

Usage:
    $name                                 # Toggle theme between dark and light mode
    $name                                 # Set to specified alacritty theme
    $name -i | --info                     # Print out programs to be dimmed
    $name -h | --help                     # Print this usage information
    $name -v | --version                  # Print version information
EOF
}

#=== theme info function=======================================================
# NAME:         printinfo
# DESCRIPTION:  Displays the programs to be dimmed, and the path to their
#               configuration files. Currently only alacritty is implemented.
#==============================================================================
printinfo() {
  for prog in "${DIM_PROGRAMS[@]}"; do
    local file
    file=$(getConfFile "$prog")
    if [ -z "$file" ]; then
      file="No associated configuration file found."
    fi
    echo "$prog" "-" "$file"
  done
}

#=== toggle dimming function===================================================
# NAME:         toggle
# DESCRIPTION:  Toggles between dark and light mode in alacritty.
#==============================================================================
toggle() {
  local file
  file=$(getConfFile "alacritty")
  if [ -z "$file" ]; then
    exit 1
  fi
  local line
  line=$(_findline "$file")
  if [ -z "$line" ]; then exit 1; fi

  if [[ -n $(_isdark "$file" "$line") ]]; then
    _replace "$line" "$file" dark light
    exit 0
  fi

  if [[ -n $(_islight "$file" "$line") ]]; then
    _replace "$line" "$file" light dark
    exit 0
  fi

  echo "Did not find a light/dark theme to toggle in alacritty."
  exit 1
}

#=== version function==========================================================
# NAME:         version
# DESCRIPTION:  Display the current version of the script.
#==============================================================================
version() {
  local name
  name=$(basename "$0")
  cat <<EOF
$name $ld_version
EOF
}

#=== get program's config file function =======================================
# NAME: getConfFile
# DESCRIPTION: Return the configuration file of the selected program.
# PARAMETER 1: [String] Name of Program
#==============================================================================
getConfFile() {
  local conf
  case $1 in
  alacritty)
    conf=$(_findfile "$DIM_ALACRITTY_CONF")
    ;;
  esac

  echo "$conf"
}

#=== verify file exists function ==============================================
# NAME:         _findfile
# DESCRIPTION:  Splits the string passed in into an array of paths and finds
#               the first existing file. Return nothing if no file found.
# PARAMETER 1:  [String] of paths, delimited by ":"
#==============================================================================
_findfile() {
  IFS=':' read -ra paths <<<"$1"
  for i in "${paths[@]}"; do
    if [ -f "$i" ]; then
      echo "$i"
    fi
  done
}

# function signature: _findline FILE
_findline() {
  sed -n '/^colors: .*$/=' "$1"
}

# function signature: _islight LINENUMBER FILE
_islight() {
  sed -n "$2p" "$1" | grep -e "-light$"
}

# function signature: _isdark LINENUMBER FILE
_isdark() {
  sed -n "$2p" "$1" | grep -e "-dark$"
}

# function signature: _replace LINENUMBER FILE OLD NEW
_replace() {
  sed -i "$1 s/-$3$/-$4/" "$2"
}

main "$@"