1.

Solve : Add Progress Spinner To Menu Batch File?

Answer»

Hello everyone!!! Im new to batch files and im wanting to incorporate a spinning progress to my menu of 9 choices. I can just call it but it runs the spinner then runs the ping. Im wanting to hide the ping and just show the spinner and display the packets failed or revived line. Any ideas? Thanks!

SPINNER:
Code: [Select]setlocal EnableDelayedExpansion
for /f %%a in ('copy /Z "%~dpf0" nul') do set "CR=%%a"

FOR /L %%n in (1,1,50) DO (
call :spinner
ping localhost -n 1 > nul
)
exit /b

:spinner
set /a "spinner=(spinner + 1) %% 4"
set "spinChars=\|/-"
<nul set /p ".=Waiting...!spinChars:~%spinner%,1!!CR!"
exit /b
My Menu:

Code: [Select]@echo OFF

:MENU

:: Clear the window
cls

::::::::::::::::::::::::::::::::::::::::::::::::::::::
:::::::::::::::CHOOSE COLOR START:::::::::::::::::::::
:: Color attributes are specified by TWO hex digets.::
:: 1) The first corresponds to the background ::
:: 2) The second corresponds to the foreground ::
:: ::
:: COLOR 0 = BLACK COLOR 8 = GRAY ::
:: COLOR 1 = BLUE COLOR 9 = LIGHT BLUE ::
:: COLOR 2 = GREEN COLOR A = LIGHT GREEN ::
:: COLOR 3 = AQUA COLOR B = LIGHT AQUA ::
:: COLOR 4 = RED COLOR C = LIGHT RED ::
:: COLOR 5 = PURPLE COLOR D = LIGHT PURPLE ::
:: COLOR 6 = YELLOW COLOR E = LIGHT YELLOW ::
:: COLOR 7 = WHITE COLOR F = BRIGHT WHITE ::
::::::::::::::::CHOOSE COLOR END::::::::::::::::::::::
::::::::::::::::::::::::::::::::::::::::::::::::::::::

COLOR 71

echo.
echo =============FOX IV MENU=============
echo -------------------------------------
echo. 1. Ping Router
echo. 2. Ping Line 1
echo. 3. Ping Line 2
echo. 4. Ping Line 3
echo. 5. Ping Line 4
echo. 6. Ping Line 5
echo. 7. Ping Line 6
echo. 8. Ping Maintenance FoxIV
echo. 9. Exit
echo -------------------------------------
echo.

SET /P choice=Please select a number from 1-9...
if '%Choice%'=='1' GOTO MAINROUTER
if '%Choice%'=='2' GOTO LN1
if '%Choice%'=='3' GOTO LN2
if '%Choice%'=='4' GOTO LN3
if '%Choice%'=='5' GOTO LN4
if '%Choice%'=='6' GOTO LN5
if '%Choice%'=='7' GOTO LN6
if '%Choice%'=='8' GOTO TESTIV
if '%Choice%'=='9' GOTO EOF

::::::::::::::::::::::::::::::::::::::::::::::::::::::
::::::::::::::::CHOICE INVALID START::::::::::::::::::
::(1) Clear the window ::
cls
::(2) Create a space from the top ::
echo.
::(3) Tell the user what invalid entry is ::
echo. You entered a %choice% which is an invalid entry, please try again!
::(4) Timeout for 3 seconds so they can read it ::
timeout /t 3 /nobreak > nul
::(5) Clear the window ::
cls
::(6) Go back to the MENU to start over ::
goto MENU
:::::::::::::::::CHOICE INVALID END:::::::::::::::::::
::::::::::::::::::::::::::::::::::::::::::::::::::::::


:MAINROUTER
cls
echo.
ping
echo.
GOTO END

:LN1
cls
echo.
ping
echo.
GOTO END


:LN2
cls
echo.
ping
echo.
GOTO END

:LN3
cls
echo.
ping
echo.
GOTO END

:LN4
cls
echo.
ping
echo.
GOTO END


:LN5
cls
echo.
ping
echo.
GOTO END

:LN6
cls
echo.
ping
echo.
GOTO END

:TESTIV
cls
echo.
ping
echo.
GOTO END

:END

cls
echo.
echo ==============EXIT MENU==============
echo -------------------------------------
echo. 1. Go Back To Main Menu
echo. 2. Exit
echo -------------------------------------
echo.

SET /P choice=Please select a number...
if '%Choice%'=='1' GOTO MENU
if '%Choice%'=='2' GOTO EOFyou could use
Code: [Select]ping | find "Packets: "

Code: [Select]C:\Users\Lemonilla>ping 127.0.0.1 | find "Packets: "
Packets: Sent = 4, Received = 4, Lost = 0 (0% loss),
How could I incorperate the "Spinner" into each GOTO for the menu so each item I GOTO shows the "Spinner" instead of the pinging of the IP address?If your spinner is saved in a different batch file, you could 'call Spinner.bat' or if it's within your file 'call :Spinner'. Not quite sure which GOTO statements you are talking about. I assume you want to replace the ping in one of these
Code: [Select]:LN1
cls
echo.
ping
echo.
GOTO END
with the whole of the spinner without writing it in every time. To do this you could either have
Code: [Select]:SpinnerEx
setlocal EnableDelayedExpansion
for /f %%a in ('copy /Z "%~dpf0" nul') do set "CR=%%a"

FOR /L %%n in (1,1,50) DO (
call :spinner
ping localhost -n 1 > nul
)
exit /b

:spinner
set /a "spinner=(spinner + 1) %% 4"
set "spinChars=\|/-"
<nul set /p ".=Waiting...!spinChars:~%spinner%,1!!CR!"
exit /b
and replace 'ping' with 'call :SpinnerEx'

or you can save spinner into a separate batch file (I'm going to name it SpinnerEx.bat)
and replace 'ping' with 'call SpinnerEx.bat.Yes the spinner is within my bat file. I wanted to have it show the (Waiting... /|\ ) while it was pinging the selection I made and when its done pinging then show the ping results.

Example:

If I selected 1 from the menu it would GOTO LN1

Code: [Select]:LN1
cls
echo.
ping XX.XX.XXX
echo.
GOTO END


Now I wanted it to not only for all GOTO's that I select that would ping have it show the (Waiting... /|\ ) while it was pinging the selection I made and when its done pinging then show the ping results.

How can I do this, Hope this helps my newbie explation isnt helping...

If I add the call spinner it shows the spinner then pings the IP and shows that too, I tried that...

Thanks!

Code: [Select]@echo off
:loop
cls
@echo. Process RUNNING ^/
ping 127.0.0.1 -n 1 >junk.txt
cls
@echo. Process Running ^_
ping 127.0.0.1 -n 1 >junk.txt
cls
@echo. Process Running ^\
ping 127.0.0.1 -n 1 >junk.txt
cls
@echo. Process Running ^|
ping 127.0.0.1 -n 1 >junk.txt
GOTO loop

I have redirected the output of batches to a junk text file before to hide what normally would cause screen scroll and then only display the cartwheel by echo and clear screen to get rid of screen scrolling. I haven't found a clean way yet to perform cartwheel in batch. And for my lengthy batch files where I want to know where it is at in the process I just use clear screen and then something like Process at 50% checkpoints displayed and then further on in the batch process at 75% and then at the end Process at 100%. If you have a very long batch process you can change the intervals to be any scale you want etc and simply just redirect the output to a junk text file to hide it from the user display.

The above batch I have is kind of pointless for a ping as for none of the results are displayed to the user, but you can simply remove the redirection >junk.txt from the line and it will show on the display.

Code: [Select]@echo off
:loop
cls
@echo. Process Running ^/
ping 127.0.0.1 -n 1 >junk.txt
cls
@echo. Process Running ^_
ping 127.0.0.1 -n 1 >junk.txt
cls
@echo. Process Running ^\
ping 127.0.0.1 -n 1 >junk.txt
cls
@echo. Process Running ^|
ping 127.0.0.1 -n 4
GOTO loop
This one shows 3 results and loops, but the pings that are redirected to junk.txt are actually acting more like time delays for the cartwheel effect.

BUT ... the cartwheel pauses while processes cause delay as seen in the second batch I posted removing a redirection and ADDING longer ping duration. So if you want a cartwheel to keep spinning while a lengthy process is running, I haven't found a way yet to do this with batch.Here are three progress bars / spinners (not written by me) that I had squirreled away.


Code: [Select] @Echo OFF
SetLocal EnableExtensions EnableDelayedExpansion

For /f %%a in ('copy /Z "%~dpf0" nul') Do set "CR=%%a"
Set "busy=|/-\"
Set /A n=0

::BUSY SPINNER
For /L %%i in (0,1,10) Do (
Set /A "n=%%i%%4"
For /L %%n in (!n! 1 !n!) Do Set /P "=Calculating !busy:~%%n,1! !CR!"<NUL:
PING -n 2 127.0.0.1 >NUL:
)
::COUNTDOWN
For /L %%i in (10,-1,1) Do (
Set /P "=Backup will begin in %%i seconds. !CR!"<NUL:
PING -n 2 127.0.0.1 >NUL:
)
::PROGRESS
For %%i in (*) Do (
Set /P "=Copying %%i !CR!"<NUL:
PING -n 2 127.0.0.1 >NUL:
)

pause

Code: [Select]: Tom Lavedas
@echo off
setlocal
set "write=<nul set/p"
%write%=Patience, please
for /l %%a in (1,1,25) do (
%write%=Ü
ping -n 2 127.0.0.1 > nul
)
echo. Thank you for waiting.


Code: [Select]:: BEGIN FILE ::::::::::::::::::::::::::::::::::::::::::::::::::::
:: ProgBar.cmd
:: Frank P. Westlake, 2009-07-23
:: Demonstrates a progress bar.
:: Set variable 'size' with the number of times a loop will
:: be accomplished.
@ECHO OFF
SETLOCAL ENABLEEXTENSIONS ENABLEDELAYEDEXPANSION
Set /A size=1234, progress=0, item=0, last=0
Echo.Processing %size% items . . .
:: Save current code page for restoration at completion.
For /F "tokens=2 delims=:" %%a in ('CHCP') Do Set "CP=%%a"
:: Using code page 437 for the character 'Û' in the progress bar.
CHCP 437 >NUL:
:: Progress bar caption.
Echo. 10 20 30 40 50 60 70 80 90 100%%
:: 7-bit ASCII progress indicator.
::Set "indicator=___"
:: 8-bit progress indicator (Û=DBh, the inverted space character).
::Set "indicator=ÛÛÛ"
Set "indicator=±±±"
:: A demonstration loop.
For /L %%i in (0 1 %size%) Do (
Set /A item+=1,progress=item*10/%size%
If !last! NEQ !progress! (
Set /P "=!indicator!"<NUL:
Set /A last=progress
)
Call :DoNothing
)
:: Terminate the progress bar.
Echo.%indicator:~0,2%
:: Say bye now.
Echo.Bye.
:: Restore the computer operator's code page.
CHCP %CP% >NUL:
:: Goto :EOF.
Goto :EOF


:DoNothing
::Not doing anything yet . . .
:: Goto :EOF again.
Goto :EOF
:: END OF FILE :::::::::::::::::::::::::::::::::::::::::::::::::::
Quote from: oxicottin on February 05, 2013, 07:51:36 PM

Now I wanted it to not only for all GOTO's that I select that would ping have it show the (Waiting... /|\ ) while it was pinging the selection I made and when its done pinging then show the ping results.
This is not possible, as far as I'm aware.Would be cool though.... Thanks everyone for the info!!! HI,

Quote from: BC_Programmer on February 06, 2013, 06:11:15 AM
This is not possible, as far as I'm aware.
It's possible, but it's tricky.
You need a second thread, so one thread do the work and the other displays the spinner.

A second thread can be startet via start or start /b for the same window.
But as I said, it's nothing a beginner should try.

jebI wrote a simple sample for an asynchronous spinner and a smarter GetKey function, so you don't need to press enter.

I suppose it should be obvious how it works.

Code: [Select]@echo off
setlocal EnableDelayedExpansion
if "%~1"==":::" goto :spinnerThread

:menuLoop
<nul set /p menu=Select menu[1 or 2]=
call :GetKey
echo(
echo Pressed '!key!'
if !key!==1 call :menu1
if !key!==2 call :menu2
if !key!==2 call :menu2
goto :menuLoop

:menu1
:menu2
call :spinnerStart
rem do some work
ping localhost -n 3 > nl
call :spinnerStop
echo Finished
exit /b

:spinnerStart
del spinnerStop.tmp > nul 2>&1
start /b "" cmd /c "%~df0" :::
exit /b

:spinnerStop
echo dummy > spinnerStop.tmp
:__spinnerStop
if exist spinnerStop.tmp goto :__spinnerStop
exit /b

:spinnerThread
for /f %%a in ('copy /Z "%~f0" nul') do set "CR=%%a"
set "spinChars=\|/-"

:spinnerLoop
set /a "spinner=(spinner + 1) %% 4"
<nul set /p ".=Waiting...!spinChars:~%spinner%,1!!CR!"
ping localhost -n 2 > nul 2>&1
if not exist spinnerStop.tmp goto :spinnerLoop
del spinnerStop.tmp > nul 2>&1
echo(
exit /b

:GetKey
set "key="
for /F "usebackq delims=" %%L in (`xcopy /L /w "%~f0" "%~f0" 2^>NUL`) do (
if not defined key set "key=%%L"
)
set "key=%key:~-1%"
exit /b

jebIndeed, it would appear my previous comment was premature:
"testslashes.bat":
Code: [Select]@echo off
start /b slasher.bat
ping www.google.ca -n 8 > redirected.txt 2>&1
echo "test">stopslash.dat
echo "finished."
:waitdel
if exist stopslash.dat goto waitdel
cls
echo Finished!
type redirected.txt
slasher.bat:
Code: [Select]@echo off
if exist stopslash.dat del stopslash.dat
:start

for %%P in (^| \ - /) do cls&echo %%P&ping localhost -n 2
if exist stopslash.dat del stopslash.dat&goto endfile
goto start
:endfile


testslashes is the "main" one. What it does is spawns off the "slasher" batch using start /b, then it uses a ping and redirects it to a file. While it is doing this, the slasher batch is writing the spinning cursor. When it detects stopslash.dat exists, it deletes it and exits. When the ping completes in the main batch, it writes out the stopslash.dat file, then waits for it to be deleted. and clears the screen and displays the results, which were redirected to a file. The 'slasher' batch just has the logic to keep looping until the sentinel file exists, at which point it deletes the file and exits. It also deletes it when it is entered to try to prevent issues.

Wow thanks guys I REALLY appreciate it!!


Discussion

No Comment Found