In-Place Progress Output in the Terminal or Console

In-place progress output in the terminal or console

Use carriage return. '\r' should usually work.

In-place progress output to the console: How to empty the current line

You need to send the sequence of bytes that corresponds to the terminfo
variable clr_eol (capability name el) after using \r. There are several
ways that you could get that.

Simplest, assume that there's a constant value. On the terminals I've checked
it is \e[K, but I've only checked a couple. On both of those the following
works:

clear = "\e[K"
print "foo 123"
print "\r#{clear}bar\n"

You could also get the value using:

clear = `tput el` 

Or you could use the terminfo gem:

require 'terminfo'
clear = TermInfo.control_string 'el'

How do I write output in same place on the console?

You can also use the carriage return:

sys.stdout.write("Download progress: %d%%   \r" % (progress) )
sys.stdout.flush()

How to add a progress bar to a shell script?

You can implement this by overwriting a line. Use \r to go back to the beginning of the line without writing \n to the terminal.

Write \n when you're done to advance the line.

Use echo -ne to:

  1. not print \n and
  2. to recognize escape sequences like \r.

Here's a demo:

echo -ne '#####                     (33%)\r'
sleep 1
echo -ne '############# (66%)\r'
sleep 1
echo -ne '####################### (100%)\r'
echo -ne '\n'

In a comment below, puk mentions this "fails" if you start with a long line and then want to write a short line: In this case, you'll need to overwrite the length of the long line (e.g., with spaces).

How to display a progress indicator in pure C/C++ (cout/printf)?

With a fixed width of your output, use something like the following:

float progress = 0.0;
while (progress < 1.0) {
int barWidth = 70;

std::cout << "[";
int pos = barWidth * progress;
for (int i = 0; i < barWidth; ++i) {
if (i < pos) std::cout << "=";
else if (i == pos) std::cout << ">";
else std::cout << " ";
}
std::cout << "] " << int(progress * 100.0) << " %\r";
std::cout.flush();

progress += 0.16; // for demonstration only
}
std::cout << std::endl;

http://ideone.com/Yg8NKj

[>                                                                     ] 0 %
[===========> ] 15 %
[======================> ] 31 %
[=================================> ] 47 %
[============================================> ] 63 %
[========================================================> ] 80 %
[===================================================================> ] 96 %

Note that this output is shown one line below each other, but in a terminal emulator (I think also in Windows command line) it will be printed on the same line.

At the very end, don't forget to print a newline before printing more stuff.

If you want to remove the bar at the end, you have to overwrite it with spaces, to print something shorter like for example "Done.".

Also, the same can of course be done using printf in C; adapting the code above should be straight-forward.

Replace console output in Python

An easy solution is just writing "\r" before the string and not adding a newline; if the string never gets shorter this is sufficient...

sys.stdout.write("\rDoing thing %i" % i)
sys.stdout.flush()

Slightly more sophisticated is a progress bar... this is something I am using:

def start_progress(title):
global progress_x
sys.stdout.write(title + ": [" + "-"*40 + "]" + chr(8)*41)
sys.stdout.flush()
progress_x = 0

def progress(x):
global progress_x
x = int(x * 40 // 100)
sys.stdout.write("#" * (x - progress_x))
sys.stdout.flush()
progress_x = x

def end_progress():
sys.stdout.write("#" * (40 - progress_x) + "]\n")
sys.stdout.flush()

You call start_progress passing the description of the operation, then progress(x) where x is the percentage and finally end_progress()

Text progress bar in terminal with block characters


Python 3

A Simple, Customizable Progress Bar

Here's an aggregate of many of the answers below that I use regularly (no imports required).

Note: All code in this answer was created for Python 3; see end of answer to use this code with Python 2.

# Print iterations progress
def printProgressBar (iteration, total, prefix = '', suffix = '', decimals = 1, length = 100, fill = '█', printEnd = "\r"):
"""
Call in a loop to create terminal progress bar
@params:
iteration - Required : current iteration (Int)
total - Required : total iterations (Int)
prefix - Optional : prefix string (Str)
suffix - Optional : suffix string (Str)
decimals - Optional : positive number of decimals in percent complete (Int)
length - Optional : character length of bar (Int)
fill - Optional : bar fill character (Str)
printEnd - Optional : end character (e.g. "\r", "\r\n") (Str)
"""
percent = ("{0:." + str(decimals) + "f}").format(100 * (iteration / float(total)))
filledLength = int(length * iteration // total)
bar = fill * filledLength + '-' * (length - filledLength)
print(f'\r{prefix} |{bar}| {percent}% {suffix}', end = printEnd)
# Print New Line on Complete
if iteration == total:
print()

Sample Usage

import time

# A List of Items
items = list(range(0, 57))
l = len(items)

# Initial call to print 0% progress
printProgressBar(0, l, prefix = 'Progress:', suffix = 'Complete', length = 50)
for i, item in enumerate(items):
# Do stuff...
time.sleep(0.1)
# Update Progress Bar
printProgressBar(i + 1, l, prefix = 'Progress:', suffix = 'Complete', length = 50)

Sample Output

Progress: |█████████████████████████████████████████████-----| 90.0% Complete

Update

There was discussion in the comments regarding an option that allows the progress bar to adjust dynamically to the terminal window width. While I don't recommend this, here's a gist that implements this feature (and notes the caveats).

Single-Call Version of The Above

A comment below referenced a nice answer posted in response to a similar question. I liked the ease of use it demonstrated and wrote a similar one, but opted to leave out the import of the sys module while adding in some of the features of the original printProgressBar function above.

Some benefits of this approach over the original function above include the elimination of an initial call to the function to print the progress bar at 0% and the use of enumerate becoming optional (i.e. it is no longer explicitly required to make the function work).

def progressBar(iterable, prefix = '', suffix = '', decimals = 1, length = 100, fill = '█', printEnd = "\r"):
"""
Call in a loop to create terminal progress bar
@params:
iterable - Required : iterable object (Iterable)
prefix - Optional : prefix string (Str)
suffix - Optional : suffix string (Str)
decimals - Optional : positive number of decimals in percent complete (Int)
length - Optional : character length of bar (Int)
fill - Optional : bar fill character (Str)
printEnd - Optional : end character (e.g. "\r", "\r\n") (Str)
"""
total = len(iterable)
# Progress Bar Printing Function
def printProgressBar (iteration):
percent = ("{0:." + str(decimals) + "f}").format(100 * (iteration / float(total)))
filledLength = int(length * iteration // total)
bar = fill * filledLength + '-' * (length - filledLength)
print(f'\r{prefix} |{bar}| {percent}% {suffix}', end = printEnd)
# Initial Call
printProgressBar(0)
# Update Progress Bar
for i, item in enumerate(iterable):
yield item
printProgressBar(i + 1)
# Print New Line on Complete
print()

Sample Usage

import time

# A List of Items
items = list(range(0, 57))

# A Nicer, Single-Call Usage
for item in progressBar(items, prefix = 'Progress:', suffix = 'Complete', length = 50):
# Do stuff...
time.sleep(0.1)

Sample Output

Progress: |█████████████████████████████████████████████-----| 90.0% Complete

Python 2

To use the above functions in Python 2, set the encoding to UTF-8 at the top of your script:

# -*- coding: utf-8 -*-

And replace the Python 3 string formatting in this line:

print(f'\r{prefix} |{bar}| {percent}% {suffix}', end = printEnd)

With Python 2 string formatting:

print('\r%s |%s| %s%% %s' % (prefix, bar, percent, suffix), end = printEnd)

Update Command-line Output, i.e. for Progress

This can be done using ANSI Escape Sequences -- see here for a list.

In PHP, you'll use "\033" when it's indicated ESC on that page.



In your case, you could use something like this :

echo "Progress :      ";  // 5 characters of padding at the end
for ($i=0 ; $i<=100 ; $i++) {
echo "\033[5D"; // Move 5 characters backward
echo str_pad($i, 3, ' ', STR_PAD_LEFT) . " %"; // Output is always 5 characters long
sleep(1); // wait for a while, so we see the animation
}



I simplified a bit, making sure I always have 5 extra characters, and always displaying the same amount of data, to always move backwards by the same number of chars...

But, of course, you should be able to do much more complicated, if needed ;-)

And there are many other interesting escape sequences : colors, for instance, can enhance your output quite a bit ;-)



Related Topics



Leave a reply



Submit