0

This is a part of my bash file. The output I need is:

[ - ] Copyright of KatworX© Tech. Developed by Arjun Singh Kathait and Debugged by the ☆Stack Overflow Community☆

I want the spinner animation to continue spinning for 5 seconds while the echo command is being displayed. Can the community help???

spinner()
    {
        local pid=$!
        local delay=0.75
        local spinstr='|/-\'
        while [ "$(ps a | awk '{print $1}' | grep $pid)" ]; do
            local temp=${spinstr#?}
            printf " [%c]  " "$spinstr"
            local spinstr=$temp${spinstr%"$temp"}
            sleep $delay
            printf "\b\b\b\b\b\b"
        done
    }

         sleep 5 & spinner | echo -e "\nCopyright of KatworX© Tech. Developed by Arjun Singh Kathait and Debugged by the ☆Stack Overflow Community☆"
ASK Arjun
  • 111
  • 1
  • 18
  • Have a look at [multiple colors on output of bash spinner](https://stackoverflow.com/questions/46966891/multiple-colors-on-output-of-bash-spinner). You can ignore the change in color. But it is horribly inefficient to call `ps`, `awk` and `grep` in a while loop. – David C. Rankin Nov 11 '17 at 06:15
  • Can you modify this code segment @DavidC.Rankin and post it in the comment box? – ASK Arjun Nov 11 '17 at 06:18

1 Answers1

3

Continuing from the comment. To avoid calling ps, awk and grep on every iteration, you need to pass the PID as an argument to the spin function. (and you can pass a string to display and default to your string as well). I would do something similar to:

#!/bin/bash

## spinner takes the pid of the process as the first argument and
#  string to display as second argument (default provided) and spins
#  until the process completes.
spinner() {
    local PROC="$1"
    local str="${2:-'Copyright of KatworX© Tech. Developed by Arjun Singh Kathait and Debugged by the ☆Stack Overflow Community☆'}"
    local delay="0.1"
    tput civis  # hide cursor
    printf "\033[1;34m"
    while [ -d /proc/$PROC ]; do
        printf '\033[s\033[u[ / ] %s\033[u' "$str"; sleep "$delay"
        printf '\033[s\033[u[ — ] %s\033[u' "$str"; sleep "$delay"
        printf '\033[s\033[u[ \ ] %s\033[u' "$str"; sleep "$delay"
        printf '\033[s\033[u[ | ] %s\033[u' "$str"; sleep "$delay"
    done
    printf '\033[s\033[u%*s\033[u\033[0m' $((${#str}+6)) " "  # return to normal
    tput cnorm  # restore cursor
    return 0
}

## simple example with sleep
sleep 5 &

spinner $!

(it displays in blue -- but you can delete the first printf to remove the color)

David C. Rankin
  • 81,885
  • 6
  • 58
  • 85
  • Thanks a lot @David. It is people like you who make this community a better place. I have dedicated my current project to Stack Overflow Community as it has helped a lot in debugging and such. – ASK Arjun Nov 11 '17 at 06:51
  • Sure, glad to help. You can even add a `local delay="${3:-0.1}"` and pass the delay as an option if you want to make that adjustable as well. Good luck with your scripting. – David C. Rankin Nov 11 '17 at 06:52
  • you would replace `while [ -d /proc/$PROC ]; do` with `while kill -0 ${PROC} 2>/dev/null; do` to make it cross platform – nbari Nov 11 '17 at 08:38
  • If it is not a Linux platform, then pay close attention to the `man kill` syntax. The `kill -0 ${PROC} 2>/dev/null` should work -- as long as the `-0` signal sends nothing but will report errors as it does here on Linux. Where do you have `kill` but not procfs? – David C. Rankin Nov 11 '17 at 08:46
  • @DavidC.Rankin normally in the "Unixes", FreeBSD has a nice `pwait` but in macOs, `kill -0 $pid` is doing the trick – nbari Nov 11 '17 at 08:53
  • The text disappears after the function is executed. Is there a way I can keep the text after the function is done executing. @DavidC.Rankin – ASK Arjun Nov 13 '17 at 22:00
  • Sure, just get rid of the final `printf`. That is set to erase the line. – David C. Rankin Nov 13 '17 at 23:13
  • @DavidC.Rankin Aaah....gotcha mate... Thanks to you I am getting to learn Bash more faster day by day. With your help I am able to get familiar with columns, color, disabling cursors and enabling them. You are a saint. :) – ASK Arjun Nov 14 '17 at 02:17
  • Yes, the ANSI escapes are rather obscure in what they do. It's one of those (you just got to memorize or keep a handy reference). There are many around, e.g. [ANSI Escapes](http://ascii-table.com/ansi-escape-sequences.php) Always keep in mind that ANSI escapes are terminal dependent and largely non-portable outside of Linux. (they are definitely not the "meat and potatoes" of scripting). I would bet: the further you get into scripting, the less you rely on ANSI escapes, until it is ultimately none at all `:)` Keep up the good work. – David C. Rankin Nov 14 '17 at 02:24
  • (don't get me wrong, they were really cool in the 80's and 90's when all you had was a 80x25 terminal to work with and you were using a curses interface for text windows, etc..., but they have really fallen out as the number of different terminal emulators may (or may not) support them and as character sets have changed to no longer include a bulk of the old line-drawing characters, etc..) – David C. Rankin Nov 14 '17 at 02:29