Jump to content
The simFlight Network Forums
pilotjohn

PMDG JetStream 4100 (JS41/J41) Saitek Multi-Panel Lua

Recommended Posts

EDIT: Latest version (1.2.1) attached as of 12/6/2011

Here's a Lua script that makes the Saitek Multi-Panel via SPAD (default config) work with the JS41. Some minor inconveniences/notes:

1. HDG light may come one when HDG is not ON on the panel (AP ON and no LNAV selected, or sometimes when VS selected)

2. ALT light comes on when VS or IAS is selected whether ALT/ALTSEL is ON on the panel or not

3. ALT switch toggles ALTSEL mode not ALT

4. If no mode is selected when AP turned ON, heading may drift

5. Eliminates a bug in the AP where switching from IAS to VS sets VS to -9900 FPM

Rename attached .txt to .lua.

JS41SaitekMP.txt

Share this post


Link to post
Share on other sites

Rename attached .txt to .lua.

I'm afraid the attachment never happened. If you have difficulties making an attachment you can just include the file as text in the message, and tell folks to "save it as ...". Enclose it in "code" tags (the <> button above the edit area) to retain formatting.

Regards

Pete

Share this post


Link to post
Share on other sites

I'm afraid the attachment never happened. If you have difficulties making an attachment you can just include the file as text in the message, and tell folks to "save it as ...". Enclose it in "code" tags (the <> button above the edit area) to retain formatting.

Attached... I forgot to press the "Attach files" button.

JS41SaitekMP.txt

Share this post


Link to post
Share on other sites

Attached... I forgot to press the "Attach files" button.

Here it is inline as well...


-- PMDG JetStream 4100 Saitek Multi-Panel Synchronizer 1.0.0
-- E-mail: pilotjohn at gearsdown.com
--
-- Synchronizes the JS41 autopilot functionality with the default FSX
-- behavior. This allows standard FSX compatible equipment (Saitek Multi-Panel)
-- to be used for some, if not most, auto-pilot functions.
-- Developed along SPAD, untested otherwise.
-- Setup:
--
-- 1. Edit "FSUIPC.ini" and add (substitute X for 1 or next # if exists):
--     [General]
--     ShortAircraftNameOk=Substring
--     [Auto.JetStream]
--     X=Lua JS41SaitekMP

--------------------------------------------------------------------------------
-- Helpers

meters2feet = 100/2.54/12
feet2meters = 12*2.54/100

--------------------------------------------------------------------------------
-- Callbacks

local lalt=-1
local latm=-1
function altitude_set(ofs, val)
	local nalt = math.floor(val*meters2feet/65536 + 0.5)
	if (lalt == nalt) then -- eliminate double calls
		return
	elseif (lalt &gt;= 0 and math.abs(lalt - nalt) &gt; 10000) then -- if VS is pressed altitude is set 60000, ignore and reset
		ipc.writeUD(0x07D4, math.floor(lalt*feet2meters*65536 + 0.5))
		return
	else
		lalt = nalt
	end
	local jalt = ipc.readLvar("AltSelAlt")
	local diff = math.abs(nalt - jalt) / 100

	ipc.writeLvar("IrcAltSelKnob", 1)
	if (jalt &lt; nalt) then
		for i=1,diff do
			ipc.control(66587, 3921)
		end
	elseif (nalt &lt; jalt) then
		for i=1,diff do
			ipc.control(66587, 3920)
		end
	end
	ipc.control(66587, 8031)

	latm = ipc.elapsedtime()
end

local lspd = -1
local lstm = -1
function airspeed_set(ofs, val)
	local nspd = val
	if (lspd == nspd) then -- eliminate double calls
		return
	else
		lspd = nspd
	end
	local jspd = ipc.readLvar("VSIASTarget")
	if (jspd &lt; 0) then
		ipc.writeUW(0x07E2, 0)

		return
	end
	local diff = math.abs(nspd - jspd)

	if (jspd &lt; nspd) then
		for i=1,diff do
			ipc.control(66587, 1500)
		end
	elseif (nspd &lt; jspd) then
		for i=1,diff do
			ipc.control(66587, 1501)
		end
	end
	ipc.control(66587, 8031)

	lstm = ipc.elapsedtime()
end

local lhdg = -1
local lhtm = -1
function heading_set(ofs, val)
	local nhdg = math.floor(val*360/65536 + 0.5)
	if (lhdg == nhdg) then -- eliminate double calls
		return
	else
		lhdg = nhdg
	end
	local jhdg = ipc.readLvar("HDGBug")
	local diff = math.abs(nhdg - jhdg)

	if (jhdg &lt; nhdg) then
		for i=1,diff do
			ipc.control(66587, 26902)
		end
	elseif (nhdg &lt; jhdg) then
		for i=1,diff do
			ipc.control(66587, 26901)
		end
	end
	ipc.control(66587, 8031)

	lhtm = ipc.elapsedtime()
end

function apm_toggle(ctrl, param)
	ipc.writeLvar("L:APEngageSwitchSelect", 1)
	ipc.control(65580)
	ipc.control(66587,8038)
	ipc.sleep(100)
	ipc.writeLvar("L:APEngageSwitchSelect", 0)
	ipc.control(66587,8038)
end

function hdg_toggle(ctrl, param)
	ipc.writeLvar("L:FdModeselHdgSwitch", 1)
	ipc.control(66587,277)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselHdgSwitch", 0)
	ipc.control(66587,8031)
end

function nav_toggle(ofs, val)
	ipc.writeLvar("L:FdModeselNavSwitch", 1)
	ipc.control(66587,278)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselNavSwitch", 0)
	ipc.control(66587,8031)
end

function apr_toggle(ofs, val)
	ipc.writeLvar("L:FdModeselAprSwitch", 1)
	ipc.control(66587,279)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselAprSwitch", 0)
	ipc.control(66587,8031)
end

function bcr_toggle(ofs, val)
	ipc.writeLvar("L:FdModeselBcSwitch", 1)
	ipc.control(66587,280)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselBcSwitch", 0)
	ipc.control(66587,8031)
end

function alt_toggle(ofs, val)
	ipc.writeLvar("L:FdModeselAltselSwitch", 1)
	ipc.control(66587,282)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselAltselSwitch", 0)
	ipc.control(66587,8031)
end

function vsi_toggle(ofs, val)
	ipc.writeLvar("L:FdModeselVsSwitch", 1)
	ipc.control(66587,283)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselVsSwitch", 0)
	ipc.control(66587,8031)
end

function ias_toggle(ofs, val)
	ipc.writeLvar("L:FdModeselIasSwitch", 1)
	ipc.control(66587,284)
	ipc.control(66587,8031)
	ipc.sleep(100)
	ipc.writeLvar("L:FdModeselIasSwitch", 0)
	ipc.control(66587,8031)
end

function altitude_update()
	if (ipc.elapsedtime() - latm &lt; 1000) then -- give the gauge time to update
		return
	end

	-- update bug
	local jalt = ipc.readLvar("AltSelAlt")
	local oalt = math.floor(ipc.readUD(0x07D4)*meters2feet/65536 + 0.5)

	if (jalt ~= oalt) then
		ipc.writeUD(0x07D4, math.floor(jalt*feet2meters*65536 + 0.5))
	end
end

local lvsi = nil
function vertical_update()
	local jvsi = 0
	local ovsi = ipc.readSW(0x07F2)

	-- fix IAS to VS swap going to -9900 FPM
	if (lvsi ~= nil and math.abs(lvsi - ovsi) &gt; 1000) then
		ipc.writeSW(0x07F2, lvsi)
	else
		lvsi = ovsi
	end

	jvsi = ipc.readLvar("CoamingAPVS")
	ovsi = ipc.readUD(0x07EC)

	if (jvsi ~= ovsi) then
		ipc.writeUD(0x07EC, jvsi)
	end
end

function airspeed_update()
	if (ipc.elapsedtime() - lstm &lt; 1000) then -- give the gauge time to update
		return
	end

	-- update bug
	local jspd = ipc.readLvar("VSIASTarget")
	if (jspd &lt; 0) then
		jspd = 0
	end
	local ospd = ipc.readUW(0x07E2)

	if (jspd ~= ospd) then
		ipc.writeUW(0x07E2, jspd)
	end

	jspd = ipc.readLvar("CoamingAPIAS")
	ospd = ipc.readUD(0x07DC)

	if (jspd ~= ospd) then
		ipc.writeUD(0x07DC, jspd)
	end
end

function heading_update()
	if (ipc.elapsedtime() - lhtm &lt; 1000) then -- give the gauge time to update
		return
	end

	-- update bug
	local jhdg = ipc.readLvar("HDGBug")
	local ohdg = math.floor(ipc.readUW(0x07CC)*360/65536 + 0.5)

	if (jhdg ~= ohdg) then
		ipc.writeUW(0x07CC, math.floor(jhdg*65536/360 + 0.5))
	end

	-- update switch
	-- jhdg = ipc.readLvar("CoamingAPHDG")
	-- ohdg = ipc.readUD(0x07C8)

	-- if (jdgs ~= ohdg) then
		-- ipc.writeUD(0x07C8, jhdg)
	-- end
end

function ias_update()
end

function vs_update()
end

function no_op(ofs, val)
end

function run_update(t)
	altitude_update()
	vertical_update()
	airspeed_update()
	heading_update()
end

--------------------------------------------------------------------------------
-- Main

event.offset(0x07D4, "UD", "altitude_set")
event.offset(0x07E2, "UW", "airspeed_set")
event.offset(0x07CC, "UW", "heading_set")

event.intercept(0x07BC, "UD", "apm_toggle")
event.intercept(0x07C8, "UD", "hdg_toggle")
event.intercept(0x07C4, "UD", "nav_toggle")
event.intercept(0x07FC, "UD", "no_op")
event.intercept(0x0800, "UD", "apr_toggle")
event.intercept(0x0804, "UD", "bcr_toggle")
event.intercept(0x07D0, "UD", "alt_toggle")
event.intercept(0x07EC, "UD", "vsi_toggle")
event.intercept(0x07DC, "UD", "ias_toggle")

event.timer(1000, "run_update")

Share this post


Link to post
Share on other sites

Here's an update... it fixes the J41's A/P from selecting +/-100FPM VS when new ALT is selected while ALT HLD is engaged (thus causing the plane to leave the captured altitude).

Also, a mention in the instructions that you need UseProfiles=No and the name after Auto should be Jetstream not JetStream.

Rename .txt to .lua.

JS41SaitekMP.txt

Share this post


Link to post
Share on other sites

it doesnt really work well ...am i doing something wrong ?

[General]

UpdatedByVersion=4745

History=3MCGHMFD4NUKIUSJNE8T1

TCASid=Flight

TCASrange=40

AxisCalibration=No

DirectAxesToCalibs=No

ShowMultilineWindow=Yes

SuppressSingleline=No

SuppressMultilineFS=No

AxisIntercepts=No

DontResetAxes=No

WeatherReadFactor=2

WeatherRewriteSeconds=1

CustomWeatherModify=No

SimConnectStallTime=1

Console=No

AxesWrongRange=No

GetNearestAirports=No

LuaRerunDelay=66

MouseWheelTrim=No

MouseWheelTrimSpeed=1

JoystickTimeout=20

PollGFTQ6=Yes

BlankDisplays=No

FixControlAccel=No

FixMachSpeedBug=No

VisibilityOptions=No

OneCloudLayer=No

CloudTurbulence=No

CloudIcing=No

GenerateCirrus=No

SuppressCloudTurbulence=No

MaxIce=-4

MinIce=-4

UpperWindGusts=No

SuppressWindTurbulence=No

SuppressWindVariance=No

WindTurbulence=No

TurbulenceRate=1.0,5.0

TurbulenceDivisor=20,20,40,40

SuppressAllGusts=No

MaxSurfaceWind=0

WindLimitLevel=200

WindDiscardLevel=400

WindAjustAltitude=No

WindAjustAltitudeBy=2000

SmoothBySimTime=No

WindSmoothing=No

WindSmoothness=2

WindSmoothAirborneOnly=Yes

PressureSmoothness=0

TemperatureSmoothness=0

DisconnTrimForAP=No

ZeroElevForAPAlt=No

ThrottleSyncAll=No

WhiteMessages=No

ShowPMcontrols=No

SpoilerIncrement=512

MagicBattery=No

RudderSpikeRemoval=No

ElevatorSpikeRemoval=No

AileronSpikeRemoval=No

ReversedElevatorTrim=No

ClockSync=No

ClockSyncMins=5

ClearWeatherDynamics=No

OwnWeatherChanges=No

TimeForSelect=4

LoadFlightMenu=No

LoadPlanMenu=No

PauseAfterCrash=No

BrakeReleaseThreshold=75

SaveDataWithFlights=No

ZapSound=firework

ShortAircraftNameOk=No

UseProfiles=No

EnableMouseLook=No

UseProfiles=No

ShortAircraftNameOk=Substring

InitDelay=0

FSVersionUsed="Microsoft Flight Simulator X",10.0.61472.0

SimConnectUsed=10.0.61259.0

[Auto.Jetstream]

1=Lua JS41SaitekMP

[JoyNames]

AutoAssignLetters=No

0=Saitek Pro Flight Rudder Pedals

0.GUID={35247D20-F76B-11E0-8002-444553540000}

1=Saitek Pro Flight Yoke

1.GUID={3524CB40-F76B-11E0-8003-444553540000}

2=USB Pulse Generator Model 2120

2.GUID={3E173980-0879-11E1-8001-444553540000}

[WideServer]

WideFSenabled=Yes

AdvertiseService=1

Port=8002

Port2=9002

[Programs]

RunIf1=C:\Program Files (x86)\Microsoft Games\Microsoft Flight Simulator X\Modules\linda.exe

[sounds]

Path=C:\Program Files (x86)\Microsoft Games\Microsoft Flight Simulator X\Sound\

Device1=Primair geluidsstuurprogramma

Device2=Luidsprekers (High Definition Audio-apparaat)

Device3=Luidsprekers (USB AUDIO )

[buttons]

ButtonRepeat=20,10

[MacroFiles]

1=iFly737

2=leveld767

[LuaFiles]

1=ipcReady

2=linda

3=JS41SaitekMP

[AutoSave]

Next=1

Interval=60

Files=10

SaveOnGround=No

AutoSaveEnabled=No

[GPSout]

GPSoutEnabled=No

[GPSout2]

GPSoutEnabled=No

[Window.LUA display]

Docked=7343, 2808, 3559, 780

[Profile.Jetstream]

1=Jetstream

[ClientNames]

1=SIMINSTRUCTER_P

2=LAPTOP_RENS

alwso i need spad running right ?

Share this post


Link to post
Share on other sites

anyone ?

What's not working for you? If the altitude preselector works, everything else should be working. Some of the lights will not synchronize but there's no way to fix that. Are using SPAD? I've only tested it with SPAD.

Share this post


Link to post
Share on other sites

as soon as i activate the AP the heading bug jumps and nothing really works anymore ...then when i disconnect the AP the heading bug stays on the current heading and follows if i steer it is inpossible to change it anymore

Share this post


Link to post
Share on other sites

as soon as i activate the AP the heading bug jumps and nothing really works anymore ...then when i disconnect the AP the heading bug stays on the current heading and follows if i steer it is inpossible to change it anymore

Are you using SPAD?

Do you have your modes preselected before engaging AP?

What happens if you select HDG mode?

I'll try to duplicate, but the only time I've seen this is when A/P is turned on without any mode being selected, or in GA/GA mode. In that case it's an unfortunate rounding issue.

Share this post


Link to post
Share on other sites

Yes im using spad

i do preselect my modes and then engage the autopilot ....everything works fine ecept the heading as soon as i select heading i can change it with the dial after i engage the AP the heading bug jumps to the heading seen on the mip

Share this post


Link to post
Share on other sites

Yes im using spad

i do preselect my modes and then engage the autopilot ....everything works fine ecept the heading as soon as i select heading i can change it with the dial after i engage the AP the heading bug jumps to the heading seen on the mip

Just so I understanding...

You preselect HDG mode, and select a heading of XXX using the Saitek panel (with XXX displayed on both the Saitek and EHSI). Then, when you engage the A/P the heading selection to changes to YYY (the current actual heading)?

Share this post


Link to post
Share on other sites

pilotjohn, you're amazing, I am using your file to huge success.

Still tweaking things to get around a few personal quirks but I'm enjoying it a great deal. Thank you very much

Share this post


Link to post
Share on other sites

Attached is an update to the JS41 Saitek Multi-Panel Script.

There might other fixes I haven't posted here yet, but most importantly it changes the AP button functionality to turn OFF the yaw damper if it's ON but AP is OFF.

As it was, when the AP was toggled OFF the YD stayed ON (default JS41 behavior), and needed to be clicked OFF with the mouse at 200 feet AGL for landing (otherwise you'd have a nasty cross-wind touchdown). This was rather disorienting to say the least.

Thus, the new order of functionality for the AP master switch is as follows:

AP ON YD ON

AP OFF YD ON

AP OFF YD OFF

...

So when passing 500 feet AGL, AP can come OFF with YD remaining ON, and then a second press at 200 feet AGL will turn the YD OFF. On a go-around a third press will bring both AP and YD ON.

As before, change the extension to lua.

JS41SaitekMP.txt

Share this post


Link to post
Share on other sites

Hi John,

Thanks for the script.

I'm also finding the heading bug can't be moved, unless HDG mode is turned on first. This is not like the default aircraft, normally you can bug the hdg in advance.

If HDG mode is off, when I move the HDG around, it jumps back to where it was before I moved, about 1 second later.

Any ideas on what causes this or what we can change in the script?

many thanks

Share this post


Link to post
Share on other sites

Hi John,

Thanks for the script.

I'm also finding the heading bug can't be moved, unless HDG mode is turned on first. This is not like the default aircraft, normally you can bug the hdg in advance.

If HDG mode is off, when I move the HDG around, it jumps back to where it was before I moved, about 1 second later.

Any ideas on what causes this or what we can change in the script?

many thanks

I've not seen this behavior. The only odd thing I've seen is that the heading bug continually syncs to your current heading as your manuever.

It sounds like it might be related to that, but I haven't been able to pinpoint what causes the behavior.

This is really a band-aid for something that PMDG should have fixed (and clearly could have if a script can), but there's no chance of that.

It relies on so many kludges that I'm surprised it works as well as it does.

Hi , sorry but i'm new to this. Can you tell me how to use this lua file to work my multi panel on the jetstream?

If you follow the steps in the first few posts it should just works.

Google SPAD FSX, and install it, while uninstalling (or at least disabling the Saitek clients in exe.xml).

Share this post


Link to post
Share on other sites

Hi John,

I managed to get around the heading reset by overriding the heading movement as a button, then using a lua script to incr/decr heading found here: http://spad.189988.n3.nabble.com/PMDG-Jetstream-4100-AP-ALT-Display-on-Multipanel-tp4024982p4025041.html

I can now set heading before switching the HDG mode on, although it won't show in the panel until I press heading, I can see the bug in the VC.

I have only tested on the ground so far, as I'm multi-panel enabling all my planes first before I fly again.

Share this post


Link to post
Share on other sites

John.....good evening

I would like to take away some doubts on this topic . download arch. JS41SaitecMP.txt , already have FSUIPC and the SPAD istalado ... as do I that my Saitek MP works with JS4100 jetstream .

thanks....MARCONI

Share this post


Link to post
Share on other sites

good afternoon

in my case , I have the saitek multipanel installed in the cockpit , using PMDG JS41 Jetstrean , not can not turn on the autopilot multipainel , other functions are working ...

Can I help

Marconi

Share this post


Link to post
Share on other sites

Does anyone know how to contact @pilotjohn out of the forum?
 
I tried send email to "pilotjohn at gearsdown.com" and I have not received answers. Also private message.
 

Google SPAD FSX, and install it, while uninstalling (or at least disabling the Saitek clients in exe.xml).

 
Where is the exe.xml?
 
Are there a sample INI updated for today?
 
Which logs are important? How to view them?
 
I am cousin of FRANCISCO MARCONI and I am trying help him. I also wish, if allowed, of republish the codes as a project in git. If possible, under an open source license.

 

Which would be the steps to install JS41SaitekMP.lua from scratch?

Edited by alexandre-mbm

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Loading...

×
×
  • Create New...

Important Information

By using this site, you agree to our Terms of Use. Guidelines Privacy Policy We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.