diff --git a/speech/set-voice.sh b/speech/set-voice.sh index f76013a..4150d69 100755 --- a/speech/set-voice.sh +++ b/speech/set-voice.sh @@ -1,8 +1,6 @@ #!/usr/bin/env bash # Set Voice # Set the default wine voice ba$sed on installed options. -# Rate can be specified as a numeric argument to this script, 1 through 9. -# The default rate is 7 # # â– The contents of this file are subject to the Common Public Attribution @@ -44,6 +42,19 @@ #--code-- +help() { + echo "${0##*/}" + echo "Released under the terms of the Common Public Attribution License Version 1.0" + echo -e "This is a Stormux project: https://stormux.org\n" + echo -e "Usage:\n" + echo "With no arguments, open the game launcher." + for i in "${!command[@]}" ; do + echo "-${i/:/ }: ${command[${i}]}" + done | sort + exit 0 +} + + # Set a variable to make mac compatibility easier... sed="sed" grep="grep" @@ -61,29 +72,15 @@ export WINEDEBUG="-all" if [ -z "$DISPLAY" ] ; then export DISPLAY=:0 fi +# handle arguments +declare -A command=( + [b:]="the wine bottle to use." + [h]="This help screen." + [r:]="Specify voice rate, default is 7, options are 0-9 or A for fastest." + [v:]="Voice name, the voice to use, same as in the menu." +) -# Get the desired wine bottle -declare -a bottle -for i in $(find ~/.local/wine/ -maxdepth 1 -type d -not -name 'wine' | sort) ; do - bottle+=("$i" "${i##*/}") - done -export WINEPREFIX="$(dialog --backtitle "Use the up and down arrow keys to find the option you want, then press enter to select it." \ - --clear \ - --no-tags \ - --menu "Select A Wine Bottle" 0 0 0 "${bottle[@]}" --stdout)" - -if [[ -z "${WINEPREFIX}" ]]; then - exit 0 -fi - -# Get wine version if available -if [[ -r "${WINEPREFIX}/agm.conf" ]]; then - source "${WINEPREFIX}/agm.conf" - export WINE - export WINESERVER -fi -wine="${WINE:-$(command -v wine)}" msgbox() { # Returns: None @@ -143,7 +140,8 @@ set_voice() { local fullVoice local counter=0 for x in "${voiceList[@]}" ; do - [ "$x" = "$tmp" ] && break + echo "$x == $tmp" + [[ "$x" = "$tmp" ]] && break counter=$(( $counter + 1 )) done local RHVoiceName="$(find "${WINEPREFIX}/drive_c/ProgramData/Olga Yakovleva/RHVoice/data/voices/" -maxdepth 1 -type d)" @@ -153,7 +151,7 @@ set_voice() { ${wine}server -k # If we don't do this it's likely wine will overwrite our reverted change or even clobber the registry key entirely # Remove any existing rate change for voices $sed -i '/"DefaultTTSRate"=dword:/d' "${WINEPREFIX}/user.reg" - $sed -i -E -e 's/"DefaultTokenId"="HKEY_LOCAL_MACHINE\\\\(SOFTWARE|Software)\\\\(Wow6432Node\\\\|)Microsoft\\\\Speech\\\\Voices\\\\Token(Enum|)s\\\\[^"]+"/"DefaultTokenId"="HKEY_LOCAL_MACHINE\\\\'"${fullVoice//\\/\\\\}"'"\n"DefaultTTSRate"=dword:0000000'${2:-7}'/g' "${WINEPREFIX}/user.reg" + $sed -i -E -e 's/"DefaultTokenId"="HKEY_LOCAL_MACHINE\\\\(SOFTWARE|Software)\\\\(Wow6432Node\\\\|)Microsoft\\\\Speech\\\\Voices\\\\Token(Enum|)s\\\\[^"]+"/"DefaultTokenId"="HKEY_LOCAL_MACHINE\\\\'"${fullVoice//\\/\\\\}"'"\n"DefaultTTSRate"=dword:0000000'${rate:-7}'/g' "${WINEPREFIX}/user.reg" } test_voice() { @@ -183,6 +181,58 @@ EOF doRestore=1 trap restore_voice SIGINT +# Convert the keys of the command associative array to a format usable by getopts +args="${!command[*]}" +args="${args//[[:space:]]/}" +while getopts "${args}" i ; do + case "$i" in + b) + if ! [[ -d ~/".local/wine/${OPTARG}" ]]; then + echo "Invalid wine bottle specified." + exit 1 + fi + export bottle=~/".local/wine/${OPTARG}" + export WINEPREFIX=~/".local/wine/${OPTARG}" + ;; + h) help;; + r) + if ! [[ "${OPTARG}" =~ ^[0-9A]$ ]]; then + echo "Invalid rate specified. Arguments must be 0-9 or A." + exit 1 + fi + rate="${OPTARG}" + ;; + v) voice="${OPTARG}";; + esac +done + + +# Get the desired wine bottle + +# Offer a list of wine bottles if one isn't specified on the command line. +if [[ -z "${bottle}" ]]; then + declare -a bottle + for i in $(find ~/.local/wine/ -maxdepth 1 -type d -not -name 'wine' | sort) ; do + bottle+=("$i" "${i##*/}") + done + export WINEPREFIX="$(dialog --backtitle "Use the up and down arrow keys to find the option you want, then press enter to select it." \ + --clear \ + --no-tags \ + --menu "Select A Wine Bottle" 0 0 0 "${bottle[@]}" --stdout)" +fi + +if [[ -z "${WINEPREFIX}" ]]; then + exit 0 +fi + +# Get wine version if available +if [[ -r "${WINEPREFIX}/agm.conf" ]]; then + source "${WINEPREFIX}/agm.conf" + export WINE + export WINESERVER +fi +wine="${WINE:-$(command -v wine)}" + # In case the user hasn't run a game using sapi in this prefix yet, let's try to initialize all the registry keys properly. cat << "EOF" > "${bottle}/drive_c/windows/temp/speak.vbs" dim speechobject @@ -203,20 +253,22 @@ done oldVoice="$($grep -P '"DefaultTokenId"="HKEY_LOCAL_MACHINE\\\\(SOFTWARE|Software)\\\\(Wow6432Node\\\\|)Microsoft\\\\Speech\\\\Voices\\\\Token(Enum|)s\\\\[^"]+"' "${WINEPREFIX}/user.reg" | $sed -E -e 's/"DefaultTokenId"="([^"]+)"/\1/g')" exit=1 if [[ "${#voiceList[@]}" -eq 0 ]]; then -dialog --msgbox "No voices found." -1 -1 -exit 1 + dialog --msgbox "No voices found." -1 -1 + exit 1 fi while [[ $exit -ne 0 ]] ; do -voice="$(menulist "${voiceList[@]}")" + if [[ -z "${voice}" ]]; then + voice="$(menulist "${voiceList[@]}")" + fi -case $? in - 0) - set_voice "$voice" "$1" ; exit=0 ;; - 3) - test_voice "$voice";; - *) - restore_voice ; exit=0 ;; -esac -done + case $? in + 0) + set_voice "$voice" "${rate:-7}" ; exit=0 ;; + 3) + test_voice "$voice";; + *) + restore_voice ; exit=0 ;; + esac + done exit 0