#!/usr/bin/env bash
# rice-dictate - offline voice typing into the focused window (nerd-dictation).
#
#   rice-dictate toggle    start listening, or stop and finish typing
#   rice-dictate status    on / off
#
# The first run downloads a small English speech model (about 40 MB) into
# ~/.config/nerd-dictation/model. Drop a different VOSK model there to change language.
set -uo pipefail

run="${XDG_RUNTIME_DIR:-/tmp}/rice"
model_dir="${XDG_CONFIG_HOME:-$HOME/.config}/nerd-dictation/model"
model_url="https://alphacephei.com/vosk/models/vosk-model-small-en-us-0.15.zip"
mkdir -p "$run"

listening() { pgrep -u "$UID" -f 'nerd-dictation begin' >/dev/null; }
poke() { date +%s%N > "$run/dictation.rev"; }

fetch_model() {
  local tmp
  rice-notify send "Dictation" "Downloading the speech model (about 40 MB)…"
  tmp=$(mktemp -d) || return 1
  if curl -fsSL -o "$tmp/model.zip" "$model_url" && unzip -q "$tmp/model.zip" -d "$tmp"; then
    mkdir -p "$(dirname "$model_dir")"
    mv "$tmp"/vosk-model-* "$model_dir"
    rm -rf "$tmp"
    rice-notify send "Dictation" "Model ready. Press super + ctrl + x again to start."
  else
    rm -rf "$tmp"
    rice-notify send "Dictation" "Could not download the speech model"
    return 1
  fi
}

case "${1:-toggle}" in
  toggle)
    command -v nerd-dictation >/dev/null || { rice-notify send "Dictation" "Install nerd-dictation-git to dictate"; exit 1; }
    if listening; then
      nerd-dictation end
      poke
    elif [[ ! -d $model_dir ]]; then
      fetch_model
    else
      setsid -f nerd-dictation begin --simulate-input-tool=XDOTOOL >/dev/null 2>&1
      poke
      notify-send -a rice -u low -t 1500 "Dictation" "Listening. super + ctrl + x to stop."
    fi
    ;;
  status) listening && echo on || echo off ;;
  *) sed -n '2,9p' "$0" | sed 's/^# \{0,1\}//'; exit 2 ;;
esac
