remove obsolete files

This commit is contained in:
l_samenv
2024-07-12 10:58:59 +02:00
parent ed505d29c7
commit 0c0662b0b1
4 changed files with 0 additions and 1643 deletions

219
dummy.py
View File

@ -1,219 +0,0 @@
#!/usr/bin/env python
import json
import sys
import copy
from collections import OrderedDict, deque
import tcp_lineserver as lineserver
import uuid
import traceback
class Group(object):
def __init__(self, name):
self.name = name
self.title = name
self.components = []
class Component(object):
def __init__(self, name, g):
self.name = name
self.group = g
self.value = None
self.properties = {}
init_values = ['device name', 'device stick_name']
def set_value(c, value):
c.value = value
print 'set',c.name,c.value,c.group
for n in init_values:
if c.name == n:
init(cindex['device name'].value)
break
for client in clients.values():
client.send_msg(dict(type='update', updates=[dict(name=c.name, value=c.value)]))
def history_add(item):
history.append(item)
id, is_cmd, line = item
for cid, client in console_clients.items():
client.send_msg(dict(
type = 'command' if is_cmd else 'reply',
origin = 'self' if cid == id else 'other',
line = line
))
class ClientType:
GROUP = 1
CONSOLE = 2
MAINUPDATE = 3
class DummyHandler(lineserver.LineHandler):
def __init__(self, *args, **kwargs):
lineserver.LineHandler.__init__(self, *args, **kwargs)
self.id = None
def send_msg(self, msg):
print '<', msg
self.send_line(json.dumps(msg))
def handle_line(self, line):
print '>', line
msg = json.loads(line)
msgtype = msg['type']
if msgtype == 'init':
id = msg.get('id', '0')
if self.id != msg['id']:
self.id = msg['id']
clients[self.id] = self
self.title = ""
global main_update
main_update.append(self)
#self.send_msg({'type': 'accept-mainupdate'})
init(cindex['device name'].value)
elif msgtype == 'getblock':
path = msg['path']
grp = path.split(",")[-1]
g = groups[grp]
clist = []
for c in g.components:
cdict = copy.deepcopy(c.properties)
cdict['name'] = c.name
clist.append(cdict)
self.send_msg(dict(type='draw', path=path, title=g.title, components=clist))
elif msgtype == 'updateblock':
path = msg['path']
grp = path.split(",")[-1]
g = groups[grp]
clist = []
updates = []
for c in g.components:
if c.properties.get('type','') != 'group':
updates.append(dict(name=c.name, value=c.value))
self.send_msg(dict(type='accept-block'))
self.send_msg(dict(type='update', updates=updates))
elif msgtype == 'console':
print '*** make console ',self.id,self
self.send_msg(dict(type='accept-console'))
console_clients[self.id] = self
for item in history:
id, is_cmd, line = item
self.send_msg(dict(
type = 'command' if is_cmd else 'reply',
origin = 'self' if self.id == id else 'other',
line = line
))
elif msgtype == 'sendcommand':
cmd = msg['command'].split(' ')
history_add((self.id, True, msg['command']))
if len(cmd) == 1:
name = cmd[0]
c = cindex.get(name, None)
val = None
else:
name = cmd[0] + " " + cmd[1]
try:
c = cindex[name]
except KeyError:
try:
c = cindex[cmd[0]]
except KeyError:
c = None
else:
name = cmd[0]
val = " ".join(cmd[1:])
else:
if len(cmd) == 2:
val = None
else:
val = " ".join(cmd[2:])
if c == None:
history_add((self.id, False, "ERROR: " + name + " not found"))
elif val == None:
history_add((self.id, False, name + " = " + c.value))
else:
set_value(c, val)
history_add((self.id, False, "OK: " + name + " = " + c.value))
self.send_msg(dict(type = 'accept-command'))
def handle_close(self):
try:
print 'close client', self
del clients[self.id]
except KeyError:
print 'can not remove client'
try:
del console_clients[self.id]
print '*** removed console client',self.id,self
except KeyError:
print '*** console client already closed',self.id,self
self.close()
def init(device):
global cindex, groups, actual_device
if device != actual_device:
print 'INIT', actual_device, device
actual_device = device
cindex = {} # component index
groups = {}
groupsfile = device + ".json"
with open(groupsfile) as fil:
groupdict = json.load(fil)
for grp in groupdict:
gdict = groupdict[grp]
g = find_group(grp)
g.title = gdict.get('title', grp)
for cdict in gdict['components']:
cname = cdict['name']
c = Component(cname, g)
g.components.append(c)
cindex[cname] = c
c.properties = dict((k, v) for k, v in cdict.items() if k != 'name' and k != 'value')
c.value = cdict.get('value','')
if c.properties.get('type','') == 'group':
gg = find_group(cname)
if 'title' in cdict:
if gg.title == gg.name:
gg.title = cdict['title']
else:
c.properties['title'] = gg.title
devlist = [cindex[n].value for n in init_values]
device_title = "DUMMY " + "/".join(devlist)
print 'ENDINIT', device_title
for m in main_update:
if m.title != device_title:
m.title=device_title
m.send_msg(dict(type='id', id=m.id, title=device_title))
def find_group(grp):
if grp in groups:
g = groups[grp]
else:
g = Group(grp)
groups[grp] = g
return g
if __name__ == "__main__":
console_clients = {}
clients = {}
cindex = {} # component index
groups = {}
history = deque(maxlen=50)
console_id = 0
main_update = []
actual_device = ''
try:
device = sys.argv[2]
except IndexError:
device = "dummy1"
try:
port = int(sys.argv[1])
except IndexError:
port = 5001
init(device)
server = lineserver.LineServer('localhost', port, DummyHandler)
server.loop()

View File

@ -1,171 +0,0 @@
import time
import sys
if sys.version_info >= (3,6):
Dict = dict
else:
from collections import OrderedDict as Dict
class PrettyFloat(float):
def __repr__(self):
return '%.15g' % self
def get_abs_time(*times):
now = int(time.time() + 0.999)
oneyear = 365 * 24 * 3600
return tuple(t + now if t < oneyear else t for t in times)
class ColorMap(object):
""""
ColorMap is using official CSS color names, with the exception of Green, as this
is defined differently with X11 colors than in SEA, and used heavily in config files.
Here Green is an alias to Lime (#00FF00) and MidGreen is #008000, which is called Green in CSS.
The function to_code is case insensitive and accepts also names with underscores.
The order is choosen by M. Zolliker for the SEA client, originally only the first 16 were used.
"""
hex_name = (
("#FFFFFF", "White"), ("#FF0000", "Red"), ("#00FF00", "Lime"), ("#0000FF", "Blue"), ("#FF00FF", "Magenta"),
("#FFFF00", "Yellow"), ("#00FFFF", "Cyan"), ("#000000", "Black"), ("#FFA500", "Orange"),
("#006400", "DarkGreen"), ("#9400D3", "DarkViolet"), ("#A52A2A", "Brown"), ("#87CEEB", "SkyBlue"),
("#808080", "Gray"), ("#FF69B4", "HotPink"), ("#FFFFE0", "LightYellow"), ("#00FF7F", "SpringGreen"),
("#000080", "Navy"), ("#1E90FF", "DodgerBlue"), ("#9ACD32", "YellowGreen"), ("#008B8B", "DarkCyan"),
("#808000", "Olive"), ("#DEB887", "BurlyWood"),
("#7B68EE", "MediumSlateBlue"), ("#483D8B", "DarkSlateBlue"), ("#98FB98", "PaleGreen"), ("#FF1493", "DeepPink"),
("#FF6347", "Tomato"), ("#32CD32", "LimeGreen"), ("#DDA0DD", "Plum"), ("#7FFF00", "Chartreuse"),
("#800080", "Purple"), ("#00CED1", "DarkTurquoise"), ("#8FBC8F", "DarkSeaGreen"), ("#4682B4", "SteelBlue"),
("#800000", "Maroon"),
("#3CB371", "MediumSeaGreen"), ("#FF4500", "OrangeRed"), ("#BA55D3", "MediumOrchid"),
("#2F4F4F", "DarkSlateGray"), ("#CD853F", "Peru"), ("#228B22", "ForestGreen"), ("#48D1CC", "MediumTurquoise"),
("#DC143C", "Crimson"),
("#D3D3D3", "LightGray"), ("#ADFF2F", "GreenYellow"), ("#7FFFD4", "Aquamarine"), ("#BC8F8F", "RosyBrown"),
("#20B2AA", "LightSeaGreen"), ("#C71585", "MediumVioletRed"), ("#F0E68C", "Khaki"),
("#6495ED", "CornflowerBlue"),
("#556B2F", "DarkOliveGreen"), ("#CD5C5C", "IndianRed "), ("#2E8B57", "SeaGreen"), ("#F08080", "LightCoral"),
("#8A2BE2", "BlueViolet"), ("#AFEEEE", "PaleTurquoise"), ("#4169E1", "RoyalBlue"), ("#0000CD", "MediumBlue"),
("#B8860B", "DarkGoldenRod"), ("#00BFFF", "DeepSkyBlue"), ("#FFC0CB", "Pink"), ("#4B0082", "Indigo "),
("#A0522D", "Sienna"),
("#FFD700", "Gold"), ("#F4A460", "SandyBrown"), ("#DAA520", "GoldenRod"), ("#DA70D6", "Orchid"),
("#E6E6FA", "Lavender"),
("#5F9EA0", "CadetBlue"), ("#D2691E", "Chocolate"), ("#66CDAA", "MediumAquaMarine"), ("#6B8E23", "OliveDrab"),
("#A9A9A9", "DarkGray"), ("#BDB76B", "DarkKhaki"), ("#696969", "DimGray"), ("#B0C4DE", "LightSteelBlue"),
("#191970", "MidnightBlue"), ("#FFE4C4", "Bisque"), ("#6A5ACD", "SlateBlue"), ("#EE82EE", "Violet"),
("#8B4513", "SaddleBrown"), ("#FF7F50", "Coral"), ("#008000", "MidGreen"), ("#DB7093", "PaleVioletRed"),
("#C0C0C0", "Silver"),
("#E0FFFF", "LightCyan"), ("#9370DB", "MediumPurple"), ("#FF8C00", "DarkOrange"),
("#00FA9A", "MediumSpringGreen"),
("#E9967A", "DarkSalmon"), ("#778899", "LightSlateGray"), ("#9932CC", "DarkOrchid"),
("#EEE8AA", "PaleGoldenRod"),
("#F8F8FF", "GhostWhite"), ("#FFA07A", "LightSalmon"), ("#ADD8E6", "LightBlue"), ("#D8BFD8", "Thistle"),
("#FFE4E1", "MistyRose"), ("#FFDEAD", "NavajoWhite"), ("#40E0D0", "Turquoise"), ("#90EE90", "LightGreen"),
("#B22222", "FireBrick"), ("#008080", "Teal"), ("#F0FFF0", "HoneyDew"), ("#FFFACD", "LemonChiffon"),
("#FFF5EE", "SeaShell"),
("#F5F5DC", "Beige"), ("#DCDCDC", "Gainsboro"), ("#FA8072", "Salmon"), ("#8B008B", "DarkMagenta"),
("#FFB6C1", "LightPink"),
("#708090", "SlateGray"), ("#87CEFA", "LightSkyBlue"), ("#FFEFD5", "PapayaWhip"), ("#D2B48C", "Tan"),
("#FFFFF0", "Ivory"),
("#F0FFFF", "Azure"), ("#F5DEB3", "Wheat"), ("#00008B", "DarkBlue"), ("#FFDAB9", "PeachPuff"),
("#8B0000", "DarkRed"),
("#FAF0E6", "Linen"), ("#B0E0E6", "PowderBlue"), ("#FFE4B5", "Moccasin"), ("#F5F5F5", "WhiteSmoke"),
("#FFF8DC", "Cornsilk"),
("#FFFAFA", "Snow"), ("#FFF0F5", "LavenderBlush"), ("#FFEBCD", "BlanchedAlmond"), ("#F0F8FF", "AliceBlue"),
("#FAEBD7", "AntiqueWhite"), ("#FDF5E6", "OldLace"), ("#FAFAD2", "LightGoldenRodYellow"),
("#F5FFFA", "MintCream"),
("#FFFAF0", "FloralWhite"), ("#7CFC00", "LawnGreen"), ("#663399", "RebeccaPurple"))
codes = {}
for i, pair in enumerate(hex_name):
codes[pair[0]] = i
low = pair[1].lower()
codes[low] = i
codes[low.replace("gray", "grey")] = i
codes["green"] = 2
codes["fuchsia"] = 4
codes["aqua"] = 6
@staticmethod
def to_code(colortext):
try:
return int(colortext)
except ValueError:
return ColorMap.codes.get(colortext.lower().replace("_", ""),-1)
@staticmethod
def check_hex(code):
if not code.startswith("#"):
return None
if len(code) == 4: # convert short code to long code
code = code[0:2] + code[1:3] + code[2:4] + code[3]
if len(code) != 7:
return None
try:
int(code[1:]) # we have a valid hex color code
return code
except ValueError:
return None
@staticmethod
def to_hex(code):
try:
return ColorMap.hex_name[code][0]
except IndexError:
return -1
def get_vars(main, time):
result = {}
time, = get_abs_time(time)
# get last value only
curves = main.get_curve_options((time, time))
for key, opts in curves.items():
if not opts.get('show', False):
continue
print(key, opts)
opts = dict(name=key, **opts)
unit = opts.pop('unit', '*')
tag = opts.pop('tag', unit)
if not tag in result:
result[tag] = dict(tag=tag, unit=unit, curves=Dict())
if 'label' not in opts:
opts['label'] = opts['name']
result[tag]["curves"][key] = opts
# determine colors
for _, curvegroup in result.items():
color_set = set()
auto_curves = []
curve_list = list(curvegroup["curves"].values())
curvegroup['curves'] = curve_list
for curve in curve_list:
col = curve.get("color", '').strip()
c = ColorMap.to_code(col)
if c < 0:
valid = ColorMap.check_hex(col)
if valid:
curve["original_color"] = col
curve["color"] = valid
else:
auto_curves.append(curve)
curve["original_color"] = col + "?"
else:
color_set.add(c)
curve["original_color"] = col
curve["color"] = ColorMap.to_hex(c)
c = 1 # omit white
for curve in auto_curves:
while c in color_set:
c += 1 # find unused color
curve["color"] = ColorMap.to_hex(c)
c += 1
return result
def get_curves(main, keys, timerange, cut_begin=True):
curves = main.get_curves(keys, get_abs_time(*timerange), maxpoints=500, cut_begin=cut_begin)
opts = main.get_curve_options(timerange, keys)
#if 'tt:target' in curves:
# print('---')
# print(curves['tt:target'].fmtm())
# print('TT', curves['tt:target'].for_json()[-5:])
return {k: c.for_json(opts.get(k, {}).get('period', 0)) for k, c in curves.items()}

View File

@ -1,232 +0,0 @@
from datetime import date
import time
import sys
import os
import logging
import json
class PrettyFloat(float):
def __repr__(self):
return '%.15g' % self
#encode = "!#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[]^_`abcdefghijklmnopqrstuvwxyz{|}~"
def get_abs_time(times):
now = int(time.time() + 0.999)
oneyear = 365 * 24 * 3600
return [t + now if t < oneyear else t for t in times]
class Scanner(object):
def __init__(self, directory, test_day=None):
self.directory = directory
self.last_time = {}
self.test_day = test_day
def scan(self, variable, timerange, next_point, *args, maxpoints=1000):
"""scan *variable* for *timerange*
args is forwarded to self.next() and contains at least the
initialisation for the result
returns a tuple(<dirty>, result)
<dirty> is true when the last time on the variable has changed
"""
start, to, now = get_abs_time(timerange + [0])
tresolution = (to - start) / float(maxpoints) if maxpoints else 0
old = None
t = 0
for di in range(date.fromtimestamp(start).toordinal(), date.fromtimestamp(to).toordinal() + 1):
d = date.fromordinal(di)
year, mon, day = self.test_day if self.test_day else (d.year, d.month, d.day)
path = self.directory + "logger/%d/%s/%.2d-%.2d.log" % \
(year, variable.lower(), mon, day)
try:
# logging.info("logger path %s", path)
with open(path) as f:
t0 = time.mktime((d.year, d.month, d.day, 0, 0, 0, 0, 0, -1))
for line in f:
if line[0] != '#':
t = t0 + (int(line[0:2]) * 60 + int(line[3:5])) * 60 + int(line[6:8])
if line[-1:] == '\n':
value = line[9:-1]
else:
value = line[9:]
if t < start:
old = value
else:
if old is not None:
next_point(start, old, tresolution, *args)
old = None
self.next(t, value, result)
if t > to:
break
except IOError:
pass
if t < start:
#if t == 0:
# t = start
if old is not None:
self.next(t, old, result)
if t != self.last_time.get(variable,0):
self.last_time[variable] = t
return True, result
return False, result
class NumCurve(object):
def __init__(self, tresolution):
self.result = []
self.tresolution = tresolution
def append(self, t, txtvalue):
try:
value = PrettyFloat(txtvalue)
except:
value = None
self.result.append((PrettyFloat(t), value))
self.value = value
self.last = t
class NumericScanner(Scanner):
def __init__(self, *args, **kwargs):
Scanner.__init__(self, *args, **kwargs)
def get_message(self, variables, timerange, show_empty=True):
tresolution = timerange / x
self.dirty = False
result = {}
for var in variables:
self.last = 0
self.dirty, curve = self.scan(var, timerange, []):
if show_empty or len(curve) > 1:
result[var] = curve
return result
class ColorMap(object):
'''
ColorMap is using official CSS color names, with the exception of Green, as this
is defined differently with X11 colors than in SEA, and used heavily in config files.
Here Green is an alias to Lime (#00FF00) and MidGreen is #008000, which is called Green in CSS.
The function to_code is case insensitive and accepts also names with underscores.
The order is choosen by M. Zolliker for the SEA client, originally only the first 16 were used.
'''
hex_name = (("#FFFFFF","White"), ("#FF0000","Red"), ("#00FF00","Lime"), ("#0000FF","Blue"), ("#FF00FF","Magenta"),
("#FFFF00","Yellow"), ("#00FFFF","Cyan"), ("#000000","Black"), ("#FFA500","Orange"), ("#006400","DarkGreen"),
("#9400D3","DarkViolet"), ("#A52A2A","Brown"), ("#87CEEB","SkyBlue"), ("#808080","Gray"), ("#FF69B4","HotPink"),
("#FFFFE0","LightYellow"), ("#00FF7F","SpringGreen"), ("#000080","Navy"), ("#1E90FF","DodgerBlue"),
("#9ACD32","YellowGreen"), ("#008B8B","DarkCyan"), ("#808000","Olive"), ("#DEB887","BurlyWood"),
("#7B68EE","MediumSlateBlue"), ("#483D8B","DarkSlateBlue"), ("#98FB98","PaleGreen"), ("#FF1493","DeepPink"),
("#FF6347","Tomato"), ("#32CD32","LimeGreen"), ("#DDA0DD","Plum"), ("#7FFF00","Chartreuse"), ("#800080","Purple"),
("#00CED1","DarkTurquoise"), ("#8FBC8F","DarkSeaGreen"), ("#4682B4","SteelBlue"), ("#800000","Maroon"),
("#3CB371","MediumSeaGreen"), ("#FF4500","OrangeRed"), ("#BA55D3","MediumOrchid"), ("#2F4F4F","DarkSlateGray"),
("#CD853F","Peru"), ("#228B22","ForestGreen"), ("#48D1CC","MediumTurquoise"), ("#DC143C","Crimson"),
("#D3D3D3","LightGray"), ("#ADFF2F","GreenYellow"), ("#7FFFD4","Aquamarine"), ("#BC8F8F","RosyBrown"),
("#20B2AA","LightSeaGreen"), ("#C71585","MediumVioletRed"), ("#F0E68C","Khaki"), ("#6495ED","CornflowerBlue"),
("#556B2F","DarkOliveGreen"), ("#CD5C5C","IndianRed "), ("#2E8B57","SeaGreen"), ("#F08080","LightCoral"),
("#8A2BE2","BlueViolet"), ("#AFEEEE","PaleTurquoise"), ("#4169E1","RoyalBlue"), ("#0000CD","MediumBlue"),
("#B8860B","DarkGoldenRod"), ("#00BFFF","DeepSkyBlue"), ("#FFC0CB","Pink"), ("#4B0082","Indigo "), ("#A0522D","Sienna"),
("#FFD700","Gold"), ("#F4A460","SandyBrown"), ("#DAA520","GoldenRod"), ("#DA70D6","Orchid"), ("#E6E6FA","Lavender"),
("#5F9EA0","CadetBlue"), ("#D2691E","Chocolate"), ("#66CDAA","MediumAquaMarine"), ("#6B8E23","OliveDrab"),
("#A9A9A9","DarkGray"), ("#BDB76B","DarkKhaki"), ("#696969","DimGray"), ("#B0C4DE","LightSteelBlue"),
("#191970","MidnightBlue"), ("#FFE4C4","Bisque"), ("#6A5ACD","SlateBlue"), ("#EE82EE","Violet"),
("#8B4513","SaddleBrown"), ("#FF7F50","Coral"), ("#008000","MidGreen"), ("#DB7093","PaleVioletRed"), ("#C0C0C0","Silver"),
("#E0FFFF","LightCyan"), ("#9370DB","MediumPurple"), ("#FF8C00","DarkOrange"), ("#00FA9A","MediumSpringGreen"),
("#E9967A","DarkSalmon"), ("#778899","LightSlateGray"), ("#9932CC","DarkOrchid"), ("#EEE8AA","PaleGoldenRod"),
("#F8F8FF","GhostWhite"), ("#FFA07A","LightSalmon"), ("#ADD8E6","LightBlue"), ("#D8BFD8","Thistle"),
("#FFE4E1","MistyRose"), ("#FFDEAD","NavajoWhite"), ("#40E0D0","Turquoise"), ("#90EE90","LightGreen"),
("#B22222","FireBrick"), ("#008080","Teal"), ("#F0FFF0","HoneyDew"), ("#FFFACD","LemonChiffon"), ("#FFF5EE","SeaShell"),
("#F5F5DC","Beige"), ("#DCDCDC","Gainsboro"), ("#FA8072","Salmon"), ("#8B008B","DarkMagenta"), ("#FFB6C1","LightPink"),
("#708090","SlateGray"), ("#87CEFA","LightSkyBlue"), ("#FFEFD5","PapayaWhip"), ("#D2B48C","Tan"), ("#FFFFF0","Ivory"),
("#F0FFFF","Azure"), ("#F5DEB3","Wheat"), ("#00008B","DarkBlue"), ("#FFDAB9","PeachPuff"), ("#8B0000","DarkRed"),
("#FAF0E6","Linen"), ("#B0E0E6","PowderBlue"), ("#FFE4B5","Moccasin"), ("#F5F5F5","WhiteSmoke"), ("#FFF8DC","Cornsilk"),
("#FFFAFA","Snow"), ("#FFF0F5","LavenderBlush"), ("#FFEBCD","BlanchedAlmond"), ("#F0F8FF","AliceBlue"),
("#FAEBD7","AntiqueWhite"), ("#FDF5E6","OldLace"), ("#FAFAD2","LightGoldenRodYellow"), ("#F5FFFA","MintCream"),
("#FFFAF0","FloralWhite"), ("#7CFC00","LawnGreen"), ("#663399","RebeccaPurple"))
codes = {}
for i, pair in enumerate(hex_name):
codes[pair[0]] = i
low = pair[1].lower()
codes[low] = i
codes[low.replace("gray","grey")] = i
codes["green"] = 2
codes["fuchsia"] = 4
codes["aqua"] = 6
@staticmethod
def to_code(colortext):
try:
return int(colortext)
except ValueError:
return ColorMap.codes.get(colortext.lower().replace("_",""),-1)
@staticmethod
def check_hex(code):
if not code.startswith("#"):
return None
if len(code) == 4: # convert short code to long code
code = code[0:2] + code[1:3] + code[2:4] + code[3]
if len(code) != 7:
return None
try:
int(code[1:]) # we have a valid hex color code
return code
except ValueError:
return None
@staticmethod
def to_hex(code):
try:
return ColorMap.hex_name[code][0]
except IndexError:
return -1
class VarsScanner(Scanner):
colors = {"red":0}
def __init__(self, directory, test_day=None):
Scanner.__init__(self, directory, test_day=test_day)
logging.info('vars dir %s', directory)
def next(self, t, value, result):
logging.info('vars %s', value)
for var in value.strip().split(" "):
vars = var.split("|")
if len(vars) == 1:
vars.append("")
if len(vars) == 2:
vars.append(vars[0])
if len(vars) == 3:
vars.append("")
name, unit, label, color = vars
if not unit in result:
result[unit] = dict(tag = unit, unit = unit.split("_")[0], curves=[])
result[unit]["curves"].append(dict(name=name, label=label, color=color))
def get_message(self, time):
# get last value only
_, result = self.scan("vars", [time, time], {})
for unit, curvegroup in result.items():
color_set = set()
auto_curves = []
for curve in curvegroup["curves"]:
col = curve["color"].strip()
c = ColorMap.to_code(col)
if c < 0:
valid = ColorMap.check_hex(col)
if valid:
curve["original_color"] = col
curve["color"] = valid
else:
auto_curves.append(curve)
curve["original_color"] = col + "?"
else:
color_set.add(c)
curve["original_color"] = col
curve["color"] = ColorMap.to_hex(c)
c = 1 # omit white
for curve in auto_curves:
while c in color_set: c += 1 # find unused color
curve["color"] = ColorMap.to_hex(c)
c += 1
return result

1021
seweb.py

File diff suppressed because it is too large Load Diff