Por alguna razón las opciones funcionan bien la primera llamada de lib_progress_bar -c "@" -u "_" 0 100
, pero en la segunda llamada y más allá todo está predeterminado porque parece que getopts c:u:d:p:s:%:m: flag
no es verdad la segunda vez, o al menos la caja nunca se ejecuta cuando usé set -x
getopts no llamará dos veces seguidas?
#!/bin/bash
lib_progress_bar() {
local current=0
local max=100
local completed_char="#"
local uncompleted_char="."
local decimal=1
local prefix=" ["
local suffix="]"
local percent_sign="%"
local max_width=$(tput cols)
local complete remain subtraction width atleast percent chars
local padding=3
while getopts c:u:d:p:s:%:m: flag; do
case "$flag" in
c) completed_char="$OPTARG";;
u) uncompleted_char="$OPTARG";;
d) decimal="$OPTARG";;
p) prefix="$OPTARG";;
s) suffix="$OPTARG";;
%) percent_sign="$OPTARG";;
m) max_width="$OPTARG";;
esac
done
shift $((OPTIND-1))
current=${1:-$current}
max=${2:-$max}
if ((decimal > 0)); then
((padding = padding + decimal + 1))
fi
let subtraction=${#completed_char}+${#prefix}+${#suffix}+padding+${#percent_sign}
let width=max_width-subtraction
if ((width < 5)); then
((atleast = 5 + subtraction))
echo >&2 "the max_width of ($max_width) is too small, must be atleast $atleast"
return 1
fi
if ((current > max));then
echo >&2 "current value must be smaller than max. value"
return 1
fi
percent=$(awk -v "f=%${padding}.${decimal}f" -v "c=$current" -v "m=$max" 'BEGIN{printf('f', c/m * 100)}')
((chars = current * width/max))
# sprintf n zeros into the var named as the arg to -v
printf -v complete '%0*.*d' '' "$chars" ''
printf -v remain '%0*.*d' '' "$((width - chars))" ''
# replace the zeros with the desired char
complete=${complete//0/"$completed_char"}
remain=${remain//0/"$uncompleted_char"}
printf '%s%s%s%s %s%s\r' "$prefix" "$complete" "$remain" "$suffix" "$percent" "$percent_sign"
if ((current >= max)); then
echo ""
fi
}
lib_progress_bar -c "@" -u "_" 0 100
echo
lib_progress_bar -c "@" -u "_" 25 100
echo
lib_progress_bar -c "@" -u "_" 50 100
echo
exit;
"OPTIND = 1" también funciona. –
Utilizo 'OPTIND = 0' después de mis getopts-while-loop y shift. No sabía sobre el truco 'local OPTIND', pero el reinicio cero debería funcionar si estás extrañamente llamando' getopts' más de una vez en la _mása función_. –