Иногда бывает, что в скрипт надо вставить скучную команду sleep
, пока что-нибудь делается, например, поднимается сетевой интерфейс или стартует демон.
Вообще, правильнее в этих случаях писать отдельные проверки, проверяя в цикле, поднялось ли, запустилось ли нужное.
Но иногда лень и где некритично можно «просто подождать», как пелось у классика. А чтобы юзеру не было скучно, и он не думал, что наш скрипт висит, можно подменить обычный sleep
небольшим скриптом, показывающим обратный отсчет, да еще и с вращающейся псевдографической фенечкой.
Я уже когда-то поднимал этот вопрос, посему с ноля все делать не придется, нужно лишь чуть доработать имеющийся скрипт.
Итак, скрипту будут передаваться два параметра. Первый обязательный, содержащий время ожидания, и второй дополнительный — сообщение, выводимое в терминал. Если второй параметр не задан, то по умолчанию будет выдано сообщение, заранее определенное во внутренней переменной скрипта.
Определяем переменные (сообщение по умолчанию, время ожидания, счетчик текущего элемента в массиве псевдографической «мельницы» и сам массив элементов):
MESSAGE="Wait"
WTIMEOUT=0
ITEM_ARR=0 #current item counter
CH_S[0]='-' #pseudographic items
CH_S[1]='/'
CH_S[2]='|'
CH_S[3]='\'
Задаем функцию вызова краткой справки:
print_help()
{
echo "use waiter <time> [message]"
echo "<time> - wait time"
echo "[message] - optional text message"
}
Проверяем первый параметр скрипта, на предмет того, нужно ли вывести справку и завершить работу:
#parameters check
if [ -z $1 ];then #if no parameters
print_help
exit 2
fi
#if help request
if [ $1 = "-h" ];then
print_help
exit 2
fi
if [ $1 = "--help" ];then
print_help
exit 2
fi
Проверяем первый параметр скрипта на соответствие его числовому значению (
подробнее описано здесь):
if (echo $1 | grep -E -q "^?[0-9]+$");then
WTIMEOUT=$1
else
echo "Not a number in first parameter <time>"
exit 1
fi
И второй параметр. Если он не пустой, присваиваем его значение переменной, содержащей сообщение:
if [ -n "$2" ];then
MESSAGE=$2
fi
Переходим к основной части скрипта:
Выводим сообщение для пользователя и сохраняем позицию курсора:
echo -n $MESSAGE" ("$WTIMEOUT" secounds): "
tput sc #save cursor position
Ключ -n
в команде echo
означает, что следующее сообщение будет печататься на той же строке, команда echo
не совершит перевод курсора на следующую строку.
while [ $WTIMEOUT -ge 0 ]; do
#print timeout and current pseudographic char
printf '%3s %s' $WTIMEOUT ${CH_S[ITEM_ARR]}
tput rc #restore cursor position
sleep 1
#decrease timeout and increase current item ctr.
let "WTIMEOUT=WTIMEOUT-1"
let "ITEM_ARR=ITEM_ARR+1"
if [ $ITEM_ARR -eq 4 ];then
#if items ctr > number of array items
#starting with 0 item
let "ITEM_ARR=0"
fi
done
В рабочем цикле сначала выводим оставшееся время ожидания и текущий символ из массива псевдографических элементов, шаблон %3s
команды printf
означает, что если выводимая строка меньше 3 символов, недостающие с начала строки знаки заменяются пробелами, %s
, что просто выводим строку, как она есть. Далее указываются 2 переменных — оставшееся время ожидания и символ из массива.
Следующим шагом восстанавливаем позицию курсора (и все, что будет напечатано в следующей итерации цикла затрет предыдущие значения).
Далее ждем одну секунду и уменьшаем оставшееся время на 1, а счетчик текущего элемента массива увеличиваем и проверяем, не больше ли он, чем последний индекс в массиве. Если больше — присваиваем счетчику значение 0, в следующем цикле опять будет выведен нулевой элемент.
В завершении печатаем символ перехода на новую строку, чтобы следующие сообщения в следующих или в вызывающих этот скрипт скриптах начинались с новой строки
#next message starting with new string
printf '\n'
Скрипт на PasteBin
Скачать с mega.nz