355 lines
9.1 KiB
Python
355 lines
9.1 KiB
Python
# Part of VCStudio
|
||
# GPLv3 or later
|
||
|
||
# This file will visualize the rendering process
|
||
|
||
import os
|
||
import sys
|
||
import json
|
||
import time
|
||
|
||
if len(sys.argv) == 1:
|
||
project = input("Project: ")
|
||
else:
|
||
project = sys.argv[1]
|
||
|
||
def get_runtime_data(project):
|
||
|
||
# This will read a specific .json file from the system.
|
||
|
||
template = {"to_render":True,
|
||
"current_progress":"Fra: 69 | Mem: 420 |Sample: 69/420"}
|
||
try:
|
||
with open(project+"/render_runtime.json") as json_file:
|
||
data = json.load(json_file)
|
||
except:
|
||
data = template.copy()
|
||
|
||
return data
|
||
|
||
def save_runtime_data(data, project):
|
||
with open(project+"/render_runtime.json", 'w') as fp:
|
||
json.dump(data, fp, indent=4)
|
||
|
||
|
||
# Colors are used to make the
|
||
clr = {
|
||
"norm":"\033[00m", # Reset to normal
|
||
"bold":"\033[01m", # Bold Text
|
||
"ital":"\033[03m", # Italic Text
|
||
"undr":"\033[04m", # Underlined
|
||
"blnk":"\033[05m", # Blinking
|
||
|
||
# Text
|
||
"tdbl":"\033[30m", # Dark Black
|
||
"tdrd":"\033[31m", # Dark Red
|
||
"tdgr":"\033[32m", # Dark Green
|
||
"tdyl":"\033[33m", # Dark Yellow
|
||
"tdbu":"\033[34m", # Dark Blue
|
||
"tdma":"\033[35m", # Dark Magenta
|
||
"tdcy":"\033[36m", # Dark Cyan
|
||
"tdwh":"\033[37m", # Dark White
|
||
|
||
"tbbl":"\033[90m", # Bright Black
|
||
"tbrd":"\033[91m", # Bright Red
|
||
"tbgr":"\033[92m", # Bright Green
|
||
"tbyl":"\033[93m", # Bright Yellow
|
||
"tbbu":"\033[94m", # Bright Blue
|
||
"tbma":"\033[95m", # Bright Magenta
|
||
"tbcy":"\033[96m", # Bright Cyan
|
||
"tbwh":"\033[97m", # Bright White
|
||
# Background
|
||
"bdbl":"\033[40m", # Dark Black
|
||
"bdrd":"\033[41m", # Dark Red
|
||
"bdgr":"\033[42m", # Dark Green
|
||
"bdyl":"\033[43m", # Dark Yellow
|
||
"bdbu":"\033[44m", # Dark Blue
|
||
"bdma":"\033[45m", # Dark Magenta
|
||
"bdcy":"\033[46m", # Dark Cyan
|
||
"bdwh":"\033[47m", # Dark White
|
||
|
||
"bbbl":"\033[100m", # Bright Black
|
||
"bbrd":"\033[101m", # Bright Red
|
||
"bbgr":"\033[102m", # Bright Green
|
||
"bbyl":"\033[103m", # Bright Yellow
|
||
"bbbu":"\033[104m", # Bright Blue
|
||
"bbma":"\033[105m", # Bright Magenta
|
||
"bbcy":"\033[106m", # Bright Cyan
|
||
"bbwh":"\033[108m" # Bright White
|
||
}
|
||
|
||
# A function that insures a specific width of the printed part
|
||
def wdth(x, n):
|
||
|
||
# Convert Data to String
|
||
mode = "normal"
|
||
if type(x) == bool and x == True:
|
||
x = "V"
|
||
mode = "bdgr"
|
||
elif type(x) == bool and x == False:
|
||
x = "X"
|
||
mode = "bdrd"
|
||
else:
|
||
x = str(x)
|
||
|
||
# Turn emogis
|
||
#x = emote(x)
|
||
|
||
# Some characters are too wide. They do not obey the
|
||
# monospace of the terminal, thus making it not pretty.
|
||
|
||
# This is the string of characters which are checked to
|
||
good = "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ!\"#$%&'’()*+,-./:;<=>?@[\]^_`{|}~ йцукенгшщзхъфывапролджэячсмитьбюЙЦУКЕНГШЩЗХЪФЫВАПРОЛДЖЭЯЧСМИТЬБЮёЁ"
|
||
|
||
# let's filter the string
|
||
y = x
|
||
|
||
|
||
x = ""
|
||
for i in y:
|
||
if i in good:
|
||
x = x + i
|
||
else:
|
||
x = x + "▓"
|
||
|
||
# Now let's print what we've got.
|
||
if len(y) < n:
|
||
fac = n-len(y)
|
||
fac1 = int(round(fac/2))
|
||
fac2 = fac1
|
||
while fac1 + fac2 > fac:
|
||
fac2 -=1
|
||
while fac1 + fac2 < fac:
|
||
fac2 +=1
|
||
x = (" "*fac1)+x+(" "*fac2)
|
||
elif len(y) > n:
|
||
if n > 10:
|
||
x = x[:n-3]+"..."
|
||
else:
|
||
x = x[:n]
|
||
if mode == "normal":
|
||
return x
|
||
else:
|
||
return clr[mode]+clr["bold"]+x+clr["norm"]
|
||
|
||
def tsize():
|
||
|
||
# This funtion will get the size of the terminal and
|
||
# return it to the variables provided width, height
|
||
|
||
# On some systems this may not work. So there is a
|
||
# try function.
|
||
|
||
try:
|
||
# Getting the size of the terminal
|
||
import os
|
||
w, h = os.get_terminal_size()
|
||
|
||
# Sometimes when the terminal width is either
|
||
# even or odd. It breaks code for some other
|
||
# thing written differenly. For example:
|
||
|
||
# You may have an even width ( like 84 ) when
|
||
# writing a function. And then it works on different
|
||
# widths as well like 62 and 80 and 48. All of them
|
||
# are still even. Then you scale the terminal to be
|
||
# something off like 63 and the function breaks. You
|
||
# have one character too much or one character too little.
|
||
|
||
# This is why I do not want to have a difference. And
|
||
# force width to be one less, if it's not divisible by 2.
|
||
|
||
if not w % 2:
|
||
w = w - 1
|
||
|
||
return w, h
|
||
|
||
except:
|
||
|
||
# If, by any reason the terminal can't get it's size.
|
||
# We want to return some size regardless.
|
||
|
||
w = 60
|
||
h = 20
|
||
|
||
return w, h
|
||
|
||
|
||
def table(data, number=True):
|
||
|
||
# This function will present data in a pretty table thing.
|
||
|
||
# So let's first of all get the size of the terminal
|
||
w, h = tsize()
|
||
|
||
if number:
|
||
w = w - 4
|
||
|
||
# Then let's draw the categories for this we need to extract
|
||
# it's sizes. If there is no 'size' variable the sizes of
|
||
# each category will be spread equally.
|
||
|
||
size = [] # Here the size will go as pure character value.
|
||
|
||
if "size" in data:
|
||
for i in data["size"]:
|
||
size.append(int(( w - 10 ) / sum(data["size"]) * i))
|
||
|
||
while sum(size) < w - 10:
|
||
size[-1] += 1
|
||
|
||
# printing categories
|
||
nb = ""
|
||
if number:
|
||
nb = " "
|
||
s = " "+clr["bdma"]+" "+clr["tbwh"]+nb
|
||
|
||
for n, item in enumerate(data["categories"]):
|
||
s = s + wdth(item.upper(), size[n])
|
||
print(s+clr["bdma"]+" "+clr["norm"])
|
||
|
||
size[-1] += 1
|
||
|
||
# printing items
|
||
for b, i in enumerate(data["data"]):
|
||
|
||
# dark bright sequence thingy
|
||
if b % 2:
|
||
d = "b"
|
||
else:
|
||
d = "d"
|
||
nb = ""
|
||
if number:
|
||
nb = clr["tbwh"]+wdth(b,4)
|
||
s = " "+clr["bdma"]+" "+nb+clr["norm"]+clr["b"+d+"bu"]#+clr["tbwh"]
|
||
for n, item in enumerate(i):
|
||
s = s +clr["b"+d+"bu"]+ clr["tbwh"]+wdth(item, size[n]-1)+clr["bdma"]+" "
|
||
print(s+clr["norm"])
|
||
|
||
def center(line, c="bdma", blink=False):
|
||
|
||
# This funtiocn will bring a given string of text
|
||
# in the center of the terminal with a nice backgroud
|
||
# around it.
|
||
|
||
|
||
w, h = tsize()
|
||
|
||
if blink:
|
||
blink = clr["blnk"]
|
||
else:
|
||
blink = ""
|
||
|
||
if len(line) % 2:
|
||
line = line + " "
|
||
|
||
if len(line) < w - 11:
|
||
print(" "+clr[c],
|
||
wdth(" ", int((w-10)/2 - (len(line)/2))),
|
||
clr["bold"]+clr["tbwh"]+blink+line,
|
||
wdth(" ", int((w-10)/2 - (len(line)/2))-1),
|
||
clr["norm"])
|
||
else:
|
||
print(" "+clr[c],
|
||
clr["bold"]+clr["tbwh"]+blink+wdth(line,w-10),
|
||
clr["norm"])
|
||
|
||
running_for = 0
|
||
lastframe = 0
|
||
maxtime = 1000000
|
||
|
||
while True:
|
||
|
||
running_for = running_for + 1
|
||
|
||
runtime = get_runtime_data(project)
|
||
if not runtime.get("to_render"):
|
||
break
|
||
|
||
x,y = tsize()
|
||
|
||
if y > 8:
|
||
print("\n\n")
|
||
|
||
process = runtime.get("current_progress", "").split(" | ")
|
||
try:
|
||
del runtime["current_progress"]
|
||
except:
|
||
pass
|
||
|
||
data_print = {"categories":list(runtime.keys()),
|
||
"size":[1]*(len(runtime)),
|
||
"data":[list(runtime.values())]}
|
||
|
||
table(data_print, False)
|
||
|
||
data_print = {"categories":[""]*(len(process)),
|
||
"size":[1]*(len(process)),
|
||
"data":[process]}
|
||
|
||
|
||
|
||
|
||
table(data_print, False)
|
||
center("")
|
||
|
||
|
||
# Latest frames data
|
||
|
||
filename = runtime.get("current_file", "")
|
||
folder = filename[:filename.rfind("/")]+"/extra"
|
||
savefile = folder+filename[filename.rfind("/"):]+".json"
|
||
|
||
try:
|
||
with open(project+savefile) as json_file:
|
||
data = json.load(json_file)
|
||
except:
|
||
data = {}
|
||
|
||
listoftimesx = data.get("analytics", {}).get(data.get("save_folder", ""), [])
|
||
listoftimes = {}
|
||
minframe = data.get("start_frame", 0)
|
||
for i in listoftimesx:
|
||
try:
|
||
listoftimes[int(i)] = listoftimesx[i]
|
||
except:
|
||
pass
|
||
try:
|
||
maxframe = max(list(listoftimes.keys()))
|
||
|
||
|
||
|
||
if maxframe > lastframe:
|
||
lastframe = maxframe
|
||
running_for = 0
|
||
maxtime = max(list(listoftimes.values()))
|
||
maxtime = max(maxtime, running_for*1000000)
|
||
|
||
print()
|
||
|
||
|
||
for i in range(max(minframe,maxframe-y+16), maxframe+1):
|
||
|
||
amount = int((x-14)/(maxtime-minframe)*(listoftimes[i]-minframe))
|
||
|
||
|
||
print(" ",wdth(i, 4), "▒"*amount)
|
||
except Exception as e:
|
||
#print(e)
|
||
maxframe = 0
|
||
#maxtime = 1
|
||
lastframe = maxframe
|
||
running_for = 0
|
||
|
||
amount = int((x-14)/maxtime*running_for*1000000)
|
||
|
||
print(" " , wdth(maxframe+1, 4), "█"*amount)
|
||
|
||
|
||
amount = int((x-14)/(data.get("end_frame", maxframe+1)-minframe)*(maxframe+1-minframe))
|
||
|
||
print()
|
||
print(" "+clr["tbma"]+wdth(data.get("end_frame", maxframe+1), 4)+" "+("█"*amount)+clr["norm"])
|
||
|
||
time.sleep(1)
|
||
os.system("clear")
|