1
0
Fork 0
A320-family/Nasal/Systems/APU.nas

361 lines
9.2 KiB
Text
Raw Normal View History

# A3XX Auxilliary Power Unit
# Jonathan Redpath (legoboyvdlp)
# Copyright (c) 2019 Jonathan Redpath (legoboyvdlp)
2020-04-14 17:07:01 +00:00
var APUNodes = {
Controls: {
2020-05-05 18:43:21 +00:00
master: props.globals.getNode("/controls/apu/master"),
fire: props.globals.getNode("/controls/apu/fire-btn"),
bleed: props.globals.getNode("/controls/pneumatics/switches/apu"),
2020-04-14 17:07:01 +00:00
},
Oil: {
2020-05-05 18:43:21 +00:00
level: props.globals.getNode("/systems/apu/oil/level-l"),
pressure: props.globals.getNode("/systems/apu/oil/oil-pressure-psi"),
temperature: props.globals.getNode("/systems/apu/oil/oil-temperature-degC"),
2020-04-14 17:07:01 +00:00
},
2020-05-05 18:43:21 +00:00
masterElecThreeMin: props.globals.getNode("/systems/apu/dc-bat-three-minutes"),
2020-04-14 17:07:01 +00:00
};
var APU = {
2020-04-14 17:07:01 +00:00
state: 0, # off, power up, watch, starting preparation, starting, run, cooldown, shutdown
inletFlap: aircraft.door.new("/controls/apu/inlet-flap", 12),
fuelValveCmd: props.globals.getNode("/systems/fuel/valves/apu-lp-valve-cmd"),
fuelValvePos: props.globals.getNode("/systems/fuel/valves/apu-lp-valve"),
2020-05-05 18:43:21 +00:00
inletFlapPos: props.globals.getNode("/controls/apu/inlet-flap/position-norm"),
oilLevel: props.globals.getNode("/systems/apu/oil/level-l"),
listenSignals: 0,
2020-04-14 17:07:01 +00:00
listenStopSignal: 0,
bleedTime: 0,
cooldownEndTime: 0,
2020-04-17 23:51:16 +00:00
fastStart: 0,
_count: 0,
2020-04-14 17:07:01 +00:00
warnings: {
lowOilLevel: 0,
},
GenericControls: {
2020-05-05 18:43:21 +00:00
starter: props.globals.getNode("/controls/engines/engine[2]/starter"),
cutoff: props.globals.getNode("/controls/engines/engine[2]/cutoff"),
throttle: props.globals.getNode("/controls/engines/engine[2]/throttle"),
2020-04-14 17:07:01 +00:00
},
signals: {
2020-05-05 18:43:21 +00:00
startInProgress: props.globals.getNode("/systems/apu/start"),
2020-04-14 17:07:01 +00:00
oilTestComplete: 0,
2020-05-05 18:43:21 +00:00
available: props.globals.getNode("/systems/apu/available"),
2020-04-14 17:07:01 +00:00
bleedWasUsed: 0,
2020-05-05 18:43:21 +00:00
fault: props.globals.getNode("/systems/apu/fault"),
2020-04-14 17:07:01 +00:00
autoshutdown: 0,
emer: 0,
2020-04-14 17:07:01 +00:00
},
setState: func(num) {
me.state = num;
},
resetStuff: func() {
me.setState(0);
me.warnings.lowOilLevel = 0;
me.listenSignals = 0;
me.listenStopSignal = 0;
me.bleedTime = 0;
me.cooldownEndTime = 0;
me.signals.oilTestComplete = 0;
me.signals.bleedWasUsed = 0;
me.signals.fault.setValue(0);
2020-04-14 17:07:01 +00:00
me.signals.autoshutdown = 0;
me.signals.emer = 0;
2020-04-17 20:56:12 +00:00
checkApuStartTimer.stop();
apuStartTimer.stop();
apuStartTimer2.stop();
shutdownTimer.stop();
cooldownTimer.stop();
2020-04-14 17:07:01 +00:00
},
new: func() {
var a = { parents:[APU] };
return a;
2020-04-14 17:07:01 +00:00
me.GenericControls.throttle.setValue(1);
},
2020-04-14 17:07:01 +00:00
# Tests
checkOil: func() {
if (me.oilLevel.getValue() < 3.69) {
me.warnings.lowOilLevel = 1;
} else {
me.warnings.lowOilLevel = 0;
}
me.signals.oilTestComplete = 1;
},
2020-04-14 17:07:01 +00:00
# Routines to do with state
powerOn: func() {
2020-04-17 20:56:12 +00:00
# just in case
me.resetStuff();
if (systems.ELEC.Bus.dcBat.getValue() < 25) {
settimer(func() {
if (systems.ELEC.Bus.dcBat.getValue() < 25) {
me.resetStuff();
return;
}
}, 0.2);
}
# apu able to receive emergency stop or start signals
2020-04-14 17:07:01 +00:00
me.setState(1);
me.fuelValveCmd.setValue(1);
me.inletFlap.open();
me.listenSignals = 1;
2020-04-17 22:27:01 +00:00
settimer(func() {
if (APUNodes.Controls.master.getValue() and !pts.Acconfig.running.getValue()) {
2020-04-17 22:27:01 +00:00
me.setState(2);
}
}, 3);
settimer(func() { me.checkOil() }, 8);
2020-04-14 17:07:01 +00:00
},
2020-04-18 16:02:08 +00:00
startCommand: func(fast = 0) {
2020-04-14 17:07:01 +00:00
if (me.listenSignals and (me.state == 1 or me.state == 2)) {
me.signals.startInProgress.setBoolValue(1);
2020-04-14 17:07:01 +00:00
me.setState(3);
checkApuStartTimer.start();
2020-04-17 23:51:16 +00:00
me.fastStart = fast;
2020-04-14 17:07:01 +00:00
}
},
2020-04-17 23:51:16 +00:00
checkApuStart: func() {
if (me.fastStart) {
me.inletFlap.setpos(1);
}
2020-04-14 17:07:01 +00:00
if (pts.APU.rpm.getValue() < 7 and me.fuelValvePos.getValue() and me.inletFlapPos.getValue() == 1 and me.signals.oilTestComplete and !me.warnings.lowOilLevel) {
me.setState(4);
me.listenStopSignal = 1;
checkApuStartTimer.stop();
me.startSequence();
}
},
startSequence: func() {
me.GenericControls.starter.setValue(1);
apuStartTimer.start();
},
waitStart: func() {
if (pts.APU.rpm.getValue() >= 4.9 or me.fastStart) {
2020-04-14 17:07:01 +00:00
me.GenericControls.cutoff.setValue(0);
if (me.fastStart) {
setprop("/fdm/jsbsim/propulsion/set-running", 2);
}
2020-04-14 17:07:01 +00:00
apuStartTimer.stop();
apuStartTimer2.start();
}
},
2020-04-14 17:07:01 +00:00
waitStart2: func() {
if (pts.APU.rpm.getValue() >= 99.9) {
me.GenericControls.starter.setValue(0);
me.signals.startInProgress.setBoolValue(0);
2020-04-14 17:07:01 +00:00
me.signals.available.setValue(1);
me.setState(5);
apuStartTimer2.stop();
}
},
cooldown: func() {
if (APUNodes.Controls.master.getValue()) {
cooldownTimer.stop();
me.setState(5);
return;
}
if (pts.Sim.Time.elapsedSec.getValue() >= me.cooldownEndTime) {
cooldownTimer.stop();
me.stopAPU();
me.setState(7);
shutdownTimer.start();
}
},
shutdown: func() {
if (!me.signals.autoshutdown and APUNodes.Controls.master.getValue()) {
me.powerOn();
return;
}
me.GenericControls.cutoff.setValue(1);
me.GenericControls.starter.setValue(0);
if (!me.signals.autoshutdown and pts.APU.rpm.getValue() < 95 and me.signals.available.getValue()) {
me.signals.available.setValue(0);
}
if (me.signals.autoshutdown and (me.signals.available.getValue() or !me.signals.fault.getValue())) {
2020-04-14 17:07:01 +00:00
me.signals.available.setValue(0);
me.signals.fault.setValue(1);
2020-04-14 17:07:01 +00:00
}
2020-04-17 22:27:01 +00:00
if (pts.APU.rpm.getValue() < 7 and !APUNodes.Controls.master.getValue()) {
2020-04-14 17:07:01 +00:00
me.inletFlap.close();
me.fuelValveCmd.setValue(0);
2020-04-14 17:07:01 +00:00
if (!APUNodes.Controls.master.getValue()) {
me.setState(0);
me.resetStuff();
shutdownTimer.stop();
}
}
},
# Signal generators / receivers
stop: func() {
if (me.listenStopSignal and me.state == 4) {
me.signals.startInProgress.setBoolValue(0);
2020-04-14 17:07:01 +00:00
me.stopAPU();
me.setState(7);
shutdownTimer.start();
} else {
if (me.signals.startInProgress.getBoolValue()) {
me.signals.startInProgress.setBoolValue(0);
}
2020-04-14 17:07:01 +00:00
if (me.signals.bleedWasUsed) {
if (me.bleedTime == 0) { me.shutBleed(); }
2020-04-14 17:07:01 +00:00
if (120 - (pts.Sim.Time.elapsedSec.getValue() - me.bleedTime) > 0) {
me.cooldownEndTime = me.bleedTime + 120;
me.setState(6);
cooldownTimer.start();
} else {
me.stopAPU();
me.setState(7);
shutdownTimer.start();
}
} else {
me.stopAPU();
me.setState(7);
shutdownTimer.start();
}
}
},
2020-04-14 17:07:01 +00:00
autoStop: func() {
if (me.state >= 4) {
checkApuStartTimer.stop();
apuStartTimer.stop();
apuStartTimer2.stop();
cooldownTimer.stop();
me.stopAPU();
me.setState(7);
shutdownTimer.start();
me.signals.autoshutdown = 1;
me.signals.fault.setValue(1);
} else {
checkApuStartTimer.stop();
me.inletFlap.close();
me.fuelValveCmd.setValue(0);
me.signals.autoshutdown = 1;
me.signals.fault.setValue(1);
me.setState(0);
2020-04-14 17:07:01 +00:00
}
},
emergencyStop: func() {
me.signals.emer = 1;
2020-04-14 17:07:01 +00:00
if (me.listenSignals and (me.state < 4)) {
checkApuStartTimer.stop();
me.inletFlap.close();
me.fuelValveCmd.setValue(0);
me.signals.autoshutdown = 1;
me.signals.fault.setValue(1);
2020-04-14 17:07:01 +00:00
me.setState(0);
} elsif (me.state >= 4) {
2020-04-17 20:56:12 +00:00
me.fuelValveCmd.setValue(0);
2020-04-14 17:07:01 +00:00
me.autoStop();
}
},
2020-04-14 17:07:01 +00:00
# Functions
stopAPU: func() {
me.GenericControls.cutoff.setValue(1);
},
shutBleed: func() {
APUNodes.Controls.bleed.setValue(0);
me.bleedTime = pts.Sim.Time.elapsedSec.getValue();
2020-04-14 17:07:01 +00:00
},
_powerLost: 0,
update: func() {
me._count += 1;
if (me._count == 5) {
me._count = 0;
if (me.state == 5 and APUNodes.Oil.pressure.getValue() < 35 or APUNodes.Oil.temperature.getValue() > 135) {
me.autoStop();
}
if (systems.ELEC.Bus.dcBat.getValue() < 25) {
if (!me._powerLost) {
me._powerLost = 1;
settimer(func() {
if (me._powerLost) {
if (me.GenericControls.starter.getValue()) {
me.GenericControls.starter.setValue(0);
}
if (me.state != 0) {
me.autoStop();
}
}
}, 0.2);
}
} else {
me._powerLost = 0;
}
}
},
};
var APUController = {
_init: 0,
APU: nil,
init: func() {
if (!me._init) {
me.APU = APU.new();
me._init = 1;
}
},
loop: func() {
if (me._init) {
me.APU.update();
}
}
2020-04-14 17:07:01 +00:00
};
var _masterTime = 0;
setlistener("/controls/apu/master", func() {
2020-04-17 22:27:01 +00:00
if (APUController.APU != nil) {
if (APUNodes.Controls.master.getValue() and APUController.APU.state == 0) {
shutdownTimer.stop();
APUNodes.masterElecThreeMin.setValue(1);
checkMasterThreeMinTimer.start();
_masterTime = pts.Sim.Time.elapsedSec.getValue();
APUController.APU.powerOn();
} elsif (!APUNodes.Controls.master.getValue()) {
APUController.APU.stop();
}
2020-04-14 17:07:01 +00:00
}
2020-04-17 23:51:16 +00:00
}, 0, 0);
2020-04-14 17:07:01 +00:00
setlistener("/controls/pneumatics/switches/apu", func() {
2020-04-17 22:27:01 +00:00
if (APUController.APU != nil) {
if (APUNodes.Controls.bleed.getValue()) {
APUController.APU.signals.bleedWasUsed = 1;
} else {
APUController.APU.bleedTime = pts.Sim.Time.elapsedSec.getValue();
}
2020-04-17 22:27:01 +00:00
}
2020-04-17 23:51:16 +00:00
}, 0, 0);
2020-04-14 17:07:01 +00:00
var checkMasterThreeMinTimer = maketimer(0.1, func() {
if (!APUNodes.Controls.master.getValue()) {
APUNodes.masterElecThreeMin.setValue(0);
checkMasterThreeMinTimer.stop();
return;
}
if (pts.Sim.Time.elapsedSec.getValue() >= _masterTime + 180) {
APUNodes.masterElecThreeMin.setValue(0);
checkMasterThreeMinTimer.stop();
}
});
var checkApuStartTimer = maketimer(0.1, func() {
APUController.APU.checkApuStart();
});
var apuStartTimer = maketimer(0.1, func() {
APUController.APU.waitStart();
});
var apuStartTimer2 = maketimer(0.1, func() {
APUController.APU.waitStart2();
});
var cooldownTimer = maketimer(0.1, func() {
APUController.APU.cooldown();
});
var shutdownTimer = maketimer(0.1, func() {
APUController.APU.shutdown();
});