_console.py 30 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910
  1. #! /usr/bin/python3
  2. # -*- coding: utf-8 -*-
  3. """
  4. This file is part of LibreLight.
  5. LibreLight is free software: you can redistribute it and/or modify
  6. it under the terms of the GNU General Public License as published by
  7. the Free Software Foundation, version 2 of the License.
  8. LibreLight is distributed in the hope that it will be useful,
  9. but WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  11. GNU General Public License for more details.
  12. You should have received a copy of the GNU General Public License
  13. along with LibreLight. If not, see <http://www.gnu.org/licenses/>.
  14. (c) 2012 micha@uxsrv.de
  15. """
  16. import sys
  17. rnd_id = ""
  18. rnd_id += " Beta 22.02 "
  19. import subprocess
  20. rnd_id += subprocess.check_output(['git', 'rev-parse', '--short', 'HEAD']).decode('ascii').strip()
  21. if "__file__" in dir():
  22. sys.stdout.write("\x1b]2;"+str(__file__)+" "+rnd_id+"\x07") # terminal title
  23. else:
  24. sys.stdout.write("\x1b]2;"+str("__file__")+" "+rnd_if+"\x07") # terminal title
  25. __run_main = 0
  26. if __name__ == "__main__":
  27. __run_main = 1
  28. else:
  29. import __main__
  30. print(dir())
  31. if "unittest" not in dir(__main__):
  32. __run_main = 1
  33. import time
  34. import socket
  35. import struct
  36. import sys
  37. import random
  38. import math
  39. from collections import OrderedDict
  40. import lib.zchat as chat
  41. import lib.ArtNetNode as ANN
  42. import _thread as thread
  43. #thread.start_new_thread
  44. import lib.motion as motion
  45. #idmx = [0]*512 # incremental dmx
  46. dmx = [0]*512 # absolute dmx data
  47. gcolor = 1
  48. def cprint(*text,color="blue",space=" ",end="\n"):
  49. #return 0 #disable print dbg
  50. if not gcolor:
  51. print(text)
  52. return 0
  53. if color == "green":
  54. txt = '\033[92m'
  55. elif color == "red":
  56. txt = '\033[0;31m\033[1m'
  57. elif color == "yellow":
  58. txt = '\033[93m\033[1m'
  59. elif color == "cyan":
  60. txt = '\033[96m'
  61. else:
  62. txt = '\033[94m'
  63. for t in text:
  64. txt += str(t ) +" "
  65. #HEADER = '\033[95m'
  66. #OKBLUE = '\033[94m'
  67. #OKCYAN = '\033[96m'
  68. #OKGREEN = '\033[92m'
  69. #WARNING = '\033[93m'
  70. #FAIL = '\033[91m'
  71. #ENDC = '\033[0m'
  72. #BOLD = '\033[1m'
  73. #UNDERLINE = '\033[4m'
  74. txt += '\033[0m'
  75. print(txt,end=end)
  76. #return txt
  77. def artnet_loop():
  78. #artnet = ANN.ArtNetNode(to="127.0.0.1",port=6555,univ=12)
  79. #artnet = ANN.ArtNetNode(to="127.0.0.1",port=6555,univ=0)
  80. artnet = ANN.ArtNetNode(to="10.10.10.255",univ=0)
  81. #artnet = ANN.ArtNetNode(to="2.0.0.255",univ=0)
  82. #artnet = ANN.ArtNetNode(to="10.10.10.255",univ=1)
  83. #dmx[205] = 255 #205 BLUE
  84. artnet.dmx= dmx #[0]*512
  85. artnet.send()
  86. while 1:
  87. #artnet._test_frame()
  88. artnet.next()
  89. time.sleep(0.01)
  90. class Main():
  91. def __init__(self):
  92. #artnet = ANN.ArtNetNode(to="127.0.0.1",port=6555,univ=12)
  93. #artnet = ANN.ArtNetNode(to="127.0.0.1",port=6555,univ=0)
  94. #artnet = ANN.ArtNetNode(to="2.0.0.255",univ=0)
  95. #artnet = ANN.ArtNetNode(to="10.10.10.255",univ=1)
  96. self.artnet = {}
  97. #self.artnet["0"] = ANN.ArtNetNode(to="10.10.10.255",univ=0)
  98. #self.artnet["0"].dmx[512-1] = 10
  99. #self.artnet["1"] = ANN.ArtNetNode(to="10.10.10.255",univ=1)
  100. #self.artnet["1"].dmx[512-1] = 11
  101. self.fx = {} # key is dmx address
  102. def loop(self):
  103. #dmx[205] = 255 #205 BLUE
  104. #self.artnet.send()
  105. xx = [0]*512
  106. #artnet = self.artnet["0"]
  107. #artnet.dmx = xx# [:] #dmx #[0]*512
  108. old_univ = -1
  109. while 1:
  110. t = clock.time()
  111. ii = 0
  112. for ii,dmxch in enumerate(Bdmx):
  113. i = ii%512
  114. univ = ii//512
  115. if str(univ) not in self.artnet:
  116. print("add uiv",univ)
  117. self.artnet[str(univ)] = ANN.ArtNetNode(to="10.10.10.255",univ=univ)
  118. self.artnet[str(univ)].dmx[512-1] = 100+univ
  119. if univ != old_univ:
  120. old_univ = univ
  121. #print("UNIV",ii/512)
  122. try:
  123. artnet.next()
  124. except:pass
  125. artnet = self.artnet[str(univ)]
  126. artnet.dmx = xx
  127. v = dmxch.next(t)
  128. if i == 0:
  129. #print(dmxch)
  130. if int(xx[i]*100) != int( v*100):
  131. #print("----v",x[i],v,t)
  132. pass
  133. #print("i:{:0.2f} xx:{:0.2f} v:{:0.2f} {:0.2f}----v {}".format(i,xx[i],v,t+100,dmxch))
  134. #print("i:{:0.2f} xx:{:0.2f} v:{:0.2f} {:0.2f}----v {}".format(i,xx[i],v,t+100,dmxch))
  135. xx[i] = int(v)
  136. try:
  137. artnet.next()
  138. except:pass
  139. time.sleep(0.01)
  140. main = Main()
  141. if __run_main:
  142. #thread.start_new_thread(artnet_loop,())
  143. thread.start_new_thread(main.loop,())
  144. class CLOCK():
  145. def __init__(self):
  146. self.__time = 0
  147. self.__start = time.time() # only for debugging
  148. self.__tick = 0.01 # incremental timer drift's on highe cpu load ?
  149. def time(self):
  150. return self.__time
  151. def get_drift(self):
  152. run_time = time.time() - self.__start
  153. tick_time = self.__time # * self.__tick
  154. print( "runtime:{:0.2f} tick_timer:{:0.2f} drift:{:0.2f}".format(run_time,tick_time,run_time-tick_time))
  155. def loop(self):
  156. while 1:
  157. self.__time +=self.__tick
  158. #if int(self.__time*100)/10. % 10 == 0:# self.__time % 2 == 0:
  159. # print( self.get_drift())
  160. #print(self.__time)
  161. #for i in range(10):
  162. time.sleep(self.__tick)
  163. class CLOCK_REAL():
  164. def __init__(self):
  165. self.__time = 0
  166. self.__start = time.time() # only for debugging
  167. self.__tick = 0.01 # incremental timer drift's on highe cpu load ?
  168. def time(self):
  169. self.__time = time.time()
  170. return self.__time
  171. def get_drift(self):
  172. run_time = time.time() - self.__start
  173. tick_time = self.__time # * self.__tick
  174. print( "runtime:{:0.2f} tick_timer:{:0.2f} drift:{:0.2f}".format(run_time,tick_time,run_time-tick_time))
  175. def loop(self):
  176. pass
  177. #clock = CLOCK()
  178. clock = CLOCK_REAL()
  179. if __run_main:
  180. thread.start_new_thread(clock.loop,())
  181. class Fade():
  182. def __init__(self,start,target,ftime,clock,delay=0):
  183. #print("init Fade ",start,target,ftime,clock)
  184. if delay < 0:
  185. delay = 0.0001
  186. if ftime <= 0:
  187. ftime = 0.0001
  188. clock += delay
  189. self.__delay = delay
  190. self.__clock = clock
  191. self.__clock_curr = clock
  192. self.__ftime = ftime
  193. self.__start = start
  194. self.__last = start
  195. self.__target = target
  196. self.run = 1
  197. #print("INIT", str(self) )
  198. def __str__(self):
  199. return self.__repr__()
  200. def __repr__(self):
  201. return "<Fade Next:{:0.2f} Start:{:0.2f} Target:{:0.2f} T{:0.2f} Clock:{:0.2f} run:{} delay:{:0.2f}>".format(
  202. self.__last, self.__start,self.__target,self.__ftime,self.__clock_curr,self.run,self.__delay )
  203. def next(self,clock=None):
  204. if self.__ftime <= 0 and self.__delay <= 0:
  205. self.__last = self.__target
  206. self.run = 0
  207. if type(clock) is float or type(clock) is int:#not None:
  208. self.__clock_curr = clock
  209. if self.__target > self.__start:
  210. if self.__last >= self.__target:
  211. self.run = 0
  212. return self.__target
  213. else:
  214. if self.__last <= self.__target:
  215. self.run = 0
  216. return self.__target
  217. current = (self.__clock - self.__clock_curr) / self.__ftime
  218. length = self.__start - self.__target
  219. self.__last = self.__start+ length*current
  220. #if self.__last < 0:
  221. # self.__last = 0
  222. #if self.__last > 255:
  223. # self.__last = 255
  224. self.run = 1
  225. return self.__last
  226. def ctl(self,cmd="",value=None): # if x-fade cmd="%" value=50
  227. # start,stop,fwd,bwd,revers
  228. pass
  229. class _MASTER():
  230. def __init__(self,name="None"):
  231. self.__data = {}
  232. self.name = name
  233. def val(self,name,value=None):
  234. _value = 100 #%
  235. name = str(name)
  236. if name not in self.__data:
  237. self.__data[name] = 100
  238. _value = self.__data[name]
  239. if value is not None:
  240. if _value != value:
  241. print(self.name,"CHANGE MASTER",name,_value)
  242. self.__data[name] = value
  243. _value = self.__data[name]
  244. return _value /100.
  245. class SPEED_MASTER(_MASTER):
  246. def __init__(self):
  247. super().__init__("SPEED")
  248. class SIZE_MASTER(_MASTER):
  249. def __init__(self):
  250. super().__init__("SIZE")
  251. size_master = SIZE_MASTER()
  252. speed_master = SPEED_MASTER()
  253. class MASTER_FX():
  254. def __init__(self):
  255. #cprint(self,"MASTER_FX INIT !",color="green")
  256. self.__data = []
  257. self.__ok = []
  258. self.i=0
  259. self.old_offsets = []
  260. self.offsets = []
  261. self.count = -1
  262. self.init = 10
  263. def add(self,fx):
  264. if fx not in self.__data:
  265. #cprint(self,"ADD TO MASTER !",color="green")
  266. self.__data.append(fx)
  267. info = fx._get_info()
  268. #cprint(self,"ADD" ,info,color="green")
  269. offset = 0
  270. if "offset" in info:
  271. offset = info["offset"]
  272. self.old_offsets.append(offset)
  273. self.offsets.append(offset)
  274. if "xtype" in info:
  275. if info["xtype"] == "rnd":
  276. self._shuffle()
  277. #self.init += 1
  278. def _shuffle(self):
  279. #cprint(self,"REORDER RANDOM !",color="green")
  280. #self.init = 0
  281. #cprint(self.old_offsets)
  282. random.shuffle(self.old_offsets)
  283. #cprint(self.old_offsets)
  284. def _init(self):
  285. self._shuffle()
  286. #self.offsets = []
  287. for i,v in enumerate(self.old_offsets):
  288. offset = self.old_offsets[i]
  289. self.offsets[i] = offset
  290. self.init = 0
  291. def next(self,child):
  292. i = self.__data.index(child)
  293. offset = self.old_offsets[i]
  294. self.offsets[i] = offset
  295. return offset
  296. #for i,v in enumerate(self.old_offsets):
  297. # offset = self.old_offsets[i]
  298. # self.offsets[i] = offset
  299. def get(self,child,count):
  300. offset = 0
  301. if child not in self.__data:
  302. return offset
  303. if self.init:
  304. self._init()
  305. idx = self.__data.index(child)
  306. if (self.count != count and idx == 0 ) or self.init == 0:
  307. self.init = 1
  308. self._shuffle()
  309. #print( count)
  310. self.count=count
  311. idx = self.__data.index(child)
  312. offset = self.offsets[idx]
  313. return offset
  314. class FX():
  315. def __init__(self,xtype="sinus",size=10,speed=10,invert=0,width=100,start=0,offset=0,base="",clock=0,master=None,master_id=1):
  316. self.__xtype=xtype
  317. self.__size = size
  318. self.__start = start
  319. self.__master_id = master_id
  320. if width > 200:
  321. width = 200
  322. if width <= 0:
  323. width = 1
  324. self.__fade_in_master = 0
  325. self.__width = width
  326. self.__invert = invert
  327. self.__base = base
  328. self.__speed = speed
  329. self.__offset = offset
  330. self.__clock = clock
  331. self.__clock_curr = clock
  332. self.__clock_delta = 0
  333. self.__clock_old = self.__clock_curr
  334. self.out = 0
  335. self.old_v = -1
  336. self.run = 1
  337. self.count = -1
  338. self.__angel = self.__clock_curr*360%360
  339. if master is None:
  340. cprint(master, "MASTER_FX ERR",master,color="red")
  341. self.__master = MASTER_FX()
  342. self.__master.add(self)
  343. else:
  344. #cprint( "MASTER_FX OK",master,color="red")
  345. self.__master = master
  346. self.__master.add(self)
  347. if self.__xtype == "rnd":
  348. self.__offset = self.__master.get(self,-2)
  349. self.__offset = self.__master.next(self)#,count)
  350. self.next()
  351. #print("init FX",self)
  352. def _get_info(self):
  353. print(self.__offset)
  354. return {"offset":self.__offset,"xtype":self.__xtype}
  355. #return self.next(),self.__xtype, self.__size,self.__speed,self.__angel, self.__base,self.__clock_curr,self.run
  356. def __str__(self):
  357. return self.__repr__()
  358. def __repr__(self):
  359. return "<FX Next:{:0.2f} xtype:{} Size:{:0.2f} Speed:{:0.2f} ang:{:0.2f} base:{} Clock:{:0.2f} run:{}>".format(
  360. self.next(),self.__xtype, self.__size,self.__speed,self.__angel, self.__base,self.__clock_curr,self.run )
  361. def next(self,clock=None):
  362. if type(clock) is float or type(clock) is int:#not None:
  363. self.__clock_curr = clock
  364. self.__clock_delta += (self.__clock_curr - self.__clock_old) * ( speed_master.val(self.__master_id)-1)
  365. #print(self.__clock_delta )
  366. self.__clock_old = self.__clock_curr
  367. t = self.__clock_curr
  368. t += self.__clock_delta
  369. t *= self.__speed / 60
  370. t += self.__offset / 100 #255 #1024 #255
  371. t += self.__start / 1024 #255
  372. #t = t*speed_master.val(self.__master_id)
  373. tw = t%1
  374. count = t//1
  375. t = t * (100/self.__width)
  376. if tw > self.__width/100:
  377. t = 1
  378. self.__angel = t%1*360
  379. t = t%1
  380. rad = math.radians(self.__angel)
  381. v=0
  382. out = 0
  383. base = 0
  384. size = self.__size
  385. if self.__base == "+": # add
  386. base = size/2
  387. elif self.__base == "-": # sub
  388. base = size/2*-1
  389. if self.__xtype == "sinus":
  390. v = math.sin( rad )
  391. v/=2
  392. elif self.__xtype == "cosinus":
  393. v = math.cos( rad )
  394. if self.__base == "+": # add
  395. size *= -1
  396. v/=2
  397. elif self.__xtype == "rnd":
  398. #base = 0
  399. if self.__angel > 90 and self.__angel <=270:
  400. v=1
  401. else:
  402. v=0
  403. #if count != self.count and v: # % 2 == 0:#!= self.count:
  404. # #self.__offset = random.randint(0,1024)# /1024
  405. # self.__master._shuffle()
  406. if count != self.count and v == 0: # and v: # % 2 == 0:#!= self.count:
  407. self.__master.next(self)#,count)
  408. #self.__master.next(self)#,count)
  409. self.__offset = self.__master.get(self,count)
  410. base = 0
  411. if self.__base == "-": # sub
  412. if self.__invert:
  413. v = 1-v
  414. #base = -size
  415. size *=-1
  416. v *=-1
  417. elif self.__base == "+": # sub
  418. if self.__invert:
  419. v = v-1
  420. else:
  421. v = (t%1-0.5)
  422. elif self.__xtype == "on":
  423. #base = 0
  424. if self.__angel > 90 and self.__angel <=270:
  425. v=1
  426. else:
  427. v=0
  428. base = 0
  429. if self.__base == "-": # sub
  430. if self.__invert:
  431. v = 1-v
  432. #base = -size
  433. size *=-1
  434. v *=-1
  435. elif self.__base == "+": # sub
  436. if self.__invert:
  437. v = v-1
  438. else:
  439. v = (t%1-0.5)
  440. elif self.__xtype == "ramp" or self.__xtype == "ramp":
  441. v = (t%1)
  442. base = 0
  443. if self.__base == "-": # sub
  444. if self.__invert:
  445. v = 1-v
  446. #base = -size
  447. size *=-1
  448. v *=-1
  449. elif self.__base == "+": # sub
  450. if self.__invert:
  451. v = v-1
  452. else:
  453. v = (t%1-0.5)
  454. elif self.__xtype == "ramp2" or self.__xtype == "bump2":
  455. v = (t%1)
  456. v = 1-v
  457. if v == 1:
  458. v=0
  459. base = 0
  460. if self.__base == "-": # sub
  461. if self.__invert:
  462. v = 1-v
  463. #base = -size
  464. size *=-1
  465. v *=-1
  466. elif self.__base == "+": # sub
  467. if self.__invert:
  468. v = v-1
  469. else:
  470. v = (t%1-0.5)
  471. elif self.__xtype == "fade":
  472. x = t * 2
  473. if x > 1:
  474. x = 2-x
  475. x -= 0.5
  476. v = x*2
  477. #base /= 2
  478. #base *=2
  479. if self.__base == "+": # add
  480. pass#base /= 2
  481. else:
  482. v *= -1
  483. v/=2
  484. if self.__invert:
  485. v *=-1
  486. #if self.__fade_in_master < 255:
  487. # self.__fade_in_master += v*size
  488. out = v *size +base
  489. self.out = out
  490. self.count = count
  491. return out * size_master.val(self.__master_id) #* (self.__fade_in_master /255.)
  492. #= master_id
  493. class DMXCH(object):
  494. def __init__(self):
  495. self._base_value = 0
  496. self._fade = None
  497. self._fx = [None,None] # None
  498. self._fx_value = 0
  499. self._flash = None
  500. self._flash_fx = None
  501. self._flash_fx_value = 0
  502. self._last_val = None
  503. def fade(self,target,ftime=0,clock=0,delay=0):
  504. if target != self._base_value:
  505. try:
  506. target = float(target)
  507. self._fade = Fade(self._base_value,target,ftime=ftime,clock=clock,delay=delay)
  508. #self._fade.next()
  509. #self._fade.next()
  510. except Exception as e:
  511. print( "Except:fade",e,target,ftime,clock)
  512. def fx(self,xtype="sinus",size=40,speed=40,invert=0,width=100,start=0,offset=0,base="", clock=0,master=None):
  513. print([self,xtype,size,speed,start,offset,base, clock])
  514. self._fx[0] = self._fx[1]
  515. if str(xtype).lower() == "off":
  516. fx_value = self._fx_value
  517. if fx_value != 0:
  518. cprint("???????______ FX OFF AS FADE",fx_value,0,255)
  519. self._fx[1] = Fade(fx_value,0,ftime=0.5,clock=clock)
  520. else:
  521. self._fx[1] = None
  522. self._fx_value = 0
  523. else:
  524. self._fx[1] = FX(xtype=xtype,size=size,speed=speed,invert=invert,width=width,start=start,offset=offset,base=base,clock=clock,master=master)
  525. def flash(self,target,ftime=0,clock=0,delay=0):
  526. if str(target).lower() == "off":
  527. self._flash = None
  528. else:#elif target != self._base_value:
  529. try:
  530. target = float(target)
  531. self._flash = Fade(self._last_val,target,ftime=ftime,clock=clock,delay=delay)
  532. except Exception as e:
  533. print( "Except:flash",target,ftime,clock,__name__,e,)
  534. def flash_fx(self,xtype="sinus",size=40,speed=40,invert=0,width=100,start=0,offset=0,base="",clock=0,master=None):
  535. #if self._flash_fx is not None :
  536. # cprint("flash_fx",xtype)
  537. if str(xtype).lower() == "off":
  538. fx_value = self._fx_value
  539. #if fx_value != 0:
  540. # cprint("???????______ FX OFF AS FADE",fx_value,0,255)
  541. # self._flash_fx = Fade(fx_value,0,ftime=0.5,clock=clock)#,delay=delay)
  542. # self._flash_fx = None
  543. #else:
  544. # self._flash_fx = None
  545. # self._flash_fx_value = 0
  546. self._flash_fx = None
  547. self._flash_fx_value = 0
  548. else:
  549. self._flash_fx = FX(xtype=xtype,size=size,speed=speed,invert=invert,width=width,start=start,offset=offset,base=base,clock=clock,master=master)
  550. def fx_ctl(self,cmd=""):#start,stop,off
  551. pass
  552. def __str__(self):
  553. return self.__repr__()
  554. def __repr__(self):
  555. return "< DMXCH {:0.2f} > {} {}".format( self._last_val,self._fx,self._fade)
  556. def fade_ctl(self,cmd=""):#start,stop,backw,fwd,bounce
  557. pass
  558. def next(self,clock=0):
  559. value = self._base_value
  560. if self._last_val is None:
  561. self._last_val = value
  562. fx_value = self._fx_value
  563. if self._flash is not None:
  564. value = self._flash.next(clock)
  565. #flicker bug ?!
  566. value = self._flash.next(clock)
  567. fx_value = 0
  568. elif self._fade is not None:#is Fade:# is Fade:
  569. self._base_value = self._fade.next(clock)
  570. #flicker bug ?!
  571. self._base_value = self._fade.next(clock)
  572. value = self._base_value
  573. if self._flash_fx is not None:# is FX:
  574. fx_value = self._flash_fx.next(clock)
  575. else:
  576. self._fx_value = 0
  577. if self._fx[-1] is not None and self._flash is None:# is FX:
  578. self._fx_value += self._fx[-1].next(clock)
  579. #if self._fx[0] is not None and self._flash is None:# is FX:
  580. # self._fx_value += self._fx[0].next(clock)
  581. fx_value = self._fx_value
  582. self._last_val = value + fx_value
  583. return self._last_val
  584. Bdmx = []
  585. for i in range(512*3):
  586. Bdmx.append( DMXCH() )
  587. #print(type(dmx[i]))
  588. def split_cmd(data):
  589. if "cmd" in data:
  590. cmd = data["cmd"]
  591. #print("cmd",cmd)
  592. if "," in cmd:
  593. cmds = cmd.split(",")
  594. else:
  595. cmds = [cmd]
  596. return cmds
  597. import time
  598. import json
  599. import zlib
  600. def JCB(data): #json client input
  601. t_start = time.time()
  602. #jdatas = data["cmd"].split("\x00")
  603. jdatas = [data["cmd"]]
  604. c = clock.time()
  605. c = float(c)
  606. print("JCB",round(c,2))
  607. ftime = 0
  608. delay = 0
  609. for j in jdatas:
  610. master_fx = MASTER_FX()
  611. if not j:
  612. continue
  613. try:
  614. cprint("JCB::")#,j)
  615. jdata = j #jdatas[j]
  616. jtxt = jdata
  617. #jtxt = zlib.decompress(jtxt) #jtxt.decode())
  618. jtxt = str(jtxt,"UTF-8")
  619. cmds = json.loads(jtxt)
  620. for x in cmds:
  621. #cprint(int(clock.time()*1000)/1000,end=" ",color="yellow")#time.time())
  622. #cprint("json", x,type(x),color="yellow")#,cmds[x])
  623. if "CMD" in x:
  624. print("CMD:",x)
  625. if "SPEED-MASTER" == x["CMD"]:
  626. speed_master.val(x["NR"],x["VALUE"])
  627. if "SIZE-MASTER" == x["CMD"]:
  628. size_master.val(x["NR"],x["VALUE"])
  629. else:
  630. if "DMX" in x:
  631. DMX = int(x["DMX"])
  632. else:continue
  633. if DMX > 0:
  634. DMX -=1
  635. else:continue
  636. if "VALUE" in x:# and x["VALUE"] is not None:
  637. v = x["VALUE"]
  638. else:continue
  639. if "FX" in x:# and x["VALUE"] is not None:
  640. fx = x["FX"]
  641. else:fx=""
  642. if "FX2" in x:# and x["VALUE"] is not None:
  643. fx2 = x["FX2"]
  644. else:fx2={}
  645. if "FADE" in x:
  646. ftime = x["FADE"]
  647. else:ftime=0
  648. if "DELAY" in x:
  649. delay = x["DELAY"]
  650. else:delay=0
  651. if len(Bdmx) < DMX:
  652. continue
  653. if v is not None:
  654. if "FLASH" in x:
  655. #print("FLASH")
  656. Bdmx[DMX].flash(target=v,ftime=ftime, clock=c,delay=delay)
  657. else:
  658. #print("FADE")
  659. Bdmx[DMX].fade(target=v,ftime=ftime, clock=c,delay=delay)
  660. if type(fx2) is dict and fx2:
  661. #cprint("FX2",DMX,fx2,color="green")
  662. xtype="fade"
  663. size = 10
  664. speed = 10
  665. start = 0
  666. offset= 0
  667. width=100
  668. invert=0
  669. base = "-"
  670. if "TYPE" in fx2:
  671. xtype = fx2["TYPE"]
  672. if "SIZE" in fx2:
  673. size = fx2["SIZE"]
  674. if "SPEED" in fx2:
  675. speed = fx2["SPEED"]
  676. if "OFFSET" in fx2:
  677. offset = fx2["OFFSET"]
  678. if "BASE" in fx2:
  679. base = fx2["BASE"]
  680. if "INVERT" in fx2:
  681. invert = fx2["INVERT"]
  682. if "WIDTH" in fx2:
  683. width = fx2["WIDTH"]
  684. if "off" == x["VALUE"]: #fix fx flash off
  685. xtype= "off"
  686. if "alloff" == xtype.lower():
  687. for i in Bdmx:
  688. if i is not None:
  689. i.flash_fx(xtype="off",clock=c)
  690. i.fx(xtype="off",clock=c)
  691. if "FLASH" in x:
  692. Bdmx[DMX].flash_fx(xtype=xtype,size=size,speed=speed,invert=invert,width=width,start=start,offset=offset,base=base,clock=c,master=master_fx)
  693. else:
  694. Bdmx[DMX].fx(xtype=xtype,size=size,speed=speed,invert=invert,width=width,start=start,offset=offset,base=base,clock=c,master=master_fx)
  695. elif type(fx) is str and fx: # old fx like sinus:200:12:244
  696. ccm = str(DMX+1)+":"+fx
  697. print("fx",ccm)
  698. if "FLASH" in x:
  699. CB({"cmd":"fxf"+ccm})
  700. else:
  701. CB({"cmd":"fx"+ccm})
  702. cprint("{:0.04} sec.".format(time.time()-t_start),color="yellow")
  703. cprint("{:0.04} t.".format(time.time()),color="yellow")
  704. except Exception as e:
  705. cprint("EXCEPTION JCB",e,color="red")
  706. cprint("----",str(jdata)[:150],"...",color="red")
  707. cprint("Error on line {}".format(sys.exc_info()[-1].tb_lineno),color="red")
  708. cprint()
  709. cprint("{:0.04} sec.".format(time.time()-t_start),color="yellow")
  710. cprint("{:0.04} t.".format(time.time()),color="yellow")
  711. def CB(data): # raw/text client input
  712. #print("CB",data)
  713. cmds = split_cmd(data)
  714. c = clock.time()
  715. c = float(c)
  716. ftime = 0
  717. delay = 0
  718. for xcmd in cmds:
  719. if xcmd:
  720. cprint("CB",xcmd,end=" ")
  721. pass
  722. else:
  723. continue
  724. if xcmd.startswith("fxf"):
  725. xxcmd=xcmd[3:].split(":")
  726. #print("fxf:",xxcmd)
  727. if "alloff" == xxcmd[1].lower():
  728. for i in Bdmx:
  729. if i is not None:
  730. i.flash_fx(xtype="off",clock=c)
  731. l = xxcmd
  732. try:
  733. xtype=""
  734. size=40
  735. speed=100
  736. start=0
  737. offset=0
  738. base=""
  739. k=int(l[0])-1
  740. xtype=l[1]
  741. if len(l) >= 3:
  742. try:size=int(l[2])
  743. except:pass
  744. if len(l) >= 4:
  745. try:speed=int(l[3])
  746. except:pass
  747. if len(l) >= 5:
  748. try:start=int(l[4])
  749. except:pass
  750. if len(l) >= 6:
  751. try:offset=int(l[5])
  752. except:pass
  753. if len(l) >= 7:
  754. try:base=l[6]
  755. except:pass
  756. if len(Bdmx) > k:
  757. #Bdmx[k].fade(target=v,ftime=t, clock=c)
  758. Bdmx[k].flash_fx(xtype=xtype,size=size,speed=speed,start=start,offset=offset,base=base,clock=c)
  759. except Exception as e:
  760. print("EXCEPTION IN FX",e)
  761. print("Error on line {}".format(sys.exc_info()[-1].tb_lineno))
  762. elif xcmd.startswith("fx"):
  763. xxcmd=xcmd[2:].split(":")
  764. print("DMX:",xxcmd)
  765. if len(xxcmd) < 2:
  766. print("xxcmd err",xxcmd,xcmd)
  767. continue
  768. if "alloff" == xxcmd[1].lower():
  769. for i in Bdmx:
  770. i.fx(xtype="off",clock=c)
  771. l = xxcmd
  772. try:
  773. xtype=""
  774. size=40
  775. speed=100
  776. start=0
  777. offset=0
  778. base=""
  779. k=int(l[0])-1
  780. xtype=l[1]
  781. if len(l) >= 3:
  782. try:size=int(l[2])
  783. except:pass
  784. if len(l) >= 4:
  785. try:speed=int(l[3])
  786. except:pass
  787. if len(l) >= 5:
  788. try:start=int(l[4])
  789. except:pass
  790. if len(l) >= 6:
  791. try:offset=int(l[5])
  792. except:pass
  793. if len(l) >= 7:
  794. try:base=l[6]
  795. except:pass
  796. if len(Bdmx) > k:
  797. #Bdmx[k].fade(target=v,ftime=t, clock=c)
  798. Bdmx[k].fx(xtype=xtype,size=size,speed=speed,start=start,offset=offset,base=base,clock=c)
  799. except Exception as e:
  800. print("EXCEPTION IN FX",xcmd,e)
  801. print("Error on line {}".format(sys.exc_info()[-1].tb_lineno))
  802. if __run_main:
  803. #jchat = chat.CMD(CB,port=50001) # server listener
  804. #thread.start_new_thread(jchat.poll,())
  805. chat.cmd(JCB) # server listener
  806. #chat.cmd(JCB,port=50001) # server listener
  807. #input("END")