Is there a way to update progress bar in Windows Vista to 10?

Discussion forum for all Windows batch related topics.

Moderator: DosItHelp

Post Reply
Message
Author
WiVi71
Posts: 19
Joined: 06 Jan 2020 02:33

Is there a way to update progress bar in Windows Vista to 10?

#1 Post by WiVi71 » 07 Jan 2020 10:15

I am making a simple code to download Wget with BITSADMIN contains a progress bar.
This is a part of my code :

Code: Select all

@ECHO OFF
:: This is a part of my batch
SET "WGET_URL=https://eternallybored.org/misc/wget/1.20.3/64/wget.exe"
SET "WGET_PATH=%USERPROFILE%"

:Prepare
REM * Prepare - Set Window
COLOR 07
TITLE GMK: Downloading Wget
MODE CON COLS=84 LINES=25

REM * Prepare - Logo
ECHO                            / \                   / \       / \
ECHO           / \ /\       /     \    / \       /     ^>/ \/    // \
ECHO         /    /  /  / \/    / \/  /     ^>    /     //    /\ //    // \
ECHO       /    /  /  /   //   /   // /     /    /     //    /    /    //   //\
ECHO       \ /  /  /   //   /   // /     //\ /     //    // \/    //   //    ^>
ECHO        /  /  /   //   /   // /     //  / ^<    //    //    /\ //   //     / /\
ECHO       \/  /   //   /   // / / \//  /  / \/  \ //    /  /   \//     / /  /
ECHO            \ /\ /   //  ^</   //  /  /  ^|\\   /    /  /  / \/     / /  /
ECHO                 /\ //   / \//\/   \  ^|/  /   \ /\/    \^</    /  \/
ECHO                 \ /     \ /          \  /                   \ /
ECHO                                          ˇ           
ECHO                                   --  Some Text --
ECHO:
ECHO -----------------------------------------------------------------------------------
ECHO:

REM * Download - Wget: Prepare Download
:: Need to use call in addfile(why?)
BITSADMIN.EXE /CANCEL Wget_download > NUL
BITSADMIN.EXE /CREATE /DOWNLOAD Wget_download > NUL
CALL BITSADMIN.EXE /ADDFILE Wget_download "%WGET_URL%" "%WGET_PATH%\wget.exe" > NUL
BITSADMIN.EXE /SETPRIORITY Wget_download HIGH > NUL
BITSADMIN.EXE /SETPROXYSETTINGS Wget_download AUTODETECT > NUL

REM * Download - Wget: Get Basic Information
:: Proxy option has never tested
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCREATIONTIME Wget_download') DO SET "BITS_CREATIONTIME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETDISPLAYNAME Wget_download') DO SET "BITS_JOBNAME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPRIORITY Wget_download') DO SET "BITS_PRIORITY=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYUSAGE Wget_download') DO SET "BITS_PROXYUSAGE=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYLIST Wget_download') DO SET "BITS_PROXYLIST=%%A"

REM * Download - Wget: Show Basic Information
ECHO This download process is using BITSADMIN ^(BITS administration utility^)
ECHO:
ECHO %BITS_CREATIONTIME% - Started Job : %BITS_JOBNAME% [Priority : %BITS_PRIORITY%]
ECHO Current proxy usage setting is "%BITS_PROXYUSAGE%" [Proxy List : %BITS_PROXYLIST%]
ECHO:
ECHO Downloading %WGET_URL%

REM * Download - Wget: Start Download
BITSADMIN.EXE /RESUME Wget_download > NUL

:BITSADMIN_State_Loop
REM * Download - Wget: Update State
:: https://docs.microsoft.com/en-us/windows-server/administration/windows-commands/bitsadmin-getstate
:: There is an overflowing problem(18446744073709551615 problem)
:: Need to loop fast
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETSTATE Wget_download') DO (
	ECHO Awaiting TRANSFERRING State..  [ Current State : %%A ]
	REM :: IF "%%A" == "ERROR" GOTO BITSADMIN_Download_Error
	REM :: IF "%%A" == "TRANSIENT_ERROR" GOTO BITSADMIN_Download_Error
	REM :: IF "%%A" == "SUSPENDED" GOTO BITSADMIN_State_Else
	REM :: IF "%%A" == "CANCELED" GOTO BITSADMIN_State_Else
	IF "%%A" == "TRANSFERRING" ECHO: & GOTO BITSADMIN_Download_Loop
	IF "%%A" == "ACKNOWLEDGED" GOTO BITSADMIN_Download_Success
	IF "%%A" == "TRANSFERRED" GOTO BITSADMIN_Download_Succes
)

TIMEOUT 1 > NUL
GOTO BITSADMIN_State_Loop

:BITSADMIN_Download_Loop
:: Need to loop fast
REM * Download - Wget: Update Bytes
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTOTAL Wget_download') DO SET "BITS_TOTALBYTES=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTRANSFERRED Wget_download') DO SET "BITS_TRANSFERREDBYTES=%%A"

REM * Download - Wget: Get percent
SET /A "BITS_PERCENT=(BITS_TRANSFERREDBYTES*100)/BITS_TOTALBYTES"

REM * Download - Wget: Convert bytes to Kibibytes
SET /A "BITS_TOTALKIB=BITS_TOTALBYTES/1024"
SET /A "BITS_TRANSFERREDKIB=BITS_TRANSFERREDBYTES/1024"

REM * Download - Wget: Get Progress bar
:: CALL SET is slow than SET
:: Do not use variable starts with "A"
SET "BITS_HASHS="
SET "BITS_UNDERLINES="
SET /A "BITS_HASHNUM=BITS_PERCENT/3"
FOR /L %%A IN (1,1,%BITS_HASHNUM%) DO CALL SET "BITS_HASHS=%%BITS_HASHS%%#"
SET /A "BITS_UNDERLINENUM=33-BITS_HASHNUM"
FOR /L %%A IN (1,1,%BITS_UNDERLINENUM%) DO CALL SET "BITS_UNDERLINES=%%BITS_UNDERLINES%%_"

REM * Download - Wget: Update Progress bar
:: Need to add state checking
ECHO wget.exe       [%BITS_HASHS%%BITS_UNDERLINES%]  %BITS_PERCENT%%% ^| %BITS_TRANSFERREDKIB%KiB/%BITS_TOTALKIB%KiB
IF "%BITS_PERCENT%" == "100" GOTO BITSADMIN_Download_Success
TIMEOUT 1 > NUL
GOTO BITSADMIN_Download_Loop

:BITSADMIN_Download_Success
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCOMPLETIONTIME Wget_download') DO SET "BITS_COMPLETIONTIME=%%A"
BITSADMIN.EXE /COMPLETE Wget_download > NUL
IF %ERRORLEVEL% NEQ 0 REM :: GOTO BITSADMIN_Download_Error
ECHO:
ECHO %BITS_CREATIONTIME% - Job %BITS_JOBNAME% Completed
ECHO Saved file to "%WGET_PATH%\wget.exe"
EXPLORER.EXE %WGET_PATH%
pause
img.png
img.png (18.4 KiB) Viewed 6994 times
And I have some questions to improve this batch file.

| 1. I need a code to overwrite the progress bar line; that supports Windows Vista to the Current version.
I searched about this topic and I found awesome codes about this problem. But I couldn't find what I wanted..

viewtopic.php?t=7898
The "Move cursor to *any position* using just ECHO command" didn't work at Windows 10;(Without editing registry)

viewtopic.php?p=43716#p43716
The "timeout 1 > con" worked in every Windows version, but I didn't find the way how to find "where is the line current is"
So It was possible to overwrite another line like this image.
123.png
123.png (2.37 KiB) Viewed 6983 times
https://stackoverflow.com/a/44138141

Code: Select all

@echo off
setlocal EnableDelayedExpansion
MODE CON COLS=84 LINES=25
rem Get a BS and TAB control characters
for /F %%a in ('echo prompt $H ^| cmd') do set "BS=%%a"
REM Be sure that TAB variable contains an Ascii 9 character
::https://www.dostips.com/forum/viewtopic.php?t=7898
for /F "skip=4 delims=pR tokens=2" %%a in ('reg query hkcu\environment /v temp' ) do set "TAB=%%a"
rem Then, the method for newer versions
rem http://www.dostips.com/forum/viewtopic.php?f=3&t=1733&p=6840#p6853
for /F "tokens=2 delims=0" %%a in ('shutdown /? ^| findstr /BC:E') do if not defined TAB set "TAB=%%a"

rem Leave some empty lines and do a PAUSE
echo Three empty lines below + pause
echo/
echo/
echo/
pause

rem Get width of screen buffer, set number of lines to go above
set /A buffWid=84, linesAbove=3

rem Assemble the "go above" control string with the proper number of BSs
set "BSs="
set /A "cntBS = 2 + (buffWid + 7) / 8 * linesAbove"
for /L %%i in (1,1,%cntBS%) do set "BSs=!BSs!!BS!"

rem Move cursor up the desired number of lines
echo %TAB%!BSs!

echo Hello,
echo World
echo This line overwrites the one with PAUSE output
pause
This one didn't work at Windows 10

viewtopic.php?p=54400#p54400
viewtopic.php?p=54392#p54392
I don't want to use external tools.(like cscript/wscript/powershell; some computers block these.)
hybrid batch is ok(only for .net) but hybrid batch is already using to choose files(with js.net) but there is no way to use multiple hybrid .net batch..

https://superuser.com/a/1166728
And <nul set /p " didn't work at Windows 10.

Is there another way to update progress bar that works on Windows vista to 10?

| 2. What is the difference between bitsadmin and bitsadmin.exe?

Code: Select all

:: Save this code to .bat/.cmd to see this bug.
bitsadmin.exe /cancel wget_download > nul
pause > nul
bitsadmin /cancel wget_download > nul
pause > nul
The First command works but second does not.
Here is a screenshot of output.
imp2.png
imp2.png (47.72 KiB) Viewed 6672 times
| 3. What does 'call' does?

Code: Select all

CALL BITSADMIN.EXE /ADDFILE Wget_download "%WGET_URL%" "%WGET_PATH%\wget.exe" > NUL
In Here the batch use "call bitsadmin"
What does "call" does to bitsadmin at that batch?

Code: Select all

FOR /L %%A IN (1,1,%BITS_HASHNUM%) DO CALL SET "BITS_HASHS=%%BITS_HASHS%%#"
SET /A "BITS_UNDERLINENUM=33-BITS_HASHNUM"
FOR /L %%A IN (1,1,%BITS_UNDERLINENUM%) DO CALL SET "BITS_UNDERLINES=%%BITS_UNDERLINES%%_"
Isn't "call set" slow? If "call set" is slow, Is there another way to set multiple blocks?
Last edited by WiVi71 on 28 Jan 2020 02:32, edited 2 times in total.

jfl
Posts: 226
Joined: 26 Oct 2012 06:40
Location: Saint Hilaire du Touvet, France
Contact:

Re: Is there a way to update progress bar in Windows Vista to 10?

#2 Post by jfl » 10 Jan 2020 09:26

2. What is the difference between bitsadmin and bitsadmin.exe?
If you don't provide the extension, cmd.exe will try all the extensions in enviroment variable PATHEXT, and use the first program that matches.
Could it be that you named your test script "bitsadmin.bat" ?
In that case, this explains why you have an infinite loop: Contrary to other types of programs, invoking batch files likes this JUMPS into the other batch, and never comes back.
What does 'call' does?
Its primary role is to call an external batch file (overcoming the issue I mentioned above), or call an internal subroutine.
There's also a side role, which is to parse an instruction twice. It's only needed in loops, when a VARIABLE changes within the loop. All %VARIABLE% references are expanded before the loop starts, so you don't see the changes. To get the updated value, you need to use !VARIABLE! expansion, or use the 'call ... %%VARIABLE%% ...' syntax. (Notice the double % signs: The initial % expansion before the loops starts changes each %% to a %, then the second parsing done by call expands the remaining %VARIABLE% to its updated value.)

pieh-ejdsch
Posts: 239
Joined: 04 Mar 2014 11:14
Location: germany

Re: Is there a way to update progress bar in Windows Vista to 10?

#3 Post by pieh-ejdsch » 17 Jan 2020 17:49

You can change the prompt so that the display can be used as output.

viewtopic.php?f=3&t=8051

Code: Select all

@ECHO OFF

if :%1 == :print shift &goto :print
for /f %%a in ('copy /Z "%~dpf0" nul') do set "CR=%%a"

:: This is a part of my batch
SET "WGET_URL=https://eternallybored.org/misc/wget/1.20.3/64/wget.exe"
SET "WGET_PATH=%USERPROFILE%"
:Prepare
REM * Prepare - Set Window
COLOR 07
TITLE GMK: Downloading Wget
:MODE CON COLS=84 LINES=25

REM * Prepare - Logo
ECHO                            / \                   / \       / \
ECHO           / \ /\       /     \    / \       /     ^>/ \/    // \
ECHO         /    /  /  / \/    / \/  /     ^>    /     //    /\ //    // \
ECHO       /    /  /  /   //   /   // /     /    /     //    /    /    //   //\
ECHO       \ /  /  /   //   /   // /     //\ /     //    // \/    //   //    ^>
ECHO        /  /  /   //   /   // /     //  / ^<    //    //    /\ //   //     / /\
ECHO       \/  /   //   /   // / / \//  /  / \/  \ //    /  /   \//     / /  /
ECHO            \ /\ /   //  ^</   //  /  /  ^|\\   /    /  /  / \/     / /  /
ECHO                 /\ //   / \//\/   \  ^|/  /   \ /\/    \^</    /  \/
ECHO                 \ /     \ /          \  /                   \ /
ECHO                                          ?           
ECHO                                   --  Some Text --
ECHO:
ECHO -----------------------------------------------------------------------------------
ECHO:

REM * Download - Wget: Prepare Download
:: Need to use call in addfile(why?)
BITSADMIN.EXE /CANCEL Wget_download > NUL
BITSADMIN.EXE /CREATE /DOWNLOAD Wget_download > NUL
CALL BITSADMIN.EXE /ADDFILE Wget_download "%WGET_URL%" "%WGET_PATH%\wget.exe" > NUL
BITSADMIN.EXE /SETPRIORITY Wget_download HIGH > NUL
BITSADMIN.EXE /SETPROXYSETTINGS Wget_download AUTODETECT > NUL

REM * Download - Wget: Get Basic Information
:: Proxy option has never tested
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCREATIONTIME Wget_download') DO SET "BITS_CREATIONTIME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETDISPLAYNAME Wget_download') DO SET "BITS_JOBNAME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPRIORITY Wget_download') DO SET "BITS_PRIORITY=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYUSAGE Wget_download') DO SET "BITS_PROXYUSAGE=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYLIST Wget_download') DO SET "BITS_PROXYLIST=%%A"

REM * Download - Wget: Show Basic Information
ECHO This download process is using BITSADMIN ^(BITS administration utility^)
ECHO:
ECHO %BITS_CREATIONTIME% - Started Job : %BITS_JOBNAME% [Priority : %BITS_PRIORITY%]
ECHO Current proxy usage setting is "%BITS_PROXYUSAGE%" [Proxy List : %BITS_PROXYLIST%]
ECHO:
ECHO Downloading %WGET_URL%

REM * Download - Wget: Start Download
BITSADMIN.EXE /RESUME Wget_download > NUL

:BITSADMIN_State_Loop
REM * Download - Wget: Update State
:: https://docs.microsoft.com/en-us/windows-server/administration/windows-commands/bitsadmin-getstate
:: There is an overflowing problem(18446744073709551615 problem)
:: Need to loop fast
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETSTATE Wget_download') DO (
	cmd /c if . equ . "%~f0" print "!CR!  Awaiting TRANSFERRING State..  [ Current State : %%A ]"
	REM :: IF "%%A" == "ERROR" GOTO BITSADMIN_Download_Error
	 rem GOTO BITSADMIN_Download_%%A
	REM :: IF "%%A" == "TRANSIENT_ERROR" GOTO BITSADMIN_Download_Error
	REM :: IF "%%A" == "SUSPENDED" GOTO BITSADMIN_State_Else
	REM :: IF "%%A" == "CANCELED" GOTO BITSADMIN_State_Else
	IF "%%A" == "TRANSFERRING" ECHO: & GOTO BITSADMIN_Download_Loop
	IF "%%A" == "ACKNOWLEDGED" GOTO BITSADMIN_Download_Success
	IF "%%A" == "TRANSFERRED" GOTO BITSADMIN_Download_Succes
)

:TIMEOUT 1 > NUL
GOTO BITSADMIN_State_Loop

:BITSADMIN_Download_TRANSFERRING
:BITSADMIN_Download_Loop
:: Need to loop fast
REM * Download - Wget: Update Bytes
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTOTAL Wget_download') DO SET "BITS_TOTALBYTES=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTRANSFERRED Wget_download') DO SET "BITS_TRANSFERREDBYTES=%%A"

REM * Download - Wget: Get percent
SET /A "BITS_PERCENT=(BITS_TRANSFERREDBYTES*100)/BITS_TOTALBYTES"

REM * Download - Wget: Convert bytes to Kibibytes
SET /A "BITS_TOTALKIB=BITS_TOTALBYTES/1024"
SET /A "BITS_TRANSFERREDKIB=BITS_TRANSFERREDBYTES/1024"

REM * Download - Wget: Get Progress bar
:: CALL SET is slow than SET
:: Do not use variable starts with "A"
SET "BITS_HASHS="
SET "BITS_UNDERLINES="
SET /A "BITS_HASHNUM=BITS_PERCENT/3"
FOR /L %%A IN (1,1,%BITS_HASHNUM%) DO CALL SET "BITS_HASHS=%%BITS_HASHS%%#"
SET /A "BITS_UNDERLINENUM=33-BITS_HASHNUM"
FOR /L %%A IN (1,1,%BITS_UNDERLINENUM%) DO CALL SET "BITS_UNDERLINES=%%BITS_UNDERLINES%%_"

REM * Download - Wget: Update Progress bar
:: Need to add state checking
cmd /c if . equ . "%~f0" print " !CR!  wget.exe       [%BITS_HASHS%%BITS_UNDERLINES%]  %BITS_PERCENT%%% ^| %BITS_TRANSFERREDKIB%KiB/%BITS_TOTALKIB%KiB"

 rem ECHO 
IF "%BITS_PERCENT%" == "100" GOTO BITSADMIN_Download_Success
TIMEOUT 1 > NUL
GOTO BITSADMIN_Download_Loop

:BITSADMIN_Download_Success
:BITSADMIN_Download_ACKNOWLEDGED
:BITSADMIN_Download_TRANSFERRED
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCOMPLETIONTIME Wget_download') DO SET "BITS_COMPLETIONTIME=%%A"
BITSADMIN.EXE /COMPLETE Wget_download > NUL
IF %ERRORLEVEL% NEQ 0 REM :: GOTO BITSADMIN_Download_Error
ECHO:
ECHO %BITS_CREATIONTIME% - Job %BITS_JOBNAME% Completed
ECHO Saved file to "%WGET_PATH%\wget.exe"
EXPLORER.EXE %WGET_PATH%
pause
exit /b

:BITSADMIN_Download_Error
:BITSADMIN_Download_TRANSIENT_ERROR
echo BITSADMIN_Download_Error

exit /b 1

:print
 rem Please note that this function/batch can NOT be started with a call.
 rem  Since it terminates the calling batch.
 rem  Usage: cmd /c if. equ . "Path\batchname" "whiteSpaces ...message Text"
@echo on
@( setlocal enabledelayedexpansion
set "prompt=%~1"
)
%== !required this is an empty Line, do not remove! ==%
@( echo off
Phil

WiVi71
Posts: 19
Joined: 06 Jan 2020 02:33

Re: Is there a way to update progress bar in Windows Vista to 10?

#4 Post by WiVi71 » 28 Jan 2020 00:48

pieh-ejdsch wrote:
17 Jan 2020 17:49
You can change the prompt so that the display can be used as output.

viewtopic.php?f=3&t=8051

Code: Select all

@ECHO OFF

if :%1 == :print shift &goto :print
for /f %%a in ('copy /Z "%~dpf0" nul') do set "CR=%%a"

:: This is a part of my batch
SET "WGET_URL=https://eternallybored.org/misc/wget/1.20.3/64/wget.exe"
SET "WGET_PATH=%USERPROFILE%"
:Prepare
REM * Prepare - Set Window
COLOR 07
TITLE GMK: Downloading Wget
:MODE CON COLS=84 LINES=25

REM * Prepare - Logo
ECHO                            / \                   / \       / \
ECHO           / \ /\       /     \    / \       /     ^>/ \/    // \
ECHO         /    /  /  / \/    / \/  /     ^>    /     //    /\ //    // \
ECHO       /    /  /  /   //   /   // /     /    /     //    /    /    //   //\
ECHO       \ /  /  /   //   /   // /     //\ /     //    // \/    //   //    ^>
ECHO        /  /  /   //   /   // /     //  / ^<    //    //    /\ //   //     / /\
ECHO       \/  /   //   /   // / / \//  /  / \/  \ //    /  /   \//     / /  /
ECHO            \ /\ /   //  ^</   //  /  /  ^|\\   /    /  /  / \/     / /  /
ECHO                 /\ //   / \//\/   \  ^|/  /   \ /\/    \^</    /  \/
ECHO                 \ /     \ /          \  /                   \ /
ECHO                                          ?           
ECHO                                   --  Some Text --
ECHO:
ECHO -----------------------------------------------------------------------------------
ECHO:

REM * Download - Wget: Prepare Download
:: Need to use call in addfile(why?)
BITSADMIN.EXE /CANCEL Wget_download > NUL
BITSADMIN.EXE /CREATE /DOWNLOAD Wget_download > NUL
CALL BITSADMIN.EXE /ADDFILE Wget_download "%WGET_URL%" "%WGET_PATH%\wget.exe" > NUL
BITSADMIN.EXE /SETPRIORITY Wget_download HIGH > NUL
BITSADMIN.EXE /SETPROXYSETTINGS Wget_download AUTODETECT > NUL

REM * Download - Wget: Get Basic Information
:: Proxy option has never tested
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCREATIONTIME Wget_download') DO SET "BITS_CREATIONTIME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETDISPLAYNAME Wget_download') DO SET "BITS_JOBNAME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPRIORITY Wget_download') DO SET "BITS_PRIORITY=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYUSAGE Wget_download') DO SET "BITS_PROXYUSAGE=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYLIST Wget_download') DO SET "BITS_PROXYLIST=%%A"

REM * Download - Wget: Show Basic Information
ECHO This download process is using BITSADMIN ^(BITS administration utility^)
ECHO:
ECHO %BITS_CREATIONTIME% - Started Job : %BITS_JOBNAME% [Priority : %BITS_PRIORITY%]
ECHO Current proxy usage setting is "%BITS_PROXYUSAGE%" [Proxy List : %BITS_PROXYLIST%]
ECHO:
ECHO Downloading %WGET_URL%

REM * Download - Wget: Start Download
BITSADMIN.EXE /RESUME Wget_download > NUL

:BITSADMIN_State_Loop
REM * Download - Wget: Update State
:: https://docs.microsoft.com/en-us/windows-server/administration/windows-commands/bitsadmin-getstate
:: There is an overflowing problem(18446744073709551615 problem)
:: Need to loop fast
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETSTATE Wget_download') DO (
	cmd /c if . equ . "%~f0" print "!CR!  Awaiting TRANSFERRING State..  [ Current State : %%A ]"
	REM :: IF "%%A" == "ERROR" GOTO BITSADMIN_Download_Error
	 rem GOTO BITSADMIN_Download_%%A
	REM :: IF "%%A" == "TRANSIENT_ERROR" GOTO BITSADMIN_Download_Error
	REM :: IF "%%A" == "SUSPENDED" GOTO BITSADMIN_State_Else
	REM :: IF "%%A" == "CANCELED" GOTO BITSADMIN_State_Else
	IF "%%A" == "TRANSFERRING" ECHO: & GOTO BITSADMIN_Download_Loop
	IF "%%A" == "ACKNOWLEDGED" GOTO BITSADMIN_Download_Success
	IF "%%A" == "TRANSFERRED" GOTO BITSADMIN_Download_Succes
)

:TIMEOUT 1 > NUL
GOTO BITSADMIN_State_Loop

:BITSADMIN_Download_TRANSFERRING
:BITSADMIN_Download_Loop
:: Need to loop fast
REM * Download - Wget: Update Bytes
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTOTAL Wget_download') DO SET "BITS_TOTALBYTES=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTRANSFERRED Wget_download') DO SET "BITS_TRANSFERREDBYTES=%%A"

REM * Download - Wget: Get percent
SET /A "BITS_PERCENT=(BITS_TRANSFERREDBYTES*100)/BITS_TOTALBYTES"

REM * Download - Wget: Convert bytes to Kibibytes
SET /A "BITS_TOTALKIB=BITS_TOTALBYTES/1024"
SET /A "BITS_TRANSFERREDKIB=BITS_TRANSFERREDBYTES/1024"

REM * Download - Wget: Get Progress bar
:: CALL SET is slow than SET
:: Do not use variable starts with "A"
SET "BITS_HASHS="
SET "BITS_UNDERLINES="
SET /A "BITS_HASHNUM=BITS_PERCENT/3"
FOR /L %%A IN (1,1,%BITS_HASHNUM%) DO CALL SET "BITS_HASHS=%%BITS_HASHS%%#"
SET /A "BITS_UNDERLINENUM=33-BITS_HASHNUM"
FOR /L %%A IN (1,1,%BITS_UNDERLINENUM%) DO CALL SET "BITS_UNDERLINES=%%BITS_UNDERLINES%%_"

REM * Download - Wget: Update Progress bar
:: Need to add state checking
cmd /c if . equ . "%~f0" print " !CR!  wget.exe       [%BITS_HASHS%%BITS_UNDERLINES%]  %BITS_PERCENT%%% ^| %BITS_TRANSFERREDKIB%KiB/%BITS_TOTALKIB%KiB"

 rem ECHO 
IF "%BITS_PERCENT%" == "100" GOTO BITSADMIN_Download_Success
TIMEOUT 1 > NUL
GOTO BITSADMIN_Download_Loop

:BITSADMIN_Download_Success
:BITSADMIN_Download_ACKNOWLEDGED
:BITSADMIN_Download_TRANSFERRED
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCOMPLETIONTIME Wget_download') DO SET "BITS_COMPLETIONTIME=%%A"
BITSADMIN.EXE /COMPLETE Wget_download > NUL
IF %ERRORLEVEL% NEQ 0 REM :: GOTO BITSADMIN_Download_Error
ECHO:
ECHO %BITS_CREATIONTIME% - Job %BITS_JOBNAME% Completed
ECHO Saved file to "%WGET_PATH%\wget.exe"
EXPLORER.EXE %WGET_PATH%
pause
exit /b

:BITSADMIN_Download_Error
:BITSADMIN_Download_TRANSIENT_ERROR
echo BITSADMIN_Download_Error

exit /b 1

:print
 rem Please note that this function/batch can NOT be started with a call.
 rem  Since it terminates the calling batch.
 rem  Usage: cmd /c if. equ . "Path\batchname" "whiteSpaces ...message Text"
@echo on
@( setlocal enabledelayedexpansion
set "prompt=%~1"
)
%== !required this is an empty Line, do not remove! ==%
@( echo off
Phil
Thank you Phil! This is what I really wanted!

And I can't understand the details of this code :?:
It seems that this is using "If . equ ." to open the batch file as a "cmd /c" command, and sets prompt to show the output.
But I wonder why newline does not happen after command.

Can someone please explain how does this works?
Last edited by WiVi71 on 28 Jan 2020 02:43, edited 2 times in total.

WiVi71
Posts: 19
Joined: 06 Jan 2020 02:33

Re: Is there a way to update progress bar in Windows Vista to 10?

#5 Post by WiVi71 » 28 Jan 2020 01:16

jfl wrote:
10 Jan 2020 09:26
2. What is the difference between bitsadmin and bitsadmin.exe?
If you don't provide the extension, cmd.exe will try all the extensions in enviroment variable PATHEXT, and use the first program that matches.
Could it be that you named your test script "bitsadmin.bat" ?
In that case, this explains why you have an infinite loop: Contrary to other types of programs, invoking batch files likes this JUMPS into the other batch, and never comes back.
What does 'call' does?
Its primary role is to call an external batch file (overcoming the issue I mentioned above), or call an internal subroutine.
There's also a side role, which is to parse an instruction twice. It's only needed in loops, when a VARIABLE changes within the loop. All %VARIABLE% references are expanded before the loop starts, so you don't see the changes. To get the updated value, you need to use !VARIABLE! expansion, or use the 'call ... %%VARIABLE%% ...' syntax. (Notice the double % signs: The initial % expansion before the loops starts changes each %% to a %, then the second parsing done by call expands the remaining %VARIABLE% to its updated value.)
Thanks for detail explanation jfl!

WiVi71
Posts: 19
Joined: 06 Jan 2020 02:33

Re: Is there a way to update progress bar in Windows Vista to 10?

#6 Post by WiVi71 » 28 Jan 2020 01:16

Code: Select all

@ECHO OFF
IF /I "%1" == "PRINT" SHIFT & GOTO PRINT
FOR /F %%A IN ('COPY /Z "%~DPF0" NUL') DO SET "CR=%%A"

SET "BITS_URL=https://raw.githubusercontent.com/EIGHTFINITE-Vendor/wget/wget-1.19.2-win64/wget.exe"
SET "BITS_PATH=%USERPROFILE%"

:Prepare
REM * Prepare - Set Window
COLOR 07
TITLE BITSADMIN: Downloading Wget
MODE CON COLS=84 LINES=25

REM * Prepare - Logo
ECHO                            / \                   / \       / \
ECHO           / \ /\       /     \    / \       /     ^>/ \/    // \
ECHO         /    /  /  / \/    / \/  /     ^>    /     //    /\ //    // \
ECHO       /    /  /  /   //   /   // /     /    /     //    /    /    //   //\
ECHO       \ /  /  /   //   /   // /     //\ /     //    // \/    //   //    ^>
ECHO        /  /  /   //   /   // /     //  / ^<    //    //    /\ //   //     / /\
ECHO       \/  /   //   /   // / / \//  /  / \/  \ //    /  /   \//     / /  /
ECHO            \ /\ /   //  ^</   //  /  /  ^|\\   /    /  /  / \/     / /  /
ECHO                 /\ //   / \//\/   \  ^|/  /   \ /\/    \^</    /  \/
ECHO                 \ /     \ /          \  /                   \ /
ECHO                                          ˇ
ECHO:
ECHO                                 = Downloading Wget =
ECHO:
ECHO -----------------------------------------------------------------------------------
ECHO:

REM * Download - BITSADMIN: Setting Job
BITSADMIN.EXE /CANCEL Wget_download > NUL
BITSADMIN.EXE /CREATE /DOWNLOAD Wget_download > NUL
CALL BITSADMIN.EXE /ADDFILE Wget_download "%BITS_URL%" "%BITS_PATH%\wget.exe" > NUL
BITSADMIN.EXE /SETPRIORITY Wget_download HIGH > NUL
BITSADMIN.EXE /SETPROXYSETTINGS Wget_download AUTODETECT > NUL
BITSADMIN.EXE /SETNOPROGRESSTIMEOUT Wget_download 30 > NUL

REM * Download - BITSADMIN: Get Information of Job
:: Proxy option has never tested
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCREATIONTIME Wget_download') DO SET "BITS_CREATIONTIME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETDISPLAYNAME Wget_download') DO SET "BITS_JOBNAME=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPRIORITY Wget_download') DO SET "BITS_PRIORITY=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYUSAGE Wget_download') DO SET "BITS_PROXYUSAGE=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETPROXYLIST Wget_download') DO SET "BITS_PROXYLIST=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETNOPROGRESSTIMEOUT Wget_download') DO SET "BITS_TIMEOUT=%%A"

REM * Download - BITSADMIN: Get BITSADMIN version
BITSADMIN.EXE /RAWRETURN /UTIL /VERSION >NUL 2>&1
IF %ERRORLEVEL% NEQ 0 (
	SET "BITS_VERSION=1.5 and earlier"
) ELSE (
	FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /UTIL /VERSION') DO SET "BITS_VERSION=%%A"
)

REM * Download - BITSADMIN: Show Basic Information
ECHO This download process is using BITSADMIN version %BITS_VERSION%
ECHO:
ECHO %BITS_CREATIONTIME% - Started Job : %BITS_JOBNAME% [Priority : %BITS_PRIORITY%]
ECHO Current proxy usage setting is "%BITS_PROXYUSAGE%" [Proxy List : %BITS_PROXYLIST%]
ECHO:
ECHO Downloading %BITS_URL%

REM * Download - BITSADMIN: Start Download
BITSADMIN.EXE /RESUME Wget_download > NUL

:BITSADMIN_State_Loop
REM * Download - BITSADMIN: Update State
:: https://docs.microsoft.com/en-us/windows-server/administration/windows-commands/bitsadmin-getstate
:: https://stackoverflow.com/a/21352240
:: https://www.dostips.com/forum/viewtopic.php?p=35376&sid=7d74f4bac79338d3aa3903a72ead8135#p35376
:: "bitsadmin /getbytestotal" shows 18446744073709551615 when the Job is just started(for a few seconds) in BITSADMIN 3.0 - Windows 7
:: 10 spaces are needed to overwrite the previous state line.
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETSTATE Wget_download') DO (
	CMD.EXE /C IF . EQU . "%~F0" PRINT "!CR!Awaiting TRANSFERRING State..  [ Current State : %%A ]          "
	FINDSTR.EXE /RI /C:"^ *:BITSADMIN_Download_%%A " /C:"^ *:BITSADMIN_Download_%%A$" "%~F0" >NUL 2>&1 && GOTO BITSADMIN_Download_%%A
)
PATHPING.EXE 127.0.0.1 -n -q 1 -p 250 > NUL
GOTO BITSADMIN_State_Loop

:BITSADMIN_Download_TRANSFERRING
REM * Download - BITSADMIN: Create Full Progress bar
REM :: FOR /L %%A IN (1,1,33) DO CALL SET "BITS_HASHS=%%BITS_HASHS%%#"
REM :: FOR /L %%A IN (1,1,33) DO CALL SET "BITS_UNDERLINES=%%BITS_UNDERLINES%%_"
REM :: SET "BITS_FULLBAR=%BITS_HASHS%%BITS_UNDERLINES%"
SET "BITS_FULLBAR=#################################_________________________________"

REM * Download - BITSADMIN: Reset TimeOutvalue
BITSADMIN.EXE /SETNOPROGRESSTIMEOUT Wget_download 30 > NUL

:BITSADMIN_Download_Loop
REM * Download - BITSADMIN: Update Bytes
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTOTAL Wget_download') DO SET "BITS_TOTALBYTES=%%A"
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETBYTESTRANSFERRED Wget_download') DO SET "BITS_TRANSFERREDBYTES=%%A"

REM * Download - BITSADMIN: Get percent
SET /A "BITS_PERCENT=(BITS_TRANSFERREDBYTES*100)/BITS_TOTALBYTES"

REM * Download - BITSADMIN: Convert bytes to Kibibytes
SET /A "BITS_TOTALKIB=BITS_TOTALBYTES/1024"
SET /A "BITS_TRANSFERREDKIB=BITS_TRANSFERREDBYTES/1024"

REM * Download - BITSADMIN: Extract part of the Full Progress bar
:: Do not use variable starts with "A"
SET /A "BITS_BARNUM=33-BITS_PERCENT/3"
CALL SET "BITS_BAR=%%BITS_FULLBAR:~%BITS_BARNUM%,33%%"

REM * Download - BITSADMIN: Update Progress bar
CMD.EXE /C IF . EQU . "%~F0" PRINT "!CR!wget.exe       [%BITS_BAR%]  %BITS_PERCENT%%%  ^|  %BITS_TRANSFERREDKIB%KiB/%BITS_TOTALKIB%KiB"

FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETSTATE Wget_download') DO (
	IF "%%A" == "TRANSFERRING" (
		PATHPING.EXE 127.0.0.1 -n -q 1 -p 250 > NUL
		GOTO BITSADMIN_Download_Loop
	)
	IF NOT "%%A" == "QUEUED" IF NOT "%%A" == "CONNECTING" (
		FINDSTR.EXE /RI /C:"^ *:BITSADMIN_Download_%%A " /C:"^ *:BITSADMIN_Download_%%A$" "%~F0" >NUL 2>&1 && GOTO BITSADMIN_Download_%%A
	)
	GOTO BITSADMIN_Download_Unexpected
)

:BITSADMIN_Download_TRANSIENT_ERROR
COLOR 0E
ECHO:
ECHO:
ECHO %DATE% %TIME% [ERROR] - TRANSIENT_ERROR state occurred!
ECHO If the TRANSIENT_ERROR occurs for more than 30 seconds, then the Job will be placed in a fatal error state.
ECHO:

:BITSADMIN_Download_Transient_Loop
:: The timeout interval stops or resets when a byte of data is successfully transferred; not stops or resets on QUEUED or CONNECTING state..
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETSTATE Wget_download') DO (
	CMD.EXE /C IF . EQU . "%~F0" PRINT "!CR!Waiting for non-error state. The current error status is %%A.          "
	IF "%%A" == "TRANSIENT_ERROR" (
		PATHPING.EXE 127.0.0.1 -n -q 1 -p 250 > NUL
		GOTO BITSADMIN_Download_Transient_Loop
	)
	COLOR 07
	ECHO:
	CMD.EXE /C IF . EQU . "%~F0" PRINT "!CR!%%A State occurred. Please wait..."
	IF NOT "%%A" == "QUEUED" IF NOT "%%A" == "CONNECTING" (
		FINDSTR.EXE /RI /C:"^ *:BITSADMIN_Download_%%A " /C:"^ *:BITSADMIN_Download_%%A$" "%~F0" >NUL 2>&1
		IF %ERRORLEVEL% EQU 0 (
			GOTO BITSADMIN_Download_%%A
		) ELSE (
			GOTO BITSADMIN_Download_Unexpected
		)
	)
	ECHO:
	BITSADMIN.EXE /SETNOPROGRESSTIMEOUT Wget_download 120 > NUL
	GOTO BITSADMIN_State_Loop
)

:BITSADMIN_Download_ERROR
ECHO:
ECHO:
ECHO %DATE% %TIME% [ERROR] - ERROR state occurred!
BITSADMIN.EXE /RAWRETURN /GETERROR Wget_download
GOTO BITSADMIN_Download_Selection

:BITSADMIN_Download_Unexpected
:BITSADMIN_Download_SUSPENDED
:BITSADMIN_Download_CANCELED
SET "BITS_ERRORNAME=Unexpected state occurred!"
SET "BITS_ERRORINFO=An unexpected state has occurred. (like SUSPENDED or CANCELED state)"
GOTO BITSADMIN_Download_Errorinfo

:BITSADMIN_Download_Complete_Error
SET "BITS_ERRORNAME=Error occurred when completing the Job!"
SET "BITS_ERRORINFO=An ErrorLevel has detected when completing the Job."
GOTO BITSADMIN_Download_Errorinfo

:BITSADMIN_Download_Errorinfo
ECHO:
ECHO:
ECHO %DATE% %TIME% [ERROR] - %BITS_ERRORNAME%
ECHO %BITS_ERRORINFO%

:BITSADMIN_Download_Selection
COLOR 0C
REM :: ECHO 1) restart download 2) check state again 3) change downloader server 4) exit
REM :: SET /P ....
PAUSE
BITSADMIN.EXE /CANCEL Wget_download > NUL

:BITSADMIN_Download_TRANSFERRED
:BITSADMIN_Download_ACKNOWLEDGED
REM * Download - BITSADMIN: Update Progress bar
CMD.EXE /C IF . EQU . "%~F0" PRINT "!CR!wget.exe       [%BITS_BAR%]  %BITS_PERCENT%%%  ^|  %BITS_TRANSFERREDKIB%KiB/%BITS_TOTALKIB%KiB"

REM * Download - BITSADMIN: Complete Transferring
FOR /F "TOKENS=*" %%A IN ('BITSADMIN.EXE /RAWRETURN /GETCOMPLETIONTIME Wget_download') DO SET "BITS_COMPLETIONTIME=%%A"
BITSADMIN.EXE /COMPLETE Wget_download > NUL
IF %ERRORLEVEL% NEQ 0 GOTO BITSADMIN_Download_Complete_Error
ECHO:
ECHO:
ECHO %BITS_CREATIONTIME% - Job %BITS_JOBNAME% Completed
ECHO Saved file to %BITS_PATH%\wget.exe

:: after download
explorer.exe %BITS_PATH%
pause
exit /b

:PRINT
rem Please note that this function/batch can NOT be started with a call.
rem Since it terminates the calling batch.
rem Usage: cmd /c if. equ . "Path\batchname" "whiteSpaces ...message Text"
@ECHO ON
@( SETLOCAL ENABLEDELAYEDEXPANSION
SET "PROMPT=%~1"
)
%== !required this is an empty Line, do not remove! ==%
@( ECHO OFF
img3.png
img3.png (25.48 KiB) Viewed 6681 times

Improvements ::
· used "cmd /c if . equ ...."
· added some codes for error state.
· added bitsadmin version information check.
· improved code for progress bar.
· replaced timeout to pathping to loop fast.
· added some bitsadmin settings.

Thanks for the suggestioins! :D

Post Reply