From 1daa38c90a22d33961970db4ca0b95869078cd70 Mon Sep 17 00:00:00 2001 From: Charalampos Gkikas Date: Thu, 14 Mar 2019 22:44:35 +0200 Subject: [PATCH 1/3] Basic Windows support --- progress/__init__.py | 38 +++++++++++++++++++++++++++++++++++--- 1 file changed, 35 insertions(+), 3 deletions(-) diff --git a/progress/__init__.py b/progress/__init__.py index e434c25..7742554 100644 --- a/progress/__init__.py +++ b/progress/__init__.py @@ -14,6 +14,8 @@ from __future__ import division, print_function +import os +import shutil from collections import deque from datetime import timedelta from math import ceil @@ -29,6 +31,14 @@ HIDE_CURSOR = '\x1b[?25l' SHOW_CURSOR = '\x1b[?25h' +if os.name == 'nt': + import msvcrt + import ctypes + + class _CursorInfo(ctypes.Structure): + _fields_ = [("size", ctypes.c_int), + ("visible", ctypes.c_byte)] + class Infinite(object): file = stderr @@ -51,7 +61,16 @@ def __init__(self, message='', **kwargs): if self.file and self.is_tty(): if self.hide_cursor: - print(HIDE_CURSOR, end='', file=self.file) + if os.name == 'nt': + ci = _CursorInfo() + handle = ctypes.windll.kernel32.GetStdHandle(-11) + ctypes.windll.kernel32.GetConsoleCursorInfo( + handle, ctypes.byref(ci)) + ci.visible = False + ctypes.windll.kernel32.SetConsoleCursorInfo( + handle, ctypes.byref(ci)) + else: + print(HIDE_CURSOR, end='', file=self.file) print(self.message, end='', file=self.file) self.file.flush() @@ -87,7 +106,11 @@ def start(self): def clearln(self): if self.file and self.is_tty(): - print('\r\x1b[K', end='', file=self.file) + if os.name == 'nt': + empty_line = (shutil.get_terminal_size()[0]-1)*" " + print('\r%s\r' % (empty_line), end='', file=self.file) + else: + print('\r\x1b[K', end='', file=self.file) def write(self, s): if self.file and self.is_tty(): @@ -106,7 +129,16 @@ def finish(self): if self.file and self.is_tty(): print(file=self.file) if self.hide_cursor: - print(SHOW_CURSOR, end='', file=self.file) + if os.name == 'nt': + ci = _CursorInfo() + handle = ctypes.windll.kernel32.GetStdHandle(-11) + ctypes.windll.kernel32.GetConsoleCursorInfo( + handle, ctypes.byref(ci)) + ci.visible = True + ctypes.windll.kernel32.SetConsoleCursorInfo( + handle, ctypes.byref(ci)) + else: + print(SHOW_CURSOR, end='', file=self.file) def is_tty(self): return self.file.isatty() if self.check_tty else True From 32e83ea7ebf04e47c27feb9ec09624abd2e2b2ec Mon Sep 17 00:00:00 2001 From: Charalampos Gkikas Date: Sat, 16 Mar 2019 12:38:00 +0200 Subject: [PATCH 2/3] lazy writing support --- progress/__init__.py | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/progress/__init__.py b/progress/__init__.py index 7742554..9c43c3a 100644 --- a/progress/__init__.py +++ b/progress/__init__.py @@ -59,6 +59,9 @@ def __init__(self, message='', **kwargs): self._width = 0 self.message = message + # Lazy writing + self.previous_line = '' + if self.file and self.is_tty(): if self.hide_cursor: if os.name == 'nt': @@ -107,7 +110,9 @@ def start(self): def clearln(self): if self.file and self.is_tty(): if os.name == 'nt': - empty_line = (shutil.get_terminal_size()[0]-1)*" " + max_empty_size = min(shutil.get_terminal_size()[ + 0]-1, len(self.previous_line)) + empty_line = max_empty_size * " " print('\r%s\r' % (empty_line), end='', file=self.file) else: print('\r\x1b[K', end='', file=self.file) @@ -121,9 +126,11 @@ def write(self, s): def writeln(self, line): if self.file and self.is_tty(): - self.clearln() - print(line, end='', file=self.file) - self.file.flush() + if line != self.previous_line: + self.clearln() + print(line, end='', file=self.file) + self.file.flush() + self.previous_line = line def finish(self): if self.file and self.is_tty(): From 1c231ccb0571121c9688db33100720ae915698f0 Mon Sep 17 00:00:00 2001 From: Charalampos Gkikas Date: Tue, 19 Mar 2019 10:56:00 +0200 Subject: [PATCH 3/3] No more use of clearln() just +'\r' --- progress/__init__.py | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/progress/__init__.py b/progress/__init__.py index 9c43c3a..4de261f 100644 --- a/progress/__init__.py +++ b/progress/__init__.py @@ -127,8 +127,12 @@ def write(self, s): def writeln(self, line): if self.file and self.is_tty(): if line != self.previous_line: - self.clearln() - print(line, end='', file=self.file) + # We are not clearing the line just printing spaces + # at the of the line + # self.clearln() + empty = max(0, len(self.previous_line) - len(line)) + empty = min(empty, shutil.get_terminal_size()[0]-1) + print("\r" + line + empty*" ", end='', file=self.file) self.file.flush() self.previous_line = line