-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathjdt.py
181 lines (159 loc) · 5.31 KB
/
jdt.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
'''
Progress bar.
Did you know about `tqdm`?
Usage:
```python
with Jdt(500, 'loading...') as j:
for i in range(500):
j.acc()
doJob(i)
```
Run this file to see demo.
Set `override_terminal_width` when using Jupyter Notebook with jdt.
'''
from time import time
from math import log
from terminalsize import get_terminal_size
from graphic_terminal import clearLine
override_terminal_width = None
def effectiveTermWidth():
return override_terminal_width or get_terminal_size()[0]
class JdtAlreadyClosedError(BaseException):
'''Cannot update Jdt after complete. '''
def smartUnit(size, is_speed=False):
'''
n_byte => 6-char string with smart unit (KB, MG, GB)
'''
if size == 0:
return ' 0 '
if is_speed:
magnitude = int(log(size, 1024))
else:
magnitude = int(log(size / 9, 1024))
magnitude = min(magnitude, 3)
return format(size / 1024**magnitude, '4.0f') + \
{0: 'B ', 1: 'KB', 2: 'MB', 3: 'GB'}[magnitude]
class Jdt:
MIN_BAR_WIDTH = 6
def __init__(self, goal, msg='', width=None, UPP = 1):
self.active = True
self.goal = goal
self.msg = msg
if width is not None:
print('jdt Warning: argument `width` is deprecated. ')
self.done = 0
self.UPP = UPP
self.UPP_count = 0
# updates per print
self.print_mode = False
def getSuffix(self, done, progress):
return '%s Total: %d Done: %d' % (
format(progress, '4.0%'),
self.goal,
done
)
def update(self, new_done, symbol = '*', getSuffix = None, flush = False):
if not self.active:
raise JdtAlreadyClosedError
self.done = new_done
if not flush and self.UPP_count > 0:
self.UPP_count -= 1
return
self.UPP_count = self.UPP - 1
if self.goal == 0:
progress = 1
else:
progress = new_done / self.goal
terminal_width = effectiveTermWidth() - 4
if getSuffix is None:
getSuffix = self.getSuffix
suffix = getSuffix(new_done, progress)
msg_and_bar_width = terminal_width - len(suffix)
msg_width = min(len(self.msg), int(msg_and_bar_width / 2))
msg_to_print = self.msg[-msg_width:]
bar_width = msg_and_bar_width - msg_width
if bar_width < self.MIN_BAR_WIDTH:
bar_width = terminal_width - 2
msg_to_print = ''
suffix = ''
bar_inner_width = bar_width - 2
bar_fill_width = int(bar_inner_width * progress)
bar_empty_width = bar_inner_width - bar_fill_width
print('\r', msg_to_print, ' ',
'[', symbol * bar_fill_width, '_'*bar_empty_width, ']',
' ', suffix,
sep = '', end='',flush=True)
self.print_mode = False
def acc(self):
self.update(self.done + 1)
def complete(self):
def getSuffix(done, progress):
return 'Complete! Total: %d' % self.goal
self.update(self.goal, symbol = '#', getSuffix = getSuffix, flush = True)
self.active = False
print()
def print(self, *args, **kw):
if not self.print_mode:
self.print_mode = True
clearLine()
print()
print(f'jdt {self.done} / {self.goal}')
print(*args, **kw)
def __enter__(self):
return self
def __exit__(self, e_type, e_value, e_trace):
if e_type is None:
self.complete()
class CommJdt(Jdt):
def __init__(self, *argv, **kw):
super(__class__, self).__init__(*argv, **kw)
self.last_time = time()
def update(self, new_done, *argv, **kw):
delta_time = time() - self.last_time
self.last_time += delta_time
delta_done = new_done - self.done
self.done = new_done
if delta_time == 0:
speed = 999999999
else:
speed = delta_done / delta_time
def getSuffix(done, progress):
nonlocal speed
return '%s Total: %s Done: %s Speed: %s/s' % (
format(progress, '4.0%'),
smartUnit(self.goal),
smartUnit(done),
smartUnit(speed, is_speed = True)
)
kw['getSuffix'] = getSuffix
super(__class__, self).update(new_done, *argv, **kw)
def jdtIter(iterable, msg='', width = None, UPP = 1, goal = None):
'''
`iterable` must provide `__len__()`.
'''
goal = goal or len(iterable)
with Jdt(goal, msg, width, UPP) as j:
for x in iterable:
yield x
j.acc()
if __name__=='__main__':
from time import sleep
j=CommJdt(10240000, '/sdcard/download/browser/file.jpg')
for i in range(0,10240000,32345):
j.update(i)
sleep(0.01)
j.complete()
with Jdt(500, 'launching game') as j:
for i in range(500):
if i == 200:
j.print('Something happens!')
j.print('Logging information')
j.print('more information haha')
if i == 300:
j.print('Something else happens!')
j.print('Logging information')
sleep(0.01)
j.acc()
for i in jdtIter(range(500), 'jdtIter test'):
sleep(0.01)
input('Enter..')