Synchronize switches with xplane not working
Re: Synchronize switches with xplane not working
I hear you but this is a specific application. Another application will require different code. The combining of different API functions to achieve a certain outcome is certainly something that could do with a repository of useful functions. We did start a useful community functions library a while back so perhaps we could add this to it. I’ll dig out that thread and ask if anyone has any further examples they would like to see added.
Air Manager panels at https://www.experimentalsimavionics.com
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Re: Synchronize switches with xplane not working
Appreciated Tony.Sling wrote: ↑Sun Apr 11, 2021 11:00 am I hear you but this is a specific application. Another application will require different code. The combining of different API functions to achieve a certain outcome is certainly something that could do with a repository of useful functions. We did start a useful community functions library a while back so perhaps we could add this to it. I’ll dig out that thread and ask if anyone has any further examples they would like to see added.
I still appear to have come across a couple of potential 'bugs' - however, until and unless I explore all possibilites - AND get more experienced with AM AND Lua - then I have to consider all issues as being at my end. (apart from the obvious 'problem between chair and keyboard' errors) ..
100% on the library or repository - definitely needed inho. I can certainly offer what I can and learn a hell of a lot from others.
Joe
Joe. CISSP, MSc.
Re: Synchronize switches with xplane not working
Sling wrote: ↑Sat Apr 10, 2021 4:06 pm @xplanearg Let me explain. First up what you have come up with will work but it has flaws in that you are sharing the same callback for the switch and the subscribe. The switch callback and subscribe callback can and often do have different arguments that are given to the callback to perform its function. In this case you have stumbled across a working solution because you are only using a single argument for each and it happens to be the valid data for both sources.
Let me show the conventional way to do this as per my instructions.
Create a variable to store the hardware switch position at the head of your code and initialise it with the hardware switch position. You can get the position by using the hw_switch_get_position() function.
I made a little error here. It should go after the switch add because it can’t get the position until the switch has been added. See below.
Update this variable with the switch position in the switch callback.Subscribe to the dataref that relates to the switch in question and in the callback compare the subscribed data (sim switch position) to the previously stored hardware switch position. If they are different call the switch callback with the correct position data as the argument.Code: Select all
function switch_49_callback(position) if position == 0 then xpl_command("sim/lights/landing_lights_off") else xpl_command("sim/lights/landing_lights_on") end hw_sw_pos = position —update hw switch position var end switch_49_id = hw_switch_add("ARDUINO_MEGA2560_A_D49", switch_49_callback) local hw_sw_pos = hw_switch_get_position(switch_49_id) —this is the var create and initialise
Like I said at the start, your code will work but for the reasons given this is the more conventional method.Code: Select all
function subscribe_callback(pos) —if sim switch position does not match the hardware switch position then —call the switch callback to send the correct command to the sim If pos ~= hw_sw_pos then switch_49_callback{hw_sw_pos) end end xpl_dataref_subscribe("sim/cockpit2/switches/landing_lights_on", "INT", subscribe_callback)
Hopefully this explains how to do it and what is happening in each step. A slightly different method would not use a variable to store the hw switch position but just use the hw_switch_get_position() function within the subscribe callback to get the hw switch position just before doing the comparison.
I hope this helps.
Tony
Hi Tony, thanks for your answer, however your solution does not work.
when you move the switch the code automatically writes down the value to zero. It goes on briefly and then off again. So its impossible to turn on the switch.
Ive tried to fix your code, however i think airmanager is fundamentally flawed.
The problem with initial synchronization is still there after i fixed your code, the same happens with my 'solution' previously proposed. Both solutions don't work properly with initial synchronization.
Code: Select all
function switch_36_callback(position)
local position = hw_switch_get_position(switch_36_id)
print("The battery switch got changed to position " .. position)
if position == 0 then
xpl_command("sim/electrical/battery_1_off")
xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_dn") -- c90 laminar
elseif position == 1 then
xpl_command("sim/electrical/battery_1_on")
xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_up") -- c90 laminar
end
end
switch_36_id = hw_switch_add("ARDUINO_MEGA2560_A_D36", switch_36_callback)
xpl_dataref_subscribe("sim/cockpit2/electrical/battery_on", "INT[8]", switch_36_callback)
There is no 'While true loop' or continues loop that runs the lua code. It is event driven, only runs when something changes.
Im surprised and disappointed that something so simple like a switch, something basic for any cockpit builder is so hard to configure properly in air manager. I cant believe im the first person with this issue.
the way i got around this, and im still testing it is like so:
Code: Select all
function switch_36_callback(position)
local position = hw_switch_get_position(switch_36_id)
print("The battery switch got changed to position " .. position)
if position == 0 then
xpl_command("sim/electrical/battery_1_off")
xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_dn") -- c90 laminar
elseif position == 1 then
xpl_command("sim/electrical/battery_1_on")
xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_up") -- c90 laminar
end
end
switch_36_id = hw_switch_add("ARDUINO_MEGA2560_A_D36", switch_36_callback)
xpl_dataref_subscribe("sim/time/total_running_time_sec", "FLOAT", switch_36_callback)
this dataref increments itself every second, so this forces the call of the callback every second.
Effectively im transforming this event driven callback into a continuous while true loop.
I hope this addresses the issue and can move on to building other parts of the sim
Re: Synchronize switches with xplane not working
There is no fundamental flaw. I have switch sync working very well with lots of my panels.
I’m not at my sim pc right now so let me take a look when I’m home. It will likely be something trivial.
Tony
ps. I must stress again. My code does not use the same callback for both the switch and the subscribe. There are no examples AFAIK showing them combined so why do you persist with this?
Also forcing the callback to fire every second is simply not required and means code will be unnecessarily run. Not the best for optimal performance.
I’m not at my sim pc right now so let me take a look when I’m home. It will likely be something trivial.
Tony
ps. I must stress again. My code does not use the same callback for both the switch and the subscribe. There are no examples AFAIK showing them combined so why do you persist with this?
Also forcing the callback to fire every second is simply not required and means code will be unnecessarily run. Not the best for optimal performance.
Air Manager panels at https://www.experimentalsimavionics.com
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Re: Synchronize switches with xplane not working
Hi,
To be honest, your code seems flawed
Doing a xpl_subscribe using the same switch callback means that the INT[] will be placed in the position argument of the switch_36_callback function.
This is probably not what you want to happen.
You can use the timer if you want to simulate a loop:
Corjan
To be honest, your code seems flawed
Doing a xpl_subscribe using the same switch callback means that the INT[] will be placed in the position argument of the switch_36_callback function.
This is probably not what you want to happen.
You can use the timer if you want to simulate a loop:
Code: Select all
function switch_36_callback(position)
-- Ignore
end
switch_36_id = hw_switch_add("ARDUINO_MEGA2560_A_D36", function()
-- ignore events from switch
end)
-- Called every 100ms
timer_start(0, 100, function()
local position = hw_switch_get_position(switch_36_id)
print("The battery switch got changed to position " .. position)
if position == 0 then
xpl_command("sim/electrical/battery_1_off")
xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_dn") -- c90 laminar
elseif position == 1 then
xpl_command("sim/electrical/battery_1_on")
xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_up") -- c90 laminar
end
end)
Corjan
Re: Synchronize switches with xplane not working
@xplanearg
As i suspected it was a couple of small issues. The first was a typo that would of reported an error the second was just the variable declaration. All fixed below.
As i suspected it was a couple of small issues. The first was a typo that would of reported an error the second was just the variable declaration. All fixed below.
Code: Select all
local hw_sw_pos
function switch_49_callback(position)
if position == 0 then
xpl_command("sim/lights/landing_lights_off")
else
xpl_command("sim/lights/landing_lights_on")
end
hw_sw_pos = position --update hw switch position var
end
switch_49_id = hw_switch_add("ARDUINO_MEGA2560_A_D49", switch_49_callback)
hw_sw_pos = hw_switch_get_position(switch_49_id) --this is the var create and initialise
function subscribe_callback(pos)
--f sim switch position does not match the hardware switch position then
--call the switch callback to send the correct command to the sim
if pos ~= hw_sw_pos then
switch_49_callback(hw_sw_pos)
end
end
xpl_dataref_subscribe("sim/cockpit2/switches/landing_lights_on", "INT", subscribe_callback)
Air Manager panels at https://www.experimentalsimavionics.com
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Re: Synchronize switches with xplane not working
I did further testing with this method, and although it works when applied to multiple switches, air manager fundamentally slows down. Now i have a 1 second delay from the moment i press a button to the actual action happeningxplanearg wrote: ↑Tue Apr 13, 2021 8:32 pm
the way i got around this, and im still testing it is like so:
Instead of subscribing to the corresponding dataref, (battery state dataref in this case) im subscribing to the 'sim/time/total_running_time_sec' dataref.Code: Select all
function switch_36_callback(position) local position = hw_switch_get_position(switch_36_id) print("The battery switch got changed to position " .. position) if position == 0 then xpl_command("sim/electrical/battery_1_off") xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_dn") -- c90 laminar elseif position == 1 then xpl_command("sim/electrical/battery_1_on") xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_up") -- c90 laminar end end switch_36_id = hw_switch_add("ARDUINO_MEGA2560_A_D36", switch_36_callback) xpl_dataref_subscribe("sim/time/total_running_time_sec", "FLOAT", switch_36_callback)
this dataref increments itself every second, so this forces the call of the callback every second.
Effectively im transforming this event driven callback into a continuous while true loop.
I hope this addresses the issue and can move on to building other parts of the sim
Re: Synchronize switches with xplane not working
Is this the recommended way to have a switch in airmanager? so far ive been proposed several options, non of those work properly. What is the recommended way?Corjan wrote: ↑Wed Apr 14, 2021 7:15 am Hi,
To be honest, your code seems flawed
Doing a xpl_subscribe using the same switch callback means that the INT[] will be placed in the position argument of the switch_36_callback function.
This is probably not what you want to happen.
You can use the timer if you want to simulate a loop:Code: Select all
function switch_36_callback(position) -- Ignore end switch_36_id = hw_switch_add("ARDUINO_MEGA2560_A_D36", function() -- ignore events from switch end) -- Called every 100ms timer_start(0, 100, function() local position = hw_switch_get_position(switch_36_id) print("The battery switch got changed to position " .. position) if position == 0 then xpl_command("sim/electrical/battery_1_off") xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_dn") -- c90 laminar elseif position == 1 then xpl_command("sim/electrical/battery_1_on") xpl_command("laminar/c90/fltctrl/switch/elev_trim_control_up") -- c90 laminar end end)
Corjan
if i do this timer for many switches, will airmanager slow down?
thanks.
Re: Synchronize switches with xplane not working
Thanks for your code, i suppose this is what you run in your sim and works? i will test this shortly.Sling wrote: ↑Wed Apr 14, 2021 8:37 am @xplanearg
As i suspected it was a couple of small issues. The first was a typo that would of reported an error the second was just the variable declaration. All fixed below.
Code: Select all
local hw_sw_pos function switch_49_callback(position) if position == 0 then xpl_command("sim/lights/landing_lights_off") else xpl_command("sim/lights/landing_lights_on") end hw_sw_pos = position --update hw switch position var end switch_49_id = hw_switch_add("ARDUINO_MEGA2560_A_D49", switch_49_callback) hw_sw_pos = hw_switch_get_position(switch_49_id) --this is the var create and initialise function subscribe_callback(pos) --f sim switch position does not match the hardware switch position then --call the switch callback to send the correct command to the sim if pos ~= hw_sw_pos then switch_49_callback(hw_sw_pos) end end xpl_dataref_subscribe("sim/cockpit2/switches/landing_lights_on", "INT", subscribe_callback)
cheers.
Re: Synchronize switches with xplane not working
Yes it is tested working code.
Air Manager panels at https://www.experimentalsimavionics.com
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D
Youtube Channel https://www.youtube.com/channel/UC8ZqXX ... kfZMq5BKig
Air Manager API Tutorial Video Series https://youtube.com/playlist?list=PLNr0 ... baT4gJKg5D