PDA

View Full Version : Switch from serial card to global cache itach



rickd
January 1st, 2013, 12:59 PM
I have two serial drivers written using device manager handling my receiver and projector. They use two serial ports. I would like to migrate them to global cache itach wifi serial devices which are ip based.

What is the best way to simply use girder ip or transport handling for receive response and handling?

Thanks rick

shaun5
January 1st, 2013, 06:54 PM
Here is a excerpt from my transport that uses a serial port on a global caché device:

Name = 'Lumagen',
Description = [[<b>Lumagen XD Video Processor serial control via Global Cache</b>]],
GUIDefaults = {
allowedtransports = {
[constants.transport.GIP] = true,
},
defaulttransport = constants.transport.GIP,
hostname = "192.168.0.99",
port = 4999,
},

Not much too it...

rickd
January 2nd, 2013, 04:06 AM
Thanks so how do you deal with data being sent from the device ie receive response code is it the same as serial lua?

Do I just replace the serial setup code comport baud and device definition at beginning og my device with this code then leave all tables and data capture tables holding state on all my variables as is?

I also have a provider for each device . When a variable changes I update my settings table and send the event to my provider to update that too foe nr and web etc.


Thanks rick

shaun5
January 3rd, 2013, 07:52 PM
I haven't had to change anything that I can remember going from one to the other. Serial setup is on the global cache web interface.

rickd
January 12th, 2013, 05:28 PM
--[[

JVC Projector Model HD100, HD1, RS1 and RS2 Serial Driver

v1.1
added screen control function 7th January 2009
(c) Rick Dry
C:\Program Files\Promixis\Girder5\plugins\serial\JVCHD100.lua
--]]

require 'Classes.Publisher'

--command header and command types
local command = '21'
local reference = '3F'
local ref_response = '40'
local header = '8901'
local input = '4950'
local power = '5057'
local gammatable = '4754'
local gammacoeff = '4750'
local remote = '5243'


local device = serial.Classes.Queued:New({

Name = "JVC HD100 Projector",
Description = "JVC HD100",

BaudRate = 19200,
Parity = 0,
--StartBits = 0,
StopBits = 0,
DataBits = 8,
FlowControl = 'N',
IntraCharacterDelay = 0,
CallbackType = serial.CB_TERMINATED,
--SendStartByte = '',
SendTerminator = serial.hextobyte ('0A'),
ReceiveStartByte = serial.hextobyte ('06'),
ReceiveTerminator = serial.hextobyte ('0A'),
IncompleteResponseTimeout = 200,
NoResponseTimeout = 200,
LogLevel = 0,
GlobalName = 'JVCProjector',


Initialize = function (self)
self.Publisher = Classes.Publisher:New()
self.Provider = DeviceManager and DeviceManager.Providers.Start('JVCHD100Provider')
gir.LogMessage(self.Name, 'Communications OK',3)
self.Status = "Communication OK"
return serial.Classes.Queued.Initialize (self)
end,

Event = function(self, ...)
self.Publisher:Event(unpack(arg))
-- print(unpack(arg))
gir.LogMessage(self.Name, table.concat(arg, ' '), 3)
end,

Subscribe = function(self, func)
return self.Publisher:Subscribe(func)
end,

Unsubscribe = function(self, func)
self.Publisher:Unsubscribe(func)
end,

SendCommand = function (self,command,callback,topofque,force)
return serial.Classes.Queued.SendCommand (self,command,callback,topofque,force)
end,




ReceiveResponse = function ( self, data, code )

if (math.band (code,serial.RXCHAR) > 0) and data then
print ('Length: '..string.len(data))

if string.len(data)==5 then
local _, _, ack, id, cmdtype = string.find(data, '(.)(..)(..)')
local ackx = string.byte(ack)
local ackbyte = string.format('%02x',ackx)
local ackn=tonumber(ackbyte)
if ackn==6 then
print ('JVC Command Acknowledged : '..cmdtype)
gir.LogMessage(self.Name, cmdtype..':JVC Command Acknowledged',3)
if JVCcommandsent == "PowerOff" and cmdtype == "PW" then
--acknowledgement of command triggers update to provider by checking last command sent and acknowleged command
self:Event('Power','Off')
JVCpower=0
elseif JVCcommandsent == "PowerOn" and cmdtype == "PW" then
self:Event('Power','On')
JVCpower=1
elseif JVCcommandsent == "InputSVideo" and cmdtype == "IP" then
self:Event('Source','SVideo')
--consider put in the JVCinput
elseif JVCcommandsent == "InputVideo" and cmdtype == "IP" then
self:Event('Source','Video')
elseif JVCcommandsent == "InputComponent" and cmdtype == "IP" then
self:Event('Source','Component')
elseif JVCcommandsent == "InputHDMI1" and cmdtype == "IP" then
self:Event('Source','HDMI1')
elseif JVCcommandsent == "InputHDMI2" and cmdtype == "IP" then
self:Event('Source','HDMI2')

elseif JVCcommandsent == "GammaNormal" and cmdtype == "GT" then
self:Event('Gamma','Normal')
elseif JVCcommandsent == "GammaTheater1" and cmdtype == "GT" then
self:Event('Gamma','Theater1')
elseif JVCcommandsent == "GammaTheater2" and cmdtype == "GT" then
self:Event('Gamma','Theater2')
elseif JVCcommandsent == "GammaDynamic" and cmdtype == "GT" then
self:Event('Gamma','Dynamic')
elseif JVCcommandsent == "GammaCustom" and cmdtype == "GT" then
self:Event('Gamma','Custom')

elseif JVCcommandsent == "GammaCoeff_1.8" and cmdtype == "GP" then
self:Event('Coeff','1_8')
elseif JVCcommandsent == "GammaCoeff_1.9" and cmdtype == "GP" then
self:Event('Coeff','1_9')
elseif JVCcommandsent == "GammaCoeff_2.0" and cmdtype == "GP" then
self:Event('Coeff','2_0')
elseif JVCcommandsent == "GammaCoeff_2.1" and cmdtype == "GP" then
self:Event('Coeff','2_1')
elseif JVCcommandsent == "GammaCoeff_2.2" and cmdtype == "GP" then
self:Event('Coeff','2_2')
elseif JVCcommandsent == "GammaCoeff_2.3" and cmdtype == "GP" then
self:Event('Coeff','2_3')
elseif JVCcommandsent == "GammaCoeff_2.4" and cmdtype == "GP" then
self:Event('Coeff','2_4')
elseif JVCcommandsent == "GammaCoeff_2.5" and cmdtype == "GP" then
self:Event('Coeff','2_5')
elseif JVCcommandsent == "GammaCoeff_2.6" and cmdtype == "GP" then
self:Event('Coeff','2_6')
end
end
elseif string.len(data)==6 then
local _, _, cmd, id, query, state = string.find(data, '(.)(..)(..)(.)')
print ('State requested & returned : cmd'..cmd, 'query '..query,'state '..state)
local cmdx = string.byte(cmd)
local cmdbyte = string.format('%02x',cmdx)
print (cmdbyte)
print (state)

if cmd=="@" and query == "PW" then
JVCpower = tonumber(state)
print(state..' :JVC Read Power Processed'..tonumber(JVCpower))
gir.LogMessage(self.Name, ':JVC Read Power Processed',3)
if JVCpower==0 then self:Event('Power','Off')
elseif JVCpower==1 then self:Event('Power','On')
--elseif JVCpower==2 then self:Event('Power','Cool')
--elseif JVCpower==4 then self:Event('Power','Warning')
end
if GetStateAll==1 then self:QueryRest() end --query all was requested and if power is on it will execute and update variables and provider

elseif cmd=="@" and query == "IP" then
JVCinput = tonumber(state)
print(state..' :JVC Read Input Status Processed'..tonumber(JVCinput))
gir.LogMessage(self.Name, ':JVC Read Input State Processed',3)
if JVCinput==0 then self:Event('Source','SVideo')
elseif JVCinput==1 then self:Event('Source','Video')
elseif JVCinput==2 then self:Event('Source','Component')
elseif JVCinput==6 then self:Event('Source','HDMI1')
elseif JVCinput==7 then self:Event('Source','HDMI2')
end

elseif cmd=="@" and query == "GT" then
JVCgamma = tonumber(state)
print(state..' :JVC Read Gamma Status Processed'..tonumber(JVCgamma))
gir.LogMessage(self.Name, ':JVC Read Gamma State Processed',3)
if JVCgamma==0 then self:Event('Gamma','Normal') --publish state back to provider
elseif JVCgamma==1 then self:Event('Gamma','Theater1')
elseif JVCgamma==2 then self:Event('Gamma','Theater2')
elseif JVCgamma==3 then self:Event('Gamma','Dynamic')
elseif JVCgamma==4 then self:Event('Gamma','Custom')
end

elseif cmd=="@" and query == "GP" then
JVCgammacoeff = tonumber(state)
print(state..' :JVC Read Gamma Status Processed'..tonumber(JVCgammacoeff))
gir.LogMessage(self.Name, ':JVC Read GammaCoeff State Processed',3)
if JVCgammacoeff==0 then self:Event('Coeff','1_8')
elseif JVCgammacoeff==1 then self:Event('Coeff','1_9')
elseif JVCgammacoeff==2 then self:Event('Coeff','2_0')
elseif JVCgammacoeff==3 then self:Event('Coeff','2_1')
elseif JVCgammacoeff==4 then self:Event('Coeff','2_2')
elseif JVCgammacoeff==5 then self:Event('Coeff','2_3')
elseif JVCgammacoeff==6 then self:Event('Coeff','2_4')
elseif JVCgammacoeff==7 then self:Event('Coeff','2_5')
elseif JVCgammacoeff==8 then self:Event('Coeff','2_6')
end
end
end
end


if math.band (code,serial.ERR) > 0 then
gir.LogMessage(self.Name, 'Communcication Error',3)
--print ('JVC Error')
end

if math.band (code, serial.NORESPONSETIMEOUT) > 0 then
code = serial.zerobits (code,serial.NORESPONSETIMEOUT)
end -- tells G4 not to report communication errors\timeouts in the Lua Console

serial.Classes.Queued.ReceiveResponse (self,data,code)

end,

--command structure is Command type..Unit ID..Command Type..Data

SendHex = function(self, bytes)
local temp = string.gsub(bytes, '%s', '') -- strip out any spaces
temp = math.hextobyte(temp)
self:SendCommand(temp)
end,

Check = function (self)
return self:SendHex ('21 89 01 00 00')
end,


---------------------------------------------------------------------------------------------------------------------
--Power
---------------------------------------------------------------------------------------------------------------------


PowerOff = function (self)
JVCcommandsent = "PowerOff"
JVCProjector:Screen("allup")
return self:SendHex (command..header..power..'30')
--Screen command insert here

end,

PowerOn = function (self)
JVCcommandsent = "PowerOn"
JVCProjector:Screen("down")
return self:SendHex (command..header..power..'31')
--screen command insert here

end,

eg how do you send hex and handle callbacks and deal with publishing events and receive response etc is it not all different? c sample of my serial device above

perhaps you can show me your code for doing all this

thanks Rick

rickd
January 21st, 2013, 09:30 PM
Any chance I can get your full lumagen as an. Example thanks rick

shaun5
January 31st, 2013, 07:10 PM
Rickd: I ment to get back to you sooner. Attached is my serial transport for a Lumagen video processor. Let me know if it helps or you have more questions...

rickd
February 3rd, 2013, 04:55 PM
Thanks that looks like a good start for me to try some stuff out. I note you don't have any command function for send input changes ...I assume you maust do that inside girder scripts when needed do you have and example of a input change code sent and assuming this is send the lumagen is responding with a confirmation which then is captured by your receive data code and published accordingly.


Also would this work ok for receive data


OnReceiveData = function(self, Event)

local JVC_data = Event:GetData()
print ('Length: '..string.len(JVC_data))

if string.len(JVC_data)==5 then
local _, _, ack, id, cmdtype = string.find(JVC_data, '(.)(..)(..)')
local ackx = string.byte(ack)
local ackbyte = string.format('%02x',ackx)
local ackn=tonumber(ackbyte)
if ackn==6 then
print ('JVC Command Acknowledged : '..cmdtype)
gir.LogMessage(self.Name, cmdtype..':JVC Command Acknowledged',3)
if JVCcommandsent == "PowerOff" and cmdtype == "PW" then
--acknowledgement of command triggers update to provider by checking last command sent and acknowleged command
self:Event('Power','Off')
JVCpower=0
elseif JVCcommandsent == "PowerOn" and cmdtype == "PW" then
self:Event('Power','On')
JVCpower=1
end
end
end
end,

Thanks

shaun5
February 3rd, 2013, 06:51 PM
I keep all my commands (for all devices) in a SQLite database. Using a database allows easier management and allows the listing of all available commands. If 'pld1' is 0 the actual command is in 'pld2', otherwise the command is looked up using 'pld1'. Here is my script action I use to send commands:

if (pld1 ~= '' or pld2 ~= '') then
local txManager = ComponentManager:GetComponentUsingName('Transport Manager')
local tp = txManager:GetTransportUsingName('My Lumagen')
if (pld1 ~= '0') then
require 'luasqlsqlite3';
local env = luasql.sqlite3();
local con = assert( env:connect("C:\\Program Files\\Promixis\\Girder5\\luascript\\transport\\de vices\\globalcache.db"))
local cur = assert (con:execute(string.format([[SELECT command from lumagen WHERE id=%s]], pld1)))
local row = cur:fetch ({},"a")
tp:Send(row.command)
cur:close()
con:close()
env:close()
else
tp:Send(pld2);
end
end

rickd
February 3rd, 2013, 07:59 PM
oh that is nice looks cool but probably a bit more complex for right now....so
tp:Send('pwon') would this work to directly hardcode a power command for example

pld1 and 2 are usually payload from events is that what is happening here can you explain that further

Also does my code look ok for receivedata

Thanks

shaun5
February 3rd, 2013, 08:20 PM
You need two additional lines with the send line (and to modify the transport name to yours) :

local txManager = ComponentManager:GetComponentUsingName('Transport Manager')
local tp = txManager:GetTransportUsingName('My Lumagen')

I control my system through a web interface. The payload variables are defined primarily within the javascript button definition, but I can also trigger events within a lua script action just as easy (there is a a second way I trigger commands, but I am phasing it out).

Are there issues with your receive data code?