Posts: 19
Threads: 8
Joined: Mar 2020
Reputation:
0
I'm trying to modify the DMX sample my goal would be to create a set method where I have a parameter for the transition time.
I could use dmxhandler.channels in the resident script and manipulate the target and ticks value, but I don't like this idea.
I would be nicer to have a function within the user.dmx.
What I don't understand is how the data from storage.exec('lset', key, chan - 1, val) gets processed to land in the self.channels, so that I can modify it to pass not only the target value but also a transition time?
Thank's
Christian
Posts: 8110
Threads: 43
Joined: Jun 2015
Reputation:
471
Try this, untested so might not work
Use
DMX.settransition to set value and transition time for a given channel.
Code:
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 182 183 184 185 186 187 188 189 190 191 192 193
local luadmx =
require (
'luadmx' )
module (
'DMX' ,
package.seeall )
local DMX = {}
local defaults = {
skey =
'dmx_line_1' ,
port =
'/dev/RS485' ,
resolution =
20 ,
channels =
3 ,
transition =
2 ,
}
local tsuffix =
'_transition'
local function range (
val ,
min ,
max )
return min <=
val and val <=
max
end
function set (
chan ,
val ,
skey )
skey =
skey or defaults.skey
chan =
tonumber (
chan )
or 0
val =
tonumber (
val )
or -
1
if range (
chan ,
1 ,
512 )
and range (
val ,
0 ,
255 )
then
storage.exec (
'lset' ,
skey ,
chan -
1 ,
val )
end
end
function settransition (
chan ,
val ,
tr ,
skey )
local tkey
skey =
skey or defaults.skey
chan =
tonumber (
chan )
or 0
val =
tonumber (
val )
or -
1
tr =
tonumber (
val )
or -
1
if range (
chan ,
1 ,
512 )
and range (
val ,
0 ,
255 )
and range (
tr ,
0 ,
255 )
then
tkey =
skey ..
tsuffix
storage.exec (
'lset' ,
skey ,
chan -
1 ,
val )
storage.exec (
'lset' ,
tkey ,
chan -
1 ,
tr )
end
end
function get (
chan ,
skey )
local res ,
val
skey =
skey or defaults.skey
chan =
tonumber (
chan )
or 0
if chan >=
1 and chan <=
512 then
res =
storage.exec (
'lrange' ,
skey ,
chan -
1 ,
chan -
1 )
if type (
res ) ==
'table' then
val =
tonumber (
res [
1 ])
end
end
return val
end
function init (
params )
local n ,
k ,
v ,
_
n =
setmetatable ({}, {
__index =
DMX })
n.params =
params or {}
_ ,
n.conn =
pcall (
require (
'redis' ).
connect )
for k ,
v in pairs (
defaults )
do
if n.params [
k ] ==
nil then
n.params [
k ] =
v
end
end
n :
reset ()
return n
end
function DMX :
reset ()
local params ,
skey ,
tkey ,
transition ,
err
params =
self.params
skey =
params.skey
tkey =
skey ..
tsuffix
transition =
params.transition
self.dm ,
err =
luadmx.open (
params.port )
if err then
os.sleep (
1 )
error (
err )
end
self.dm :
setcount (
params.channels )
self.sleep =
1 /
params.resolution
self.channels = {}
self.conn :
ltrim (
skey ,
1 ,
0 )
self.conn :
ltrim (
tkey ,
1 ,
0 )
for chan =
1 ,
params.channels do
self.channels [
chan ] = {
current =
0 ,
target =
0 ,
ticks =
0 }
self.conn :
lpush (
skey ,
0 )
self.conn :
lpush (
tkey ,
transition )
self.dm :
setchannel (
chan ,
0 )
end
end
function DMX :
getvalues ()
local skey ,
tkey ,
max ,
channels ,
values ,
transition ,
val ,
tr ,
ticks
skey =
self.params.skey
tkey =
skey ..
tsuffix
max =
self.params.channels
channels =
self.channels
values =
self.conn :
lrange (
skey ,
0 ,
max -
1 )
or {}
transitions =
self.conn :
lrange (
tkey ,
0 ,
max -
1 )
or {}
for chan =
1 ,
max do
val =
tonumber (
values [
chan ])
or 0
tr =
tonumber (
transitions [
chan ])
or 0
ticks =
math.max (
1 ,
tr *
self.params.resolution )
if val ~=
channels [
chan ].
target then
channels [
chan ].
target =
val
channels [
chan ].
delta = (
channels [
chan ].
target -
channels [
chan ].
current ) /
ticks
channels [
chan ].
ticks =
ticks
end
end
end
function DMX :
run ()
self :
getvalues ()
for i =
1 ,
self.params.resolution do
self :
step ()
self.dm :
send ()
os.sleep (
self.sleep )
end
end
function DMX :
step ()
local chan ,
channels ,
t
channels =
self.channels
for chan =
1 ,
self.params.channels do
t =
channels [
chan ].
ticks
if t >
0 then
t =
t -
1
channels [
chan ].
current =
channels [
chan ].
target -
channels [
chan ].
delta *
t
channels [
chan ].
ticks =
t
self.dm :
setchannel (
chan ,
channels [
chan ].
current )
end
end
end
Posts: 19
Threads: 8
Joined: Mar 2020
Reputation:
0
Thanks a lot, sems to work.
Line 150 should be: ticks = math.max(1, tr * self.params.resolution)