Blender-Pipeline/network/render_viewer.py

356 lines
9.1 KiB
Python
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# 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")