+
-
+
-
-
-
-
-
-
-
+
+
+
+
+
+
+
diff --git a/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/CDU/A320_Neo_CDU_VerticalRevisionPage.js b/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/CDU/A320_Neo_CDU_VerticalRevisionPage.js
index 31bbb2a0c90..9c0ea557b9a 100644
--- a/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/CDU/A320_Neo_CDU_VerticalRevisionPage.js
+++ b/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/CDU/A320_Neo_CDU_VerticalRevisionPage.js
@@ -24,8 +24,9 @@ class CDUVerticalRevisionPage {
/** @type {BaseFlightPlan} */
const targetPlan = mcdu.flightPlan(forPlan, inAlternate);
- // Use performance data of primary for waypoints in alternaten
- const performanceData = mcdu.flightPlan(forPlan, false).performanceData;
+ const mainTargetPlan = mcdu.flightPlan(forPlan, false);
+ // Use performance data of primary for waypoints in alternate
+ const performanceData = mainTargetPlan.performanceData;
const confirmConstraint = Number.isFinite(confirmSpeed) || Number.isFinite(confirmAlt);
const constraintType = CDUVerticalRevisionPage.constraintType(mcdu, wpIndex, forPlan, inAlternate);
@@ -41,11 +42,6 @@ class CDUVerticalRevisionPage {
}
}
- let coordinates = "---";
- if (waypoint.isXF()) {
- coordinates = CDUPilotsWaypoint.formatLatLong(waypoint.terminationWaypoint().location);
- }
-
const showSpeedLim = mcdu._fuelPredDone || isOrigin || isDestination || constraintType !== WaypointConstraintType.Unknown;
// the conditions other than isDestination are a workaround for no ToC
const showDesSpeedLim = showSpeedLim && (isDestination ||
@@ -53,19 +49,27 @@ class CDUVerticalRevisionPage {
(mcdu.flightPhaseManager.phase > FmgcFlightPhases.CRUISE &&
mcdu.flightPhaseManager.phase < FmgcFlightPhases.GOAROUND));
+ const climbSpeedLimitSpeed = inAlternate ? performanceData.alternateClimbSpeedLimitSpeed : performanceData.climbSpeedLimitSpeed;
+ const climbSpeedLimitAltitude = inAlternate ? performanceData.alternateClimbSpeedLimitAltitude : performanceData.climbSpeedLimitAltitude;
+ const isClimbSpeedLimitPilotEntered = inAlternate ? performanceData.isAlternateClimbSpeedLimitPilotEntered : performanceData.isClimbSpeedLimitPilotEntered;
+
+ const descentSpeedLimitSpeed = inAlternate ? performanceData.alternateDescentSpeedLimitSpeed : performanceData.descentSpeedLimitSpeed;
+ const descentSpeedLimitAltitude = inAlternate ? performanceData.alternateDescentSpeedLimitAltitude : performanceData.descentSpeedLimitAltitude;
+ const isDescentSpeedLimitPilotEntered = inAlternate ? performanceData.isAlternateDescentSpeedLimitPilotEntered : performanceData.isDescentSpeedLimitPilotEntered;
+
let speedLimitTitle = "";
let speedLimitCell = "";
if (showDesSpeedLim) {
speedLimitTitle = "\xa0DES SPD LIM";
- if (mcdu.descentSpeedLimit !== undefined) {
- speedLimitCell = `{magenta}{${mcdu.descentSpeedLimitPilot ? 'big' : 'small'}}${mcdu.descentSpeedLimit.toFixed(0).padStart(3, "0")}/${this.formatFl(mcdu.descentSpeedLimitAlt, performanceData.transitionLevel * 100)}{end}{end}`;
+ if (descentSpeedLimitSpeed !== null) {
+ speedLimitCell = `{magenta}{${isDescentSpeedLimitPilotEntered ? 'big' : 'small'}}${descentSpeedLimitSpeed.toFixed(0).padStart(3, "0")}/${this.formatFl(descentSpeedLimitAltitude, performanceData.transitionLevel * 100)}{end}{end}`;
} else {
speedLimitCell = "{cyan}*[ ]/[ ]{end}";
}
} else if (showSpeedLim) {
speedLimitTitle = "\xa0CLB SPD LIM";
- if (mcdu.climbSpeedLimit !== undefined) {
- speedLimitCell = `{magenta}{${mcdu.climbSpeedLimitPilot ? 'big' : 'small'}}${mcdu.climbSpeedLimit.toFixed(0).padStart(3, "0")}/${this.formatFl(mcdu.climbSpeedLimitAlt, performanceData.transitionAltitude)}{end}{end}`;
+ if (climbSpeedLimitSpeed !== null) {
+ speedLimitCell = `{magenta}{${isClimbSpeedLimitPilotEntered ? 'big' : 'small'}}${climbSpeedLimitSpeed.toFixed(0).padStart(3, "0")}/${this.formatFl(climbSpeedLimitAltitude, performanceData.transitionAltitude)}{end}{end}`;
} else {
speedLimitCell = "{cyan}*[ ]/[ ]{end}";
}
@@ -162,23 +166,13 @@ class CDUVerticalRevisionPage {
if (value === FMCMainDisplay.clrValue) {
if (showDesSpeedLim) {
- if (mcdu.descentSpeedLimitPilot) {
- mcdu.descentSpeedLimit = 250;
- mcdu.descentSpeedLimitAlt = 10000;
- } else {
- mcdu.descentSpeedLimit = undefined;
- mcdu.descentSpeedLimitAlt = undefined;
- }
- mcdu.descentSpeedLimitPilot = false;
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateDescentSpeedLimitSpeed' : 'descentSpeedLimitSpeed', null);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateDescentSpeedLimitAltitude' : 'descentSpeedLimitAltitude', null);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'isAlternateDescentSpeedLimitPilotEntered' : 'isDescentSpeedLimitPilotEntered', false);
} else {
- if (mcdu.climbSpeedLimitPilot) {
- mcdu.climbSpeedLimit = 250;
- mcdu.climbSpeedLimitAlt = 10000;
- } else {
- mcdu.climbSpeedLimit = undefined;
- mcdu.climbSpeedLimitAlt = undefined;
- }
- mcdu.climbSpeedLimitPilot = false;
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateClimbSpeedLimitSpeed' : 'climbSpeedLimitSpeed', null);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateClimbSpeedLimitAltitude' : 'climbSpeedLimitAltitude', null);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'isAlternateClimbSpeedLimitPilotEntered' : 'isClimbSpeedLimitPilotEntered', false);
}
CDUVerticalRevisionPage.ShowPage(mcdu, waypoint, wpIndex, verticalWaypoint, undefined, undefined, undefined, forPlan, inAlternate);
return;
@@ -203,13 +197,13 @@ class CDUVerticalRevisionPage {
alt = Math.round(alt / 10) * 10;
if (showDesSpeedLim) {
- mcdu.descentSpeedLimit = speed;
- mcdu.descentSpeedLimitAlt = alt;
- mcdu.descentSpeedLimitPilot = true;
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateDescentSpeedLimitSpeed' : 'descentSpeedLimitSpeed', speed);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateDescentSpeedLimitAltitude' : 'descentSpeedLimitAltitude', alt);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'isAlternateDescentSpeedLimitPilotEntered' : 'isDescentSpeedLimitPilotEntered', true);
} else {
- mcdu.climbSpeedLimit = speed;
- mcdu.climbSpeedLimitAlt = alt;
- mcdu.climbSpeedLimitPilot = true;
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateClimbSpeedLimitSpeed' : 'climbSpeedLimitSpeed', speed);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'alternateClimbSpeedLimitAltitude' : 'climbSpeedLimitAltitude', alt);
+ mainTargetPlan.setPerformanceData(inAlternate ? 'isAlternateClimbSpeedLimitPilotEntered' : 'isClimbSpeedLimitPilotEntered', true);
}
CDUVerticalRevisionPage.ShowPage(mcdu, waypoint, wpIndex, verticalWaypoint, undefined, undefined, undefined, forPlan, inAlternate);
diff --git a/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/FMC/A32NX_FMCMainDisplay.js b/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/FMC/A32NX_FMCMainDisplay.js
index 3ef6b69e973..53476dddb0f 100644
--- a/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/FMC/A32NX_FMCMainDisplay.js
+++ b/fbw-a32nx/src/base/flybywire-aircraft-a320-neo/html_ui/Pages/VCockpit/Instruments/Airliners/FlyByWire_A320_Neo/FMC/A32NX_FMCMainDisplay.js
@@ -100,12 +100,6 @@ class FMCMainDisplay extends BaseAirliners {
this.preSelectedCrzSpeed = undefined;
this.managedSpeedTarget = undefined;
this.managedSpeedTargetIsMach = undefined;
- this.climbSpeedLimit = undefined;
- this.climbSpeedLimitAlt = undefined;
- this.climbSpeedLimitPilot = undefined;
- this.descentSpeedLimit = undefined;
- this.descentSpeedLimitAlt = undefined;
- this.descentSpeedLimitPilot = undefined;
this.managedSpeedClimb = undefined;
this.managedSpeedClimbIsPilotEntered = undefined;
this.managedSpeedClimbMach = undefined;
@@ -450,12 +444,6 @@ class FMCMainDisplay extends BaseAirliners {
this.preSelectedCrzSpeed = undefined;
this.managedSpeedTarget = NaN;
this.managedSpeedTargetIsMach = false;
- this.climbSpeedLimit = 250;
- this.climbSpeedLimitAlt = 10000;
- this.climbSpeedLimitPilot = false;
- this.descentSpeedLimit = 250;
- this.descentSpeedLimitAlt = 10000;
- this.descentSpeedLimitPilot = false;
this.managedSpeedClimb = 290;
this.managedSpeedClimbIsPilotEntered = false;
this.managedSpeedClimbMach = 0.78;
@@ -947,11 +935,11 @@ class FMCMainDisplay extends BaseAirliners {
// apply speed limit/alt
if (this.flightPhaseManager.phase <= FmgcFlightPhases.CRUISE) {
- if (this.climbSpeedLimit !== undefined && alt <= this.climbSpeedLimitAlt) {
+ if (this.climbSpeedLimit !== null && alt <= this.climbSpeedLimitAlt) {
kcas = Math.min(this.climbSpeedLimit, kcas);
}
} else if (this.flightPhaseManager.phase < FmgcFlightPhases.GOAROUND) {
- if (this.descentSpeedLimit !== undefined && alt <= this.descentSpeedLimitAlt) {
+ if (this.descentSpeedLimit !== null && alt <= this.descentSpeedLimitAlt) {
kcas = Math.min(this.descentSpeedLimit, kcas);
}
}
@@ -4762,6 +4750,62 @@ class FMCMainDisplay extends BaseAirliners {
}
}
+ /**
+ * The maximum speed imposed by the climb speed limit in the active flight plan or null if it is not set.
+ * @returns {number | null}
+ */
+ get climbSpeedLimit() {
+ const plan = this.currFlightPlanService.active;
+
+ // The plane follows 250 below 10'000 even without a flight plan
+ return plan ? plan.performanceData.climbSpeedLimitSpeed : DefaultPerformanceData.ClimbSpeedLimitSpeed;
+ }
+
+ /**
+ * The altitude below which the climb speed limit of the active flight plan applies or null if not set.
+ * @returns {number | null}
+ */
+ get climbSpeedLimitAlt() {
+ const plan = this.currFlightPlanService.active;
+
+ // The plane follows 250 below 10'000 even without a flight plan
+ return plan ? plan.performanceData.climbSpeedLimitAltitude : DefaultPerformanceData.ClimbSpeedLimitAltitude;
+ }
+
+ get climbSpeedLimitPilot() {
+ const plan = this.currFlightPlanService.active;
+
+ return plan ? plan.performanceData.isClimbSpeedLimitPilotEntered : false;
+ }
+
+ /**
+ * The maximum speed imposed by the descent speed limit in the active flight plan or null if it is not set.
+ * @returns {number | null}
+ */
+ get descentSpeedLimit() {
+ const plan = this.currFlightPlanService.active;
+
+ // The plane follows 250 below 10'000 even without a flight plan
+ return plan ? plan.performanceData.descentSpeedLimitSpeed : DefaultPerformanceData.DescentSpeedLimitSpeed;
+ }
+
+ /**
+ * The altitude below which the descent speed limit of the active flight plan applies or null if not set.
+ * @returns {number | null}
+ */
+ get descentSpeedLimitAlt() {
+ const plan = this.currFlightPlanService.active;
+
+ // The plane follows 250 below 10'000 even without a flight plan
+ return plan ? plan.performanceData.descentSpeedLimitAltitude : DefaultPerformanceData.DescentSpeedLimitAltitude;
+ }
+
+ get descentSpeedLimitPilot() {
+ const plan = this.currFlightPlanService.active;
+
+ return plan ? plan.performanceData.isDescentSpeedLimitPilotEntered : false;
+ }
+
getFlightPhase() {
return this.flightPhaseManager.phase;
}
@@ -5078,6 +5122,13 @@ const FlightPlans = Object.freeze({
Temporary: 1,
});
+const DefaultPerformanceData = Object.freeze({
+ ClimbSpeedLimitSpeed: 250,
+ ClimbSpeedLimitAltitude: 10000,
+ DescentSpeedLimitSpeed: 250,
+ DescentSpeedLimitAltitude: 10000,
+});
+
class FmArinc429OutputWord extends Arinc429Word {
constructor(name, value = 0) {
super(0);
diff --git a/fbw-a32nx/src/systems/fmgc/src/flightplanning/plans/FlightPlan.ts b/fbw-a32nx/src/systems/fmgc/src/flightplanning/plans/FlightPlan.ts
index 25b49d99231..2bfe23e6fc8 100644
--- a/fbw-a32nx/src/systems/fmgc/src/flightplanning/plans/FlightPlan.ts
+++ b/fbw-a32nx/src/systems/fmgc/src/flightplanning/plans/FlightPlan.ts
@@ -15,6 +15,7 @@ import { FlightArea } from '@fmgc/navigation/FlightArea';
import { CopyOptions } from '@fmgc/flightplanning/plans/CloningOptions';
import { ImportedPerformanceData } from '@fmgc/flightplanning/uplink/SimBriefUplinkAdapter';
import {
+ DefaultPerformanceData,
FlightPlanPerformanceData,
FlightPlanPerformanceDataProperties,
} from '@fmgc/flightplanning/plans/performance/FlightPlanPerformanceData';
@@ -129,9 +130,20 @@ export class FlightPlan= this.firstMissedApproachLegIndex) {
throw new Error('[FPM] Cannot direct to a leg in the missed approach segment');
@@ -301,8 +313,21 @@ export class FlightPlan
| string;
+ className2?: Subscribable | string;
+ visible?: Subscribable;
+ flashing?: Subscribable;
+ flashDuration: number;
+}
+
+export class FlashOneHertz extends DisplayComponent {
+ private readonly oneHertzClock = ConsumerSubject.create(null, false);
+
+ private readonly flashingMtrig = new NXLogicTriggeredMonostableNode(this.props.flashDuration, true);
+
+ private readonly flashingMtrigResult = Subject.create(false);
+
+ private readonly visible = MappedSubject.create(
+ ([visible, oneHertzClock, flashingMtrig]) => visible && !(flashingMtrig && oneHertzClock),
+ this.props.visible ?? Subject.create(true),
+ this.oneHertzClock,
+ this.flashingMtrigResult,
+ );
+
+ private readonly class = MappedSubject.create(
+ ([visible, class1, class2]) => (visible ? class1 : class2),
+ this.visible,
+ SubscribableUtils.toSubscribable(this.props.className1 ?? '', true),
+ SubscribableUtils.toSubscribable(this.props.className2 ?? 'HiddenElement', true),
+ );
+
+ private prevClass = '';
+
+ onAfterRender(node: VNode): void {
+ super.onAfterRender(node);
+
+ const sub = this.props.bus.getSubscriber();
+
+ this.oneHertzClock.setConsumer(sub.on('oneHertzClock'));
+
+ sub.on('deltaTime').handle((dt) => {
+ const visible = this.props.visible?.get() ?? true;
+ const shouldFlash = this.props.flashing?.get() ?? true;
+ this.flashingMtrigResult.set(
+ this.props.flashDuration === Infinity
+ ? visible && shouldFlash
+ : this.flashingMtrig.write(visible && shouldFlash, dt),
+ );
+ });
+
+ this.class.sub((value) => {
+ this.props.children.forEach((child) => {
+ const classList = ((child as VNode).instance as HTMLElement).classList;
+
+ classList.remove(...FSComponent.parseCssClassesFromString(this.prevClass));
+ classList.add(...FSComponent.parseCssClassesFromString(value));
+ });
+
+ this.prevClass = value;
+ }, true);
+ }
+
+ render(): VNode {
+ return <>{this.props.children}>;
+ }
+}
diff --git a/fbw-a32nx/src/systems/instruments/src/MsfsAvionicsCommon/providers/ExtendedClockProvider.ts b/fbw-a32nx/src/systems/instruments/src/MsfsAvionicsCommon/providers/ExtendedClockProvider.ts
new file mode 100644
index 00000000000..e7db8155139
--- /dev/null
+++ b/fbw-a32nx/src/systems/instruments/src/MsfsAvionicsCommon/providers/ExtendedClockProvider.ts
@@ -0,0 +1,58 @@
+// Copyright (c) 2021-2023 FlyByWire Simulations
+//
+// SPDX-License-Identifier: GPL-3.0
+
+import { ClockEvents, EventBus, Instrument, Subject } from '@microsoft/msfs-sdk';
+
+export interface ExtendedClockEvents {
+ monotonicTime: number;
+ deltaTime: number;
+ oneHertzClock: boolean;
+}
+
+export class ExtendedClockEventProvider implements Instrument {
+ private prevSimTime = 0;
+
+ private deltaTime = 0;
+
+ private monotonicTime = 0;
+
+ private oneHertzClockTime = 0;
+
+ private readonly oneHertzClock = Subject.create(false);
+
+ constructor(private readonly bus: EventBus) {}
+
+ /** @inheritdoc */
+ public init(): void {
+ const publisher = this.bus.getPublisher();
+ const subscriber = this.bus.getSubscriber();
+
+ subscriber.on('simTime').handle((time) => {
+ this.deltaTime = time - this.prevSimTime;
+
+ this.monotonicTime += this.deltaTime;
+
+ this.oneHertzClockTime += this.deltaTime;
+
+ this.oneHertzClock.set(this.oneHertzClockTime > 500);
+
+ publisher.pub('deltaTime', this.deltaTime);
+ publisher.pub('monotonicTime', this.monotonicTime);
+
+ if (this.oneHertzClockTime > 1000) {
+ this.oneHertzClockTime = 0;
+ }
+ this.prevSimTime = time;
+ });
+
+ this.oneHertzClock.sub((oneHertzClock) => {
+ publisher.pub('oneHertzClock', oneHertzClock);
+ });
+ }
+
+ /** @inheritdoc */
+ public onUpdate(): void {
+ // noop
+ }
+}
diff --git a/fbw-a32nx/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx b/fbw-a32nx/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx
new file mode 100644
index 00000000000..2a7c0695682
--- /dev/null
+++ b/fbw-a32nx/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx
@@ -0,0 +1,33 @@
+// Copyright (c) 2021-2023 FlyByWire Simulations
+//
+// SPDX-License-Identifier: GPL-3.0
+
+import { EventBus, SimVarDefinition, SimVarValueType, SimVarPublisher } from '@microsoft/msfs-sdk';
+
+export type PseudoFwcSimvars = {
+ engine1Master: number;
+ engine2Master: number;
+ engine3Master: number;
+ engine4Master: number;
+ fmgc1DiscreteWord3: number;
+ fmgc2DiscreteWord3: number;
+ fmgc1DiscreteWord4: number;
+ fmgc2DiscreteWord4: number;
+};
+
+export class PseudoFwcSimvarPublisher extends SimVarPublisher {
+ private static simvars = new Map([
+ ['engine1Master', { name: 'A:FUELSYSTEM VALVE SWITCH:1', type: SimVarValueType.Bool }],
+ ['engine2Master', { name: 'A:FUELSYSTEM VALVE SWITCH:2', type: SimVarValueType.Bool }],
+ ['engine3Master', { name: 'A:FUELSYSTEM VALVE SWITCH:3', type: SimVarValueType.Bool }],
+ ['engine4Master', { name: 'A:FUELSYSTEM VALVE SWITCH:4', type: SimVarValueType.Bool }],
+ ['fmgc1DiscreteWord3', { name: 'L:A32NX_FMGC_1_DISCRETE_WORD_3', type: SimVarValueType.Number }],
+ ['fmgc2DiscreteWord3', { name: 'L:A32NX_FMGC_2_DISCRETE_WORD_3', type: SimVarValueType.Number }],
+ ['fmgc1DiscreteWord4', { name: 'L:A32NX_FMGC_1_DISCRETE_WORD_4', type: SimVarValueType.Number }],
+ ['fmgc2DiscreteWord4', { name: 'L:A32NX_FMGC_2_DISCRETE_WORD_4', type: SimVarValueType.Number }],
+ ]);
+
+ public constructor(bus: EventBus) {
+ super(PseudoFwcSimvarPublisher.simvars, bus);
+ }
+}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/AltitudeIndicator.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/AltitudeIndicator.tsx
index c4f0bc38767..84c6a9d27ee 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/AltitudeIndicator.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/AltitudeIndicator.tsx
@@ -2,7 +2,15 @@
//
// SPDX-License-Identifier: GPL-3.0
-import { ClockEvents, DisplayComponent, FSComponent, Subject, Subscribable, VNode } from '@microsoft/msfs-sdk';
+import {
+ ClockEvents,
+ ConsumerSubject,
+ DisplayComponent,
+ FSComponent,
+ Subject,
+ Subscribable,
+ VNode,
+} from '@microsoft/msfs-sdk';
import {
ArincEventBus,
Arinc429Register,
@@ -17,6 +25,7 @@ import { PFDSimvars } from './shared/PFDSimvarPublisher';
import { DigitalAltitudeReadout } from './DigitalAltitudeReadout';
import { VerticalTape } from './VerticalTape';
import { Arinc429Values } from './shared/ArincValueProvider';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
const DisplayRange = 570;
const ValueSpacing = 100;
@@ -294,7 +303,9 @@ enum TargetAltitudeColor {
export class AltitudeIndicatorOfftape extends DisplayComponent {
private abnormal = FSComponent.createRef();
- private tcasFailed = FSComponent.createRef();
+ private readonly altFlagVisible = Subject.create(false);
+
+ private readonly tcasFailed = ConsumerSubject.create(null, false);
private normal = FSComponent.createRef();
@@ -326,18 +337,10 @@ export class AltitudeIndicatorOfftape extends DisplayComponent {
- if (tcasFailed) {
- this.tcasFailed.instance.style.display = 'inline';
- } else {
- this.tcasFailed.instance.style.display = 'none';
- }
- });
+ this.tcasFailed.setConsumer(sub.on('tcasFail'));
sub
.on('fmgcDiscreteWord1')
@@ -378,24 +381,27 @@ export class AltitudeIndicatorOfftape extends DisplayComponent
-
- ALT
-
+
+
+ ALT
+
+
-
-
+
+
T
-
+
C
-
+
A
-
+
S
-
+
+
{
private selectedAltUpperGroupRef = FSComponent.createRef();
- private selectedAltFailText = FSComponent.createRef();
+ private readonly selectedAltFailed = Subject.create(false);
private targetGroupRef = FSComponent.createRef();
@@ -559,22 +565,22 @@ class SelectedAltIndicator extends DisplayComponent {
this.selectedAltUpperGroupRef.instance.style.display = 'none';
this.selectedAltLowerGroupRef.instance.style.display = 'none';
this.targetGroupRef.instance.style.display = 'none';
- this.selectedAltFailText.instance.style.display = 'block';
+ this.selectedAltFailed.set(true);
} else if (this.altitude.value - this.shownTargetAltitude.value > DisplayRange) {
this.selectedAltLowerGroupRef.instance.style.display = 'block';
this.selectedAltUpperGroupRef.instance.style.display = 'none';
this.targetGroupRef.instance.style.display = 'none';
- this.selectedAltFailText.instance.style.display = 'none';
+ this.selectedAltFailed.set(false);
} else if (this.altitude.value - this.shownTargetAltitude.value < -DisplayRange) {
this.targetGroupRef.instance.style.display = 'none';
this.selectedAltUpperGroupRef.instance.style.display = 'block';
this.selectedAltLowerGroupRef.instance.style.display = 'none';
- this.selectedAltFailText.instance.style.display = 'none';
+ this.selectedAltFailed.set(false);
} else {
this.selectedAltUpperGroupRef.instance.style.display = 'none';
this.selectedAltLowerGroupRef.instance.style.display = 'none';
this.targetGroupRef.instance.style.display = 'inline';
- this.selectedAltFailText.instance.style.display = 'none';
+ this.selectedAltFailed.set(false);
}
}
@@ -661,15 +667,11 @@ class SelectedAltIndicator extends DisplayComponent {
{this.textSub}
-
- ALT SEL
-
+
+
+ ALT SEL
+
+
>
);
}
@@ -685,6 +687,8 @@ class AltimeterIndicator extends DisplayComponent {
private text = Subject.create('');
+ private readonly shouldFlash = Subject.create(false);
+
private baroInhg = new Arinc429Word(0);
private baroHpa = new Arinc429Word(0);
@@ -701,11 +705,11 @@ class AltimeterIndicator extends DisplayComponent {
private flightPhase = 0;
- private stdGroup = FSComponent.createRef();
+ private stdVisible = Subject.create(false);
- private qfeGroup = FSComponent.createRef();
+ private altiSettingVisible = Subject.create(false);
- private qfeBorder = FSComponent.createRef();
+ private qfeBorderHidden = Subject.create(true);
onAfterRender(node: VNode): void {
super.onAfterRender(node);
@@ -788,39 +792,34 @@ class AltimeterIndicator extends DisplayComponent {
this.transLvlAr.isNormalOperation() &&
100 * this.transLvlAr.value > this.props.altitude.get()
) {
- this.stdGroup.instance.classList.add('BlinkInfinite');
+ this.shouldFlash.set(true);
} else {
- this.stdGroup.instance.classList.remove('BlinkInfinite');
+ this.shouldFlash.set(false);
}
} else if (
this.flightPhase <= 3 &&
this.transAltAr.isNormalOperation() &&
this.transAltAr.value < this.props.altitude.get()
) {
- this.qfeGroup.instance.classList.add('BlinkInfinite');
+ this.shouldFlash.set(true);
} else {
- this.qfeGroup.instance.classList.remove('BlinkInfinite');
+ this.shouldFlash.set(false);
}
}
private getText() {
if (this.baroInStd) {
this.mode.set('STD');
- this.stdGroup.instance.classList.remove('HiddenElement');
- this.qfeGroup.instance.classList.add('HiddenElement');
- this.qfeBorder.instance.classList.add('HiddenElement');
} else if (this.baroInQnh) {
this.mode.set('QNH');
- this.stdGroup.instance.classList.add('HiddenElement');
- this.qfeGroup.instance.classList.remove('HiddenElement');
- this.qfeBorder.instance.classList.add('HiddenElement');
} else {
this.mode.set('QFE');
- this.stdGroup.instance.classList.add('HiddenElement');
- this.qfeGroup.instance.classList.remove('HiddenElement');
- this.qfeBorder.instance.classList.remove('HiddenElement');
}
+ this.stdVisible.set(this.baroInStd);
+ this.altiSettingVisible.set(!this.baroInStd);
+ this.qfeBorderHidden.set(this.baroInStd || this.baroInQnh);
+
if (!this.baroInInhg) {
this.text.set(Math.round(this.baroHpa.value).toString());
} else {
@@ -831,17 +830,33 @@ class AltimeterIndicator extends DisplayComponent {
render(): VNode {
return (
<>
-
-
-
- STD
-
-
-
-
+
+
+
+
+ STD
+
+
+
+
+
+
@@ -851,7 +866,7 @@ class AltimeterIndicator extends DisplayComponent {
{this.text}
-
+
>
);
}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorFixed.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorFixed.tsx
index fc003adaf1b..00f3d3e4223 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorFixed.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorFixed.tsx
@@ -6,6 +6,7 @@ import { DisplayComponent, FSComponent, Subject, Subscribable, VNode } from '@mi
import { ArincEventBus, Arinc429Register, Arinc429Word, Arinc429WordData } from '@flybywiresim/fbw-sdk';
import { FgBus } from 'instruments/src/PFD/shared/FgBusProvider';
import { FcuBus } from 'instruments/src/PFD/shared/FcuBusProvider';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
import { FlightPathDirector } from './FlightPathDirector';
import { FlightPathVector } from './FlightPathVector';
@@ -99,7 +100,7 @@ export class AttitudeIndicatorFixedCenter extends DisplayComponent
-
- ATT
-
+
+
+ ATT
+
+
+
@@ -283,7 +281,15 @@ class FlightDirector extends DisplayComponent<{ bus: ArincEventBus }> {
private verticalRef2 = FSComponent.createRef();
- private fdFlagVisibleSub = Subject.create('hidden');
+ private readonly fdFlagVisibleSub = Subject.create(false);
+
+ private readonly lateralShouldFlash = Subject.create(false);
+
+ private readonly longitudinalShouldFlash = Subject.create(false);
+
+ private readonly lateralVisible = Subject.create(false);
+
+ private readonly longitudinalVisible = Subject.create(false);
private handleFdState() {
const fdOff = this.fcuEisDiscreteWord2.bitValueOr(23, false);
@@ -297,14 +303,12 @@ class FlightDirector extends DisplayComponent<{ bus: ArincEventBus }> {
if (showRoll) {
const FDRollOffset = Math.min(Math.max(this.fdRollCommand.value, -45), 45) * 0.44;
- this.lateralRef1.instance.setAttribute('visibility', 'visible');
+ this.lateralVisible.set(true);
this.lateralRef1.instance.style.transform = `translate3d(${FDRollOffset}px, 0px, 0px)`;
- this.lateralRef2.instance.setAttribute('visibility', 'visible');
this.lateralRef2.instance.style.transform = `translate3d(${FDRollOffset}px, 0px, 0px)`;
} else {
- this.lateralRef1.instance.setAttribute('visibility', 'hidden');
- this.lateralRef2.instance.setAttribute('visibility', 'hidden');
+ this.lateralVisible.set(false);
}
const showPitch =
@@ -313,14 +317,12 @@ class FlightDirector extends DisplayComponent<{ bus: ArincEventBus }> {
if (showPitch) {
const FDPitchOffset = Math.min(Math.max(this.fdPitchCommand.value, -22.5), 22.5) * 0.89;
- this.verticalRef1.instance.setAttribute('visibility', 'visible');
+ this.longitudinalVisible.set(true);
this.verticalRef1.instance.style.transform = `translate3d(0px, ${FDPitchOffset}px, 0px)`;
- this.verticalRef2.instance.setAttribute('visibility', 'visible');
this.verticalRef2.instance.style.transform = `translate3d(0px, ${FDPitchOffset}px, 0px)`;
} else {
- this.verticalRef1.instance.setAttribute('visibility', 'hidden');
- this.verticalRef2.instance.setAttribute('visibility', 'hidden');
+ this.longitudinalVisible.set(false);
}
const onGround = this.leftMainGearCompressed || this.rightMainGearCompressed;
@@ -331,9 +333,9 @@ class FlightDirector extends DisplayComponent<{ bus: ArincEventBus }> {
this.fdPitchCommand.isFailureWarning() ||
(this.fdYawCommand.isFailureWarning() && onGround))
) {
- this.fdFlagVisibleSub.set('block');
+ this.fdFlagVisibleSub.set(true);
} else {
- this.fdFlagVisibleSub.set('none');
+ this.fdFlagVisibleSub.set(false);
}
}
@@ -341,21 +343,8 @@ class FlightDirector extends DisplayComponent<{ bus: ArincEventBus }> {
const fdRollBarFlashing = this.fmgcDiscreteWord2.bitValueOr(28, false);
const fdPitchBarFlashing = this.fmgcDiscreteWord5.bitValueOr(24, false);
- if (fdRollBarFlashing) {
- this.lateralRef1.instance.classList.add('BlinkInfinite');
- this.lateralRef2.instance.classList.add('BlinkInfinite');
- } else {
- this.lateralRef1.instance.classList.remove('BlinkInfinite');
- this.lateralRef2.instance.classList.remove('BlinkInfinite');
- }
-
- if (fdPitchBarFlashing) {
- this.verticalRef1.instance.classList.add('BlinkInfinite');
- this.verticalRef2.instance.classList.add('BlinkInfinite');
- } else {
- this.verticalRef1.instance.classList.remove('BlinkInfinite');
- this.verticalRef2.instance.classList.remove('BlinkInfinite');
- }
+ this.lateralShouldFlash.set(fdRollBarFlashing);
+ this.longitudinalShouldFlash.set(fdPitchBarFlashing);
}
onAfterRender(node: VNode): void {
@@ -455,25 +444,48 @@ class FlightDirector extends DisplayComponent<{ bus: ArincEventBus }> {
render(): VNode | null {
return (
-
-
-
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
- FD
-
+
+
+
+
+
+ FD
+
+
);
}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorHorizon.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorHorizon.tsx
index 67926919755..139dda64364 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorHorizon.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/AttitudeIndicatorHorizon.tsx
@@ -23,6 +23,7 @@ import { PFDSimvars } from './shared/PFDSimvarPublisher';
import { Arinc429Values } from './shared/ArincValueProvider';
import { HorizontalTape } from './HorizontalTape';
import { getDisplayIndex } from './PFD';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
const DisplayRange = 35;
const DistanceSpacing = 15;
@@ -443,11 +444,13 @@ class RadioAltAndDH extends DisplayComponent<{
private altitude = new Arinc429Word(0);
- private attDhText = FSComponent.createRef();
+ private readonly attDhTextVisible = Subject.create(false);
private radioAltText = Subject.create('0');
- private radioAlt = FSComponent.createRef();
+ private readonly radioAltVisible = Subject.create(true);
+
+ private readonly raFlagFlashing = Subject.create(false);
private classSub = Subject.create('');
@@ -488,7 +491,7 @@ class RadioAltAndDH extends DisplayComponent<{
sub.on('chosenRa').handle((ra) => {
if (!this.props.attExcessive.get()) {
this.radioAltitude = ra;
- const raFailed = !this.radioAltitude.isFailureWarning();
+ const raNotFailed = !this.radioAltitude.isFailureWarning();
const raHasData = !this.radioAltitude.isNoComputedData();
const raValue = this.filteredRadioAltitude;
const verticalOffset = calculateVerticalOffsetFromRoll(this.roll.value);
@@ -506,7 +509,7 @@ class RadioAltAndDH extends DisplayComponent<{
let color = 'Amber';
if (raHasData) {
- if (raFailed) {
+ if (raNotFailed) {
if (raValue < 2500) {
if (raValue > 400 || (raValue > dh.value + 100 && DHValid)) {
color = 'Green';
@@ -523,16 +526,18 @@ class RadioAltAndDH extends DisplayComponent<{
}
}
} else {
- color = belowTransitionAltitude ? 'Red Blink9Seconds' : 'Red';
+ color = 'Red';
text = 'RA';
}
}
+ this.raFlagFlashing.set(!raNotFailed && belowTransitionAltitude);
+
this.daRaGroup.instance.style.transform = `translate3d(0px, ${-verticalOffset}px, 0px)`;
- if (raFailed && DHValid && raValue <= dh.value) {
- this.attDhText.instance.style.visibility = 'visible';
+ if (raNotFailed && DHValid && raValue <= dh.value) {
+ this.attDhTextVisible.set(true);
} else {
- this.attDhText.instance.style.visibility = 'hidden';
+ this.attDhTextVisible.set(false);
}
this.radioAltText.set(text);
this.classSub.set(`${size} ${color} MiddleAlign TextOutline`);
@@ -545,9 +550,9 @@ class RadioAltAndDH extends DisplayComponent<{
this.props.attExcessive.sub((ae) => {
if (ae) {
- this.radioAlt.instance.style.visibility = 'hidden';
+ this.radioAltVisible.set(false);
} else {
- this.radioAlt.instance.style.visibility = 'visible';
+ this.radioAltVisible.set(true);
}
});
@@ -557,18 +562,22 @@ class RadioAltAndDH extends DisplayComponent<{
render(): VNode {
return (
-
+
+ DH
+
+
+
+
- DH
-
-
- {this.radioAltText}
-
+
+ {this.radioAltText}
+
+
);
}
@@ -590,7 +599,7 @@ class SideslipIndicator extends DisplayComponent {
private slideSlip = FSComponent.createRef();
- private siFailFlag = FSComponent.createRef();
+ private readonly siFlagVisible = Subject.create(false);
private onGround = true;
@@ -684,10 +693,10 @@ class SideslipIndicator extends DisplayComponent {
(!this.onGround && this.latAcc.isFailureWarning() && this.beta.isFailureWarning())
) {
this.slideSlip.instance.style.visibility = 'hidden';
- this.siFailFlag.instance.style.display = 'block';
+ this.siFlagVisible.set(true);
} else {
this.slideSlip.instance.style.visibility = 'visible';
- this.siFailFlag.instance.style.display = 'none';
+ this.siFlagVisible.set(false);
}
if (
@@ -720,15 +729,11 @@ class SideslipIndicator extends DisplayComponent {
class={this.classNameSub}
d="m73.974 47.208-1.4983-2.2175h-7.0828l-1.4983 2.2175z"
/>
-
- SI
-
+
+
+ SI
+
+
);
}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/FMA.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/FMA.tsx
index aeadd848398..924004e988a 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/FMA.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/FMA.tsx
@@ -18,6 +18,8 @@ import { FgBus } from 'instruments/src/PFD/shared/FgBusProvider';
import { FcuBus } from 'instruments/src/PFD/shared/FcuBusProvider';
import { Arinc429Values } from './shared/ArincValueProvider';
import { PFDSimvars } from './shared/PFDSimvarPublisher';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
+import { ExtendedClockEvents } from 'instruments/src/MsfsAvionicsCommon/providers/ExtendedClockProvider';
/* eslint-disable no-constant-condition,no-dupe-else-if -- for keeping the FMA code while it's not active yet */
@@ -393,7 +395,7 @@ class A2Cell extends DisplayComponent<{ bus: ArincEventBus }> {
}
handleMessage(): void {
- const [_isShown, isTwoLine, _text] = getA1A2CellText(
+ const [_isShown, isTwoLine, _text, _amberFlashingBox] = getA1A2CellText(
this.fcuAtsDiscreteWord,
this.fcuAtsFmaDiscreteWord,
0,
@@ -464,7 +466,7 @@ class Row3 extends DisplayComponent<{
-
+
);
@@ -477,13 +479,14 @@ function getA1A2CellText(
flexTemp: number,
autoBrakeMode: number,
autoBrakeActive: boolean,
-): [boolean, boolean, string] {
+): [boolean, boolean, string, boolean] {
const atEngaged = fcuAtsDiscreteWord.bitValueOr(13, false);
const atActive = fcuAtsDiscreteWord.bitValueOr(14, false);
let text = '';
let isShown = true;
let isTwoLine = false;
+ let amberFlashingBox = false;
if (fcuAtsFmaDiscreteWord.bitValueOr(11, false)) {
isShown = false;
@@ -540,16 +543,12 @@ function getA1A2CellText(
`;
} else if (fcuAtsFmaDiscreteWord.bitValueOr(17, false)) {
isShown = false;
- text = `
-
- A.FLOOR
- `;
+ amberFlashingBox = true;
+ text = 'A.FLOOR ';
} else if (fcuAtsFmaDiscreteWord.bitValueOr(18, false)) {
isShown = false;
- text = `
-
- TOGA LK
- `;
+ amberFlashingBox = true;
+ text = 'TOGA LK ';
} else if (fcuAtsFmaDiscreteWord.bitValueOr(19, false)) {
text = 'SPEED ';
} else if (fcuAtsFmaDiscreteWord.bitValueOr(20, false)) {
@@ -582,7 +581,7 @@ function getA1A2CellText(
isShown = false;
}
- return [isShown, isTwoLine, text];
+ return [isShown, isTwoLine, text, amberFlashingBox];
}
interface CellProps extends ComponentProps {
@@ -596,6 +595,8 @@ class A1A2Cell extends ShowForSecondsComponent {
private cellRef = FSComponent.createRef();
+ private readonly amberFlashingBox = Subject.create(false);
+
private flexTemp = 0;
private autoBrakeActive = false;
@@ -607,7 +608,7 @@ class A1A2Cell extends ShowForSecondsComponent {
}
private setText() {
- const [isShown, _isTwoLine, text] = getA1A2CellText(
+ const [isShown, _isTwoLine, text, amberFlashingBox] = getA1A2CellText(
this.fcuAtsDiscreteWord,
this.fcuAtsFmaDiscreteWord,
this.flexTemp,
@@ -624,6 +625,8 @@ class A1A2Cell extends ShowForSecondsComponent {
}
this.cellRef.instance.innerHTML = text;
+
+ this.amberFlashingBox.set(amberFlashingBox);
}
onAfterRender(node: VNode): void {
@@ -681,6 +684,9 @@ class A1A2Cell extends ShowForSecondsComponent {
d="m3.3 1.8143h27.127v6.0476h-27.127z"
/>
+
+
+
);
}
@@ -700,18 +706,23 @@ const getA3Message = (
let text: string;
let className: string;
+ let flashingClassName = null;
if (thrLocked) {
text = 'THR LK';
- className = 'Amber BlinkInfinite';
+ className = 'Amber';
+ flashingClassName = '';
} else if (false) {
text = 'LVR TOGA';
- className = 'White BlinkInfinite';
+ className = 'White';
+ flashingClassName = '';
} else if (clbDemand) {
text = 'LVR CLB';
- className = 'White BlinkInfinite';
+ className = 'White';
+ flashingClassName = '';
} else if (mctDemand) {
text = 'LVR MCT';
- className = 'White BlinkInfinite';
+ className = 'White';
+ flashingClassName = '';
} else if (assymThrust) {
text = 'LVR ASYM';
className = 'Amber';
@@ -719,10 +730,10 @@ const getA3Message = (
text = 'BRK MAX';
className = 'FontMediumSmaller MiddleAlign Cyan';
} else {
- return [null, null];
+ return [null, null, null];
}
- return [text, className];
+ return [text, className, flashingClassName];
};
interface A3CellProps extends CellProps {
@@ -734,12 +745,15 @@ class A3Cell extends DisplayComponent {
private textSub = Subject.create('');
+ private readonly shouldFlash = Subject.create(false);
+
private updateMessage() {
const className = this.props.A3Message.get()[1];
const text = this.props.A3Message.get()[0];
this.textSub.set(text);
this.classSub.set(`FontMedium MiddleAlign ${className}`);
+ this.shouldFlash.set(this.props.A3Message.get()[2] !== null);
}
onAfterRender(node: VNode): void {
@@ -750,9 +764,11 @@ class A3Cell extends DisplayComponent {
render(): VNode {
return (
-
- {this.textSub}
-
+
+
+ {this.textSub}
+
+
);
}
}
@@ -821,9 +837,7 @@ class B1Cell extends ShowForSecondsComponent {
private readonly inSpeedProtection = Subject.create(false);
- private speedProtectionPathRef = FSComponent.createRef();
-
- private inModeReversionPathRef = FSComponent.createRef();
+ private readonly inModeReversion = Subject.create(false);
private fmaTextRef = FSComponent.createRef();
@@ -961,17 +975,7 @@ class B1Cell extends ShowForSecondsComponent {
this.boxClassSub.set('NormalStroke White');
}
- if (longitudinalModeReversion) {
- this.inModeReversionPathRef.instance.setAttribute('visibility', 'visible');
- } else {
- this.inModeReversionPathRef.instance.setAttribute('visibility', 'hidden');
- }
-
- if (inSpeedProtection) {
- this.speedProtectionPathRef.instance.setAttribute('visibility', 'visible');
- } else {
- this.speedProtectionPathRef.instance.setAttribute('visibility', 'hidden');
- }
+ this.inModeReversion.set(longitudinalModeReversion);
const bigBoxDisplayed = tcasMode && this.fmgcDiscreteWord7.bitValueOr(18, false);
const boxPathString =
@@ -995,7 +999,7 @@ class B1Cell extends ShowForSecondsComponent {
onAfterRender(node: VNode): void {
super.onAfterRender(node);
- const sub = this.props.bus.getSubscriber();
+ const sub = this.props.bus.getSubscriber();
sub
.on('fmgcDiscreteWord1')
@@ -1067,16 +1071,13 @@ class B1Cell extends ShowForSecondsComponent {
-
-
+
+
+
+
+
+
+
{
y="7.1040988"
>
{this.verticalText}
-
- {this.additionalText}
-
+ {this.additionalText}
+
);
@@ -1482,6 +1483,8 @@ const getBC3Message = (
let text: string;
let className: string;
+ let flashingClassName1 = '';
+ let flashingClassName2 = '';
// All currently unused message are set to false
if (
!fcdcWord1.bitValue(11) &&
@@ -1492,69 +1495,85 @@ const getBC3Message = (
flightPhaseForWarning
) {
text = 'MAN PITCH TRIM ONLY';
- className = 'FontSmall Red Blink9Seconds';
+ className = 'FontSmall';
+ flashingClassName1 = 'Red Fill';
+ flashingClassName2 = 'HiddenElement';
} else if (fcdcWord1.bitValue(15) && !fcdcWord1.isFailureWarning() && flightPhaseForWarning) {
text = 'USE MAN PITCH TRIM';
- className = 'FontSmall PulseAmber9Seconds Amber';
+ className = 'FontSmall';
+ flashingClassName1 = 'Amber Fill';
+ flashingClassName2 = 'DimmedAmber Fill';
} else if (false) {
text = 'FOR GA: SET TOGA';
- className = 'FontMedium PulseAmber9Seconds Amber';
+ className = 'FontMedium';
+ flashingClassName1 = 'Amber Fill';
+ flashingClassName2 = 'DimmedAmber Fill';
} else if (TCASArmed && !isAttExcessive) {
text = 'TCAS ';
className = 'FontMediumSmaller Cyan';
} else if (false) {
text = 'DISCONNECT AP FOR LDG';
- className = 'FontMedium PulseAmber9Seconds Amber';
+ className = 'FontMedium';
+ flashingClassName1 = 'Amber Fill';
+ flashingClassName2 = 'DimmedAmber Fill';
} else if (tcasRaInhibited && !isAttExcessive) {
text = 'TCAS RA INHIBITED';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (trkFpaDeselectedTCAS && !isAttExcessive) {
text = 'TRK FPA DESELECTED';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (false) {
text = 'SET GREEN DOT SPEED';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (tdReached) {
text = 'T/D REACHED';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (false) {
text = 'MORE DRAG';
className = 'FontMedium White';
} else if (checkSpeedMode && !isAttExcessive) {
text = 'CHECK SPEED MODE';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (false) {
text = 'CHECK APPR SELECTION';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (false) {
text = 'TURN AREA EXCEEDANCE';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (setHoldSpeed) {
text = 'SET HOLD SPEED';
- className = 'FontMedium White';
+ className = 'FontMedium White Fill';
} else if (false) {
text = 'VERT DISCONT AHEAD';
- className = 'FontMedium Amber';
+ className = 'FontMedium Amber Fill';
} else if (false) {
text = 'FINAL APP SELECTED';
- className = 'FontSmall White';
+ className = 'FontSmall White Fill';
} else {
- return [null, null];
+ return [null, null, flashingClassName1, flashingClassName2];
}
- return [text, className];
+ return [text, className, flashingClassName1, flashingClassName2];
};
-class BC3Cell extends DisplayComponent<{ BC3Message: Subscribable }> {
+class BC3Cell extends DisplayComponent<{ BC3Message: Subscribable } & CellProps> {
private bc3Cell = FSComponent.createRef();
- private classNameSub = Subject.create('');
+ private readonly normalClassNames = Subject.create('');
+
+ private readonly flashingClassName1 = Subject.create('');
+
+ private readonly flashingClassName2 = Subject.create('');
+
+ private readonly isFlashing = Subject.create(false);
private fillBC3Cell() {
- const className = this.props.BC3Message.get()[1];
- const text = this.props.BC3Message.get()[0];
+ this.normalClassNames.set(`${this.props.BC3Message.get()[1]} MiddleAlign`);
+ this.flashingClassName1.set(this.props.BC3Message.get()[2]);
+ this.flashingClassName2.set(this.props.BC3Message.get()[3]);
+ this.isFlashing.set(this.props.BC3Message.get()[2] !== '');
- this.classNameSub.set(`MiddleAlign ${className}`);
+ const text = this.props.BC3Message.get()[0];
if (text !== null) {
this.bc3Cell.instance.innerHTML = text;
} else {
@@ -1571,7 +1590,17 @@ class BC3Cell extends DisplayComponent<{ BC3Message: Subscribable }> {
}
render(): VNode {
- return ;
+ return (
+
+
+
+ );
}
}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathDirector.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathDirector.tsx
index 23514a7a5e9..fccc7062251 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathDirector.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathDirector.tsx
@@ -2,7 +2,7 @@
//
// SPDX-License-Identifier: GPL-3.0
-import { ClockEvents, DisplayComponent, FSComponent, Subscribable, VNode } from '@microsoft/msfs-sdk';
+import { ClockEvents, DisplayComponent, FSComponent, Subject, Subscribable, VNode } from '@microsoft/msfs-sdk';
import { ArincEventBus, Arinc429Word, Arinc429WordData } from '@flybywiresim/fbw-sdk';
import { FcuBus } from 'instruments/src/PFD/shared/FcuBusProvider';
import { FgBus } from 'instruments/src/PFD/shared/FgBusProvider';
@@ -10,6 +10,7 @@ import { FgBus } from 'instruments/src/PFD/shared/FgBusProvider';
import { calculateHorizonOffsetFromPitch } from './PFDUtils';
import { Arinc429Values } from './shared/ArincValueProvider';
import { PFDSimvars } from './shared/PFDSimvarPublisher';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
const DistanceSpacing = 15;
const ValueSpacing = 10;
@@ -48,12 +49,14 @@ export class FlightPathDirector extends DisplayComponent<{
private needsUpdate = false;
- private isVisible = false;
+ private readonly isVisible = Subject.create(false);
private birdPath = FSComponent.createRef();
private birdPathWings = FSComponent.createRef();
+ private readonly shouldFlash = Subject.create(false);
+
onAfterRender(node: VNode): void {
super.onAfterRender(node);
@@ -133,7 +136,7 @@ export class FlightPathDirector extends DisplayComponent<{
sub.on('realTime').handle((_t) => {
this.handlePath();
- if (this.needsUpdate && this.isVisible) {
+ if (this.needsUpdate && this.isVisible.get()) {
this.moveBird();
}
});
@@ -159,15 +162,15 @@ export class FlightPathDirector extends DisplayComponent<{
this.props.isAttExcessive.get()
) {
this.birdPath.instance.style.visibility = 'hidden';
- this.isVisible = false;
+ this.isVisible.set(false);
} else {
this.birdPath.instance.style.visibility = 'visible';
- this.isVisible = true;
+ this.isVisible.set(true);
}
}
private moveBird() {
- if (this.isVisible) {
+ if (this.isVisible.get()) {
const FDRollOrder = this.data.rollFdCommand.value;
const FDRollOrderLim = Math.max(Math.min(FDRollOrder, 45), -45);
const FDPitchOrder = this.data.pitchFdCommand.value;
@@ -196,11 +199,7 @@ export class FlightPathDirector extends DisplayComponent<{
const fdRollBarFlashing = this.fmgcDiscreteWord2.bitValueOr(28, false);
const fdPitchBarFlashing = this.fmgcDiscreteWord5.bitValueOr(24, false);
- if (fdRollBarFlashing || fdPitchBarFlashing) {
- this.birdPathWings.instance.classList.add('BlinkInfinite');
- } else {
- this.birdPathWings.instance.classList.remove('BlinkInfinite');
- }
+ this.shouldFlash.set(fdRollBarFlashing || fdPitchBarFlashing);
}
render(): VNode {
@@ -215,18 +214,25 @@ export class FlightPathDirector extends DisplayComponent<{
viewBox="0 0 31 31"
xmlns="http://www.w3.org/2000/svg"
>
-
-
-
-
+
+
+
+
+
+
);
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathVector.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathVector.tsx
index f7b7e9a4f8c..d13e7af9b2c 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathVector.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/FlightPathVector.tsx
@@ -2,13 +2,14 @@
//
// SPDX-License-Identifier: GPL-3.0
-import { ClockEvents, DisplayComponent, FSComponent, VNode } from '@microsoft/msfs-sdk';
+import { ClockEvents, DisplayComponent, FSComponent, Subject, VNode } from '@microsoft/msfs-sdk';
import { ArincEventBus, Arinc429Word, Arinc429WordData } from '@flybywiresim/fbw-sdk';
import { FcuBus } from 'instruments/src/PFD/shared/FcuBusProvider';
import { calculateHorizonOffsetFromPitch } from './PFDUtils';
import { Arinc429Values } from './shared/ArincValueProvider';
import { PFDSimvars } from './shared/PFDSimvarPublisher';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
const DistanceSpacing = 15;
const ValueSpacing = 10;
@@ -23,7 +24,7 @@ interface FlightPathVectorData {
export class FlightPathVector extends DisplayComponent<{ bus: ArincEventBus }> {
private bird = FSComponent.createRef();
- private fpvFlag = FSComponent.createRef();
+ private readonly fpvFlagVisible = Subject.create(false);
private fcuDiscreteWord1 = new Arinc429Word(0);
@@ -76,14 +77,14 @@ export class FlightPathVector extends DisplayComponent<{ bus: ArincEventBus }> {
const trkFpaActive = this.fcuDiscreteWord1.bitValueOr(25, true);
const daAndFpaValid = this.data.fpa.isNormalOperation() && this.data.da.isNormalOperation();
if (trkFpaActive && daAndFpaValid) {
- this.fpvFlag.instance.style.visibility = 'hidden';
+ this.fpvFlagVisible.set(false);
this.bird.instance.classList.remove('HiddenElement');
this.moveBird();
} else if (!trkFpaActive) {
- this.fpvFlag.instance.style.visibility = 'hidden';
+ this.fpvFlagVisible.set(false);
this.bird.instance.classList.add('HiddenElement');
} else if (trkFpaActive && this.data.pitch.isNormalOperation() && this.data.roll.isNormalOperation()) {
- this.fpvFlag.instance.style.visibility = 'visible';
+ this.fpvFlagVisible.set(true);
this.bird.instance.classList.add('HiddenElement');
}
}
@@ -132,16 +133,11 @@ export class FlightPathVector extends DisplayComponent<{ bus: ArincEventBus }> {
-
- FPV
-
+
+
+ FPV
+
+
>
);
}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/HeadingIndicator.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/HeadingIndicator.tsx
index 91da4573f05..f0133c4110f 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/HeadingIndicator.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/HeadingIndicator.tsx
@@ -11,6 +11,7 @@ import { HorizontalTape } from './HorizontalTape';
import { getSmallestAngle } from './PFDUtils';
import { PFDSimvars } from './shared/PFDSimvarPublisher';
import { Arinc429Values } from './shared/ArincValueProvider';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
const DisplayRange = 24;
const DistanceSpacing = 7.555;
@@ -57,6 +58,8 @@ export class HeadingOfftape extends DisplayComponent<{ bus: ArincEventBus; faile
private abnormalRef = FSComponent.createRef();
+ private readonly hdgFlagVisible = Subject.create(false);
+
private heading = Subject.create(0);
private ILSCourse = Subject.create(0);
@@ -77,9 +80,11 @@ export class HeadingOfftape extends DisplayComponent<{ bus: ArincEventBus; faile
if (word.isNormalOperation()) {
this.normalRef.instance.style.visibility = 'visible';
this.abnormalRef.instance.style.visibility = 'hidden';
+ this.hdgFlagVisible.set(false);
} else {
this.normalRef.instance.style.visibility = 'hidden';
this.abnormalRef.instance.style.visibility = 'visible';
+ this.hdgFlagVisible.set(true);
}
});
@@ -104,9 +109,11 @@ export class HeadingOfftape extends DisplayComponent<{ bus: ArincEventBus; faile
-
- HDG
-
+
+
+ HDG
+
+
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/SpeedIndicator.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/SpeedIndicator.tsx
index 750a4e4825e..721e248e001 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/SpeedIndicator.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/SpeedIndicator.tsx
@@ -19,6 +19,7 @@ import { FcuBus } from 'instruments/src/PFD/shared/FcuBusProvider';
import { PFDSimvars } from './shared/PFDSimvarPublisher';
import { VerticalTape } from './VerticalTape';
import { Arinc429Values } from './shared/ArincValueProvider';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
const ValueSpacing = 10;
const DistanceSpacing = 10;
@@ -153,6 +154,8 @@ export class AirspeedIndicator extends DisplayComponent
private failedGroup: NodeReference = FSComponent.createRef();
+ private readonly spdFlagVisible = Subject.create(false);
+
private showBarsRef = FSComponent.createRef();
private vfeNext = FSComponent.createRef();
@@ -183,9 +186,11 @@ export class AirspeedIndicator extends DisplayComponent
if (Number.isNaN(airspeedValue)) {
this.speedTapeElements.instance.classList.add('HiddenElement');
this.failedGroup.instance.classList.remove('HiddenElement');
+ this.spdFlagVisible.set(true);
} else {
this.speedTapeElements.instance.classList.remove('HiddenElement');
this.failedGroup.instance.classList.add('HiddenElement');
+ this.spdFlagVisible.set(false);
}
const length =
@@ -252,9 +257,12 @@ export class AirspeedIndicator extends DisplayComponent
<>
-
- SPD
-
+
+
+ SPD
+
+
+
@@ -381,7 +389,7 @@ export class AirspeedIndicatorOfftape extends DisplayComponent<{ bus: ArincEvent
private decelRef = FSComponent.createRef();
- private spdLimFlagRef = FSComponent.createRef();
+ private readonly spdLimFlagVisible = Subject.create(false);
private onGround = true;
@@ -465,9 +473,9 @@ export class AirspeedIndicatorOfftape extends DisplayComponent<{ bus: ArincEvent
.whenChanged()
.handle((a) => {
if (a === 0) {
- this.spdLimFlagRef.instance.style.visibility = 'visible';
+ this.spdLimFlagVisible.set(true);
} else {
- this.spdLimFlagRef.instance.style.visibility = 'hidden';
+ this.spdLimFlagVisible.set(false);
}
});
}
@@ -491,14 +499,14 @@ export class AirspeedIndicatorOfftape extends DisplayComponent<{ bus: ArincEvent
/>
-
-
+
+
SPD
-
+
LIM
-
+
>
);
@@ -992,7 +1000,7 @@ interface SpeedStateInfo {
}
class SpeedTarget extends DisplayComponent<{ bus: ArincEventBus }> {
- private spdSelFlagRef = FSComponent.createRef();
+ private readonly spdSelFlagVisible = Subject.create(false);
private upperBoundRef = FSComponent.createRef();
@@ -1110,36 +1118,36 @@ class SpeedTarget extends DisplayComponent<{ bus: ArincEventBus }> {
this.lowerBoundRef.instance.style.visibility = 'hidden';
this.upperBoundRef.instance.style.visibility = 'hidden';
this.speedTargetRef.instance.style.visibility = 'hidden';
- this.spdSelFlagRef.instance.style.display = 'block';
+ this.spdSelFlagVisible.set(true);
} else if (spdSelNcd) {
this.lowerBoundRef.instance.style.visibility = 'hidden';
this.upperBoundRef.instance.style.visibility = 'hidden';
this.speedTargetRef.instance.style.visibility = 'hidden';
- this.spdSelFlagRef.instance.style.display = 'none';
+ this.spdSelFlagVisible.set(false);
} else if (this.speedState.speed.value - currentTargetSpeed < -DisplayRange) {
this.upperBoundRef.instance.style.visibility = 'visible';
this.lowerBoundRef.instance.style.visibility = 'hidden';
this.speedTargetRef.instance.style.visibility = 'hidden';
- this.spdSelFlagRef.instance.style.display = 'none';
+ this.spdSelFlagVisible.set(false);
this.currentVisible = this.upperBoundRef;
} else if (this.speedState.speed.value - currentTargetSpeed > DisplayRange && !this.decelActive) {
this.lowerBoundRef.instance.style.visibility = 'visible';
this.upperBoundRef.instance.style.visibility = 'hidden';
this.speedTargetRef.instance.style.visibility = 'hidden';
- this.spdSelFlagRef.instance.style.display = 'none';
+ this.spdSelFlagVisible.set(false);
this.currentVisible = this.lowerBoundRef;
} else if (Math.abs(this.speedState.speed.value - currentTargetSpeed) < DisplayRange) {
this.lowerBoundRef.instance.style.visibility = 'hidden';
this.upperBoundRef.instance.style.visibility = 'hidden';
this.speedTargetRef.instance.style.visibility = 'visible';
- this.spdSelFlagRef.instance.style.display = 'none';
+ this.spdSelFlagVisible.set(false);
this.currentVisible = this.speedTargetRef;
inRange = true;
} else {
this.lowerBoundRef.instance.style.visibility = 'hidden';
this.upperBoundRef.instance.style.visibility = 'hidden';
this.speedTargetRef.instance.style.visibility = 'hidden';
- this.spdSelFlagRef.instance.style.display = 'none';
+ this.spdSelFlagVisible.set(false);
}
return inRange;
}
@@ -1165,15 +1173,12 @@ class SpeedTarget extends DisplayComponent<{ bus: ArincEventBus }> {
>
{this.textSub}
-
- SPD SEL
-
+
+
+ SPD SEL
+
+
+
{
export class MachNumber extends DisplayComponent<{ bus: ArincEventBus }> {
private machTextSub = Subject.create('');
- private failedRef = FSComponent.createRef();
+ private readonly machFlagVisible = Subject.create(false);
private machHysteresis = false;
@@ -1306,13 +1311,13 @@ export class MachNumber extends DisplayComponent<{ bus: ArincEventBus }> {
lsDisplay;
if (hideMachDisplay) {
- this.failedRef.instance.style.visibility = 'hidden';
+ this.machFlagVisible.set(false);
this.machTextSub.set('');
} else if (!this.mach.isNormalOperation()) {
- this.failedRef.instance.style.visibility = 'visible';
+ this.machFlagVisible.set(true);
this.machTextSub.set('');
} else {
- this.failedRef.instance.style.visibility = 'hidden';
+ this.machFlagVisible.set(false);
const machPermille = Math.round(this.mach.value * 1000);
this.machTextSub.set(`.${machPermille}`);
}
@@ -1361,15 +1366,12 @@ export class MachNumber extends DisplayComponent<{ bus: ArincEventBus }> {
render(): VNode {
return (
<>
-
- MACH
-
+
+
+ MACH
+
+
+
{this.machTextSub}
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/VerticalSpeedIndicator.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/VerticalSpeedIndicator.tsx
index 4a204a920d6..296004fc29c 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/VerticalSpeedIndicator.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/VerticalSpeedIndicator.tsx
@@ -16,6 +16,7 @@ import { ArincEventBus, Arinc429Word } from '@flybywiresim/fbw-sdk';
import { Arinc429Values } from './shared/ArincValueProvider';
import { PFDSimvars } from './shared/PFDSimvarPublisher';
import { LagFilter } from './PFDUtils';
+import { FlashOneHertz } from 'instruments/src/MsfsAvionicsCommon/FlashingElementUtils';
interface VerticalSpeedIndicatorProps {
bus: ArincEventBus;
@@ -39,7 +40,7 @@ export class VerticalSpeedIndicator extends DisplayComponent();
+ private readonly vsFlagVisible = Subject.create(false);
private vsNormal = FSComponent.createRef();
@@ -127,10 +128,10 @@ export class VerticalSpeedIndicator extends DisplayComponent
-
-
+
+
V
-
+
/
-
+
S
-
+
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/instrument.tsx b/fbw-a32nx/src/systems/instruments/src/PFD/instrument.tsx
index 1acc0f43d98..b122e76883c 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/instrument.tsx
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/instrument.tsx
@@ -8,6 +8,7 @@ import { FwcPublisher, RopRowOansPublisher } from '@flybywiresim/msfs-avionics-c
import { FmsDataPublisher } from '../MsfsAvionicsCommon/providers/FmsDataPublisher';
import { DmcPublisher } from '../MsfsAvionicsCommon/providers/DmcPublisher';
+import { ExtendedClockEventProvider } from '../MsfsAvionicsCommon/providers/ExtendedClockProvider';
import { FcuBusProvider } from 'instruments/src/PFD/shared/FcuBusProvider';
import { FgBusProvider } from 'instruments/src/PFD/shared/FgBusProvider';
import { getDisplayIndex, PFDComponent } from './PFD';
@@ -48,6 +49,8 @@ class A32NX_PFD extends BaseInstrument {
private readonly fwcPublisher = new FwcPublisher(this.bus);
+ private readonly extendedClockProvider = new ExtendedClockEventProvider(this.bus);
+
/**
* "mainmenu" = 0
* "loading" = 1
@@ -68,6 +71,7 @@ class A32NX_PFD extends BaseInstrument {
this.backplane.addPublisher('Dmc', this.dmcPublisher);
this.backplane.addPublisher('RopRowOans', this.ropRowOansPublisher);
this.backplane.addPublisher('Fwc', this.fwcPublisher);
+ this.backplane.addInstrument('ExtendedClock', this.extendedClockProvider);
}
get templateID(): string {
diff --git a/fbw-a32nx/src/systems/instruments/src/PFD/style.scss b/fbw-a32nx/src/systems/instruments/src/PFD/style.scss
index 82fac194310..382a9892734 100644
--- a/fbw-a32nx/src/systems/instruments/src/PFD/style.scss
+++ b/fbw-a32nx/src/systems/instruments/src/PFD/style.scss
@@ -157,6 +157,10 @@ tspan.Cyan {
fill: $display-cyan;
stroke: none;
}
+.DimmedCyan.Fill {
+ fill: scale-color($display-cyan, $lightness: -30%);
+ stroke: none;
+}
.None {
fill: none;
@@ -203,6 +207,10 @@ text.Amber {
fill: $display-amber;
stroke: none;
}
+.DimmedAmber.Fill {
+ fill: scale-color($display-amber, $lightness: -30%);
+ stroke: none;
+}
.Yellow {
stroke: $display-yellow;
diff --git a/fbw-a32nx/src/systems/shared/src/publishers/A32NXFcuBusPublisher.ts b/fbw-a32nx/src/systems/shared/src/publishers/A32NXFcuBusPublisher.ts
new file mode 100644
index 00000000000..a4a07570d08
--- /dev/null
+++ b/fbw-a32nx/src/systems/shared/src/publishers/A32NXFcuBusPublisher.ts
@@ -0,0 +1,277 @@
+// Copyright (c) 2024 FlyByWire Simulations
+// SPDX-License-Identifier: GPL-3.0
+
+import {
+ EventBus,
+ IndexedEventType,
+ PublishPacer,
+ SimVarPublisher,
+ SimVarPublisherEntry,
+ SimVarValueType,
+} from '@microsoft/msfs-sdk';
+
+interface A32NXFcuBusBaseEvents {
+ /** The FCU selected heading. NCD if dashes or TRK/FPA mode. Raw ARINC word. */
+ a32nx_fcu_selected_heading: number;
+ /** The FCU selected altitude. Raw ARINC word. */
+ a32nx_fcu_selected_altitude: number;
+ /** The FCU selected CAS. NCD if dashes. Raw ARINC word. */
+ a32nx_fcu_selected_airspeed: number;
+ /** The FCU selected V/S. NCD if dashes or TRK/FPA mode. Raw ARINC word. */
+ a32nx_fcu_selected_vertical_speed: number;
+ /** The FCU selected track. NCD if dashes or HDG/VS mode. Raw ARINC word. */
+ a32nx_fcu_selected_track: number;
+ /** The FCU selected FPA. NCD if dashes or HDG/VS mode. Raw ARINC word. */
+ a32nx_fcu_selected_fpa: number;
+ /**
+ * FCU Autothrust System discrete word. Retransmitted from FMGC that has priority.
+ * Raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 13 | A/THR Engaged |
+ * | 14 | A/THR Active |
+ * | 17 | A/THR Instinctive Disconnect |
+ * | 18 | A/THR SPD MACH mode |
+ * | 19 | FCU Mach Selection |
+ * | 20 | RETARD Mode Active |
+ * | 21 | THRUST N1 Mode Active |
+ * | 22 | THRUST EPR Mode Active |
+ * | 23 | A/THR ALPHA FLOOR |
+ * | 24 | A/THR Inop |
+ * | 25 | A/THR Limited |
+ */
+ a32nx_fcu_ats_discrete_word: number;
+ /**
+ * FCU Autothrust System FMA discrete word. Retransmitted from FMGC that has priority.
+ * Raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | TO/GA Display |
+ * | 12 | MCT Display |
+ * | 13 | FLX Display |
+ * | 14 | CLB Display |
+ * | 15 | THR Display |
+ * | 16 | IDLE Display |
+ * | 17 | A.FLOOR Display |
+ * | 18 | TO/GA LK Display |
+ * | 19 | SPEED Display |
+ * | 20 | MACH Display |
+ * | 21 | ASYM Display |
+ * | 22 | CLB Demand Display |
+ * | 23 | MCT Demand Display |
+ */
+ a32nx_fcu_ats_fma_discrete_word: number;
+
+ /**
+ * Discrete word 1 for EIS left, raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | Baro is inHG |
+ * |12-24| Spare |
+ * | 25 | EFIS Range 10 |
+ * | 26 | EFIS Range 20 |
+ * | 27 | EFIS Range 40 |
+ * | 28 | EFIS Range 80 |
+ * | 29 | EFIS Range 160 |
+ * | | EFIS Range 320 if 25-29 false |
+ */
+ a32nx_fcu_eis_discrete_word_1_left: number;
+ /**
+ * Discrete word 1 for EIS right, raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | Baro is inHG |
+ * |12-24| Spare |
+ * | 25 | EFIS Range 10 |
+ * | 26 | EFIS Range 20 |
+ * | 27 | EFIS Range 40 |
+ * | 28 | EFIS Range 80 |
+ * | 29 | EFIS Range 160 |
+ * | | EFIS Range 320 if 25-29 false |
+ */
+ a32nx_fcu_eis_discrete_word_1_right: number;
+ /**
+ * Discrete word 2 for EIS left, raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | EFIS mode PLAN |
+ * | 12 | EFIS mode ARC |
+ * | 13 | EFIS mode ROSE NAV |
+ * | 14 | EFIS mode ROSE VOR |
+ * | 15 | EFIS mode ROSE ILS |
+ * | 16 | Spare |
+ * | 17 | EFIS Filter CSTR |
+ * | 18 | EFIS Filter WPT |
+ * | 19 | EFIS Filter VORD |
+ * | 20 | EFIS Filter NDB |
+ * | 21 | EFIS Filter ARPT |
+ * | 22 | LS Button On |
+ * | 23 | FD Button Off |
+ * | 24 | NAVAID 1 ADF |
+ * | 25 | NAVAID 2 ADF |
+ * | 26 | NAVAID 1 VOR |
+ * | 27 | NAVAID 2 VOR |
+ * | 28 | Baro on STD |
+ * | 29 | Baro on QNH |
+ */
+ a32nx_fcu_eis_discrete_word_2_left: number;
+ /**
+ * Discrete word 2 for EIS right, raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | EFIS mode PLAN |
+ * | 12 | EFIS mode ARC |
+ * | 13 | EFIS mode ROSE NAV |
+ * | 14 | EFIS mode ROSE VOR |
+ * | 15 | EFIS mode ROSE ILS |
+ * | 16 | Spare |
+ * | 17 | EFIS Filter CSTR |
+ * | 18 | EFIS Filter WPT |
+ * | 19 | EFIS Filter VORD |
+ * | 20 | EFIS Filter NDB |
+ * | 21 | EFIS Filter ARPT |
+ * | 22 | LS Button On |
+ * | 23 | FD Button Off |
+ * | 24 | NAVAID 1 ADF |
+ * | 25 | NAVAID 2 ADF |
+ * | 26 | NAVAID 1 VOR |
+ * | 27 | NAVAID 2 VOR |
+ * | 28 | Baro on STD |
+ * | 29 | Baro on QNH |
+ */
+ a32nx_fcu_eis_discrete_word_2_right: number;
+ /**
+ * FCU EIS Baro correction in inHg. Remains at previous value if in STD, and
+ * is at the inHG value corresponding to the selected hPa value if in hPa.
+ * Raw ARINC word.
+ */
+ a32nx_fcu_eis_baro_left: number;
+ /**
+ * FCU EIS Baro correction in inHg. Remains at previous value if in STD, and
+ * is at the inHG value corresponding to the selected hPa value if in hPa.
+ * Raw ARINC word.
+ */
+ a32nx_fcu_eis_baro_right: number;
+ /**
+ * FCU EIS Baro correction in hPa. Remains at previous value if in STD, and
+ * is at the hPa value corresponding to the selected inHG value if in inHG.
+ * Raw ARINC word.
+ */
+ a32nx_fcu_eis_baro_hpa_left: number;
+ /**
+ * FCU EIS Baro correction in hPa. Remains at previous value if in STD, and
+ * is at the hPa value corresponding to the selected inHG value if in inHG.
+ * Raw ARINC word.
+ */
+ a32nx_fcu_eis_baro_hpa_right: number;
+ /**
+ * FCU Discrete word 1. All pull/push bits are MTRIG processed for 0.1s to enabled
+ * async processing in other devices (FGMC, FWC etc.).
+ * Value changed bits are MTRIG processed for 0.5s.
+ * Raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | SPD/MACH Pushed |
+ * | 12 | SPD/MACH Pulled |
+ * | 13 | ALT Value changed |
+ * | 14 | VS/FPA Value changed |
+ * | 15 | SPD/MACH Value changed |
+ * | 16 | VS/FPA Pushed |
+ * | 17 | ALT Pushed |
+ * | 18 | ALT Pulled |
+ * | 19 | VS/FPA pulled |
+ * | 20 | Metric alt active |
+ * | 21 | SPD/MACH Switching button pushed |
+ * | 22 | EXPED Pushed |
+ * | 23 | APPR Pushed |
+ * | 24 | HDG/VS Active |
+ * | 25 | TRK/FPA Active |
+ * |26-29| Spare |
+ */
+ a32nx_fcu_discrete_word_1: number;
+ /**
+ * FCU Discrete word 2. All pull/push bits are MTRIG processed for 0.1s to enabled
+ * async processing in other devices (FGMC, FWC etc.).
+ * Value changed bits are MTRIG processed for 0.5s.
+ * Raw ARINC word.
+ * | Bit | Description |
+ * |:---:|:---------------------------------:|
+ * | 11 | HDG/TRK Pushed |
+ * | 12 | HDG/TRK Pulled |
+ * | 13 | LOC Pushed |
+ * | 14 | HDG/TRK Value changed |
+ * |15-19| Spare |
+ * | 20 | FMGC 1 selected (has priority) |
+ * | 21 | FMGC 2 selected (has priority) |
+ * |22-23| Spare |
+ * | 24 | FCU 1 Healthy |
+ * | 25 | FCU 2 Healthy |
+ * | 26 | FD 1 Button off |
+ * | 27 | FD 2 Button off |
+ * |28-29| Spare |
+ */
+ a32nx_fcu_discrete_word_2: number;
+}
+
+type IndexedTopics = null;
+
+type A32NXFcuBusIndexedEvents = {
+ [P in keyof Pick as IndexedEventType]: A32NXFcuBusBaseEvents[P];
+};
+
+interface A32NXFcuBusPublisherEvents extends A32NXFcuBusBaseEvents, A32NXFcuBusIndexedEvents {}
+
+/**
+ * Events for A32NX FCU bus local vars.
+ */
+export interface A32NXFcuBusEvents extends Omit, A32NXFcuBusIndexedEvents {}
+
+/**
+ * Publisher for A32NX FCU bus local vars.
+ */
+export class A32NXFcuBusPublisher extends SimVarPublisher {
+ /**
+ * Create a publisher.
+ * @param bus The EventBus to publish to
+ * @param pacer An optional pacer to use to control the rate of publishing
+ */
+ public constructor(bus: EventBus, pacer?: PublishPacer) {
+ const simvars = new Map>([
+ ['a32nx_fcu_selected_heading', { name: 'L:A32NX_FCU_SELECTED_HEADING', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_selected_altitude', { name: 'L:A32NX_FCU_SELECTED_ALTITUDE', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_selected_airspeed', { name: 'L:A32NX_FCU_SELECTED_AIRSPEED', type: SimVarValueType.Enum }],
+ [
+ 'a32nx_fcu_selected_vertical_speed',
+ { name: 'L:A32NX_FCU_SELECTED_VERTICAL_SPEED', type: SimVarValueType.Enum },
+ ],
+ ['a32nx_fcu_selected_track', { name: 'L:A32NX_FCU_SELECTED_TRACK', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_selected_fpa', { name: 'L:A32NX_FCU_SELECTED_FPA', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_ats_discrete_word', { name: 'L:A32NX_FCU_ATS_DISCRETE_WORD', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_ats_fma_discrete_word', { name: 'L:A32NX_FCU_ATS_FMA_DISCRETE_WORD', type: SimVarValueType.Enum }],
+ [
+ 'a32nx_fcu_eis_discrete_word_1_left',
+ { name: 'L:A32NX_FCU_LEFT_EIS_DISCRETE_WORD_1', type: SimVarValueType.Enum },
+ ],
+ [
+ 'a32nx_fcu_eis_discrete_word_1_right',
+ { name: 'L:A32NX_FCU_RIGHT_EIS_DISCRETE_WORD_1', type: SimVarValueType.Enum },
+ ],
+ [
+ 'a32nx_fcu_eis_discrete_word_2_left',
+ { name: 'L:A32NX_FCU_LEFT_EIS_DISCRETE_WORD_2', type: SimVarValueType.Enum },
+ ],
+ [
+ 'a32nx_fcu_eis_discrete_word_2_right',
+ { name: 'L:A32NX_FCU_RIGHT_EIS_DISCRETE_WORD_2', type: SimVarValueType.Enum },
+ ],
+ ['a32nx_fcu_eis_baro_left', { name: 'L:A32NX_FCU_LEFT_EIS_BARO', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_eis_baro_right', { name: 'L:A32NX_FCU_RIGHT_EIS_BARO', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_eis_baro_hpa_left', { name: 'L:A32NX_FCU_LEFT_EIS_BARO_HPA', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_eis_baro_hpa_right', { name: 'L:A32NX_FCU_RIGHT_EIS_BARO_HPA', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_discrete_word_1', { name: 'L:A32NX_FCU_DISCRETE_WORD_1', type: SimVarValueType.Enum }],
+ ['a32nx_fcu_discrete_word_2', { name: 'L:A32NX_FCU_DISCRETE_WORD_2', type: SimVarValueType.Enum }],
+ ]);
+
+ super(simvars, bus, pacer);
+ }
+}
diff --git a/fbw-a32nx/src/systems/systems-host/index.ts b/fbw-a32nx/src/systems/systems-host/index.ts
index 38afa459c5c..33210e739cf 100644
--- a/fbw-a32nx/src/systems/systems-host/index.ts
+++ b/fbw-a32nx/src/systems/systems-host/index.ts
@@ -2,18 +2,43 @@
//
// SPDX-License-Identifier: GPL-3.0
-import { EventBus, HEventPublisher } from '@microsoft/msfs-sdk';
+import {
+ Clock,
+ ClockEvents,
+ EventBus,
+ HEventPublisher,
+ InstrumentBackplane,
+ StallWarningPublisher,
+} from '@microsoft/msfs-sdk';
import { AtsuSystem } from './systems/atsu';
import { PowerSupplyBusses } from './systems/powersupply';
+import { PseudoFWC } from 'systems-host/systems/FWC/PseudoFWC';
+import { FuelSystemPublisher } from 'instruments/src/MsfsAvionicsCommon/providers/FuelSystemPublisher';
+import { A32NXFcuBusPublisher } from '@shared/publishers/A32NXFcuBusPublisher';
+import { PseudoFwcSimvarPublisher } from 'instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher';
class SystemsHost extends BaseInstrument {
- private readonly bus: EventBus;
+ private readonly bus = new EventBus();
- private readonly hEventPublisher: HEventPublisher;
+ private readonly backplane = new InstrumentBackplane();
- private readonly powerSupply: PowerSupplyBusses;
+ private readonly clock = new Clock(this.bus);
- private readonly atsu: AtsuSystem;
+ private readonly hEventPublisher = new HEventPublisher(this.bus);
+
+ private readonly powerSupply = new PowerSupplyBusses(this.bus);
+
+ private readonly atsu = new AtsuSystem(this.bus);
+
+ private readonly fuelSystemPublisher = new FuelSystemPublisher(this.bus);
+
+ private readonly stallWarningPublisher = new StallWarningPublisher(this.bus, 0.9);
+
+ private readonly a32nxFcuBusPublisher = new A32NXFcuBusPublisher(this.bus);
+
+ private readonly pseudoFwcPublisher = new PseudoFwcSimvarPublisher(this.bus);
+
+ private readonly pseudoFwc = new PseudoFWC(this.bus, this);
/**
* "mainmenu" = 0
@@ -26,10 +51,26 @@ class SystemsHost extends BaseInstrument {
constructor() {
super();
- this.bus = new EventBus();
- this.hEventPublisher = new HEventPublisher(this.bus);
- this.powerSupply = new PowerSupplyBusses(this.bus);
- this.atsu = new AtsuSystem(this.bus);
+ this.backplane.addInstrument('Clock', this.clock);
+ this.backplane.addInstrument('AtsuSystem', this.atsu);
+ this.backplane.addPublisher('FuelSystem', this.fuelSystemPublisher);
+ this.backplane.addPublisher('PowerPublisher', this.powerSupply);
+ this.backplane.addPublisher('stallWarning', this.stallWarningPublisher);
+ this.backplane.addPublisher('a32nxFcuBusPublisher', this.a32nxFcuBusPublisher);
+ this.backplane.addPublisher('PseudoFwcPublisher', this.pseudoFwcPublisher);
+
+ this.pseudoFwc.init();
+ let lastUpdateTime: number;
+ this.bus
+ .getSubscriber()
+ .on('simTimeHiFreq')
+ .atFrequency(50)
+ .handle((now) => {
+ const dt = lastUpdateTime === undefined ? 0 : now - lastUpdateTime;
+ lastUpdateTime = now;
+
+ this.pseudoFwc.update(dt);
+ });
}
get templateID(): string {
@@ -47,9 +88,6 @@ class SystemsHost extends BaseInstrument {
public connectedCallback(): void {
super.connectedCallback();
- this.powerSupply.connectedCallback();
- this.atsu.connectedCallback();
-
// Needed to fetch METARs from the sim
RegisterViewListener(
'JS_LISTENER_FACILITY',
@@ -58,6 +96,8 @@ class SystemsHost extends BaseInstrument {
},
true,
);
+
+ this.backplane.init();
}
public Update(): void {
@@ -67,14 +107,11 @@ class SystemsHost extends BaseInstrument {
const gamestate = this.getGameState();
if (gamestate === 3) {
this.hEventPublisher.startPublish();
- this.powerSupply.startPublish();
- this.atsu.startPublish();
}
this.gameState = gamestate;
}
- this.powerSupply.update();
- this.atsu.update();
+ this.backplane.onUpdate();
}
}
diff --git a/fbw-a32nx/src/systems/systems-host/systems/FWC/FwsSoundManager.ts b/fbw-a32nx/src/systems/systems-host/systems/FWC/FwsSoundManager.ts
new file mode 100644
index 00000000000..1010f16b25a
--- /dev/null
+++ b/fbw-a32nx/src/systems/systems-host/systems/FWC/FwsSoundManager.ts
@@ -0,0 +1,428 @@
+// Copyright (c) 2021-2024 FlyByWire Simulations
+//
+// SPDX-License-Identifier: GPL-3.0
+
+import { EventBus, SimVarValueType, Subscribable } from '@microsoft/msfs-sdk';
+
+export interface FwsSoundManagerControlEvents {
+ enqueueSound: string;
+ dequeueSound: string;
+}
+
+// Synthetic voice has priority over everything, SC is least important
+enum FwsAuralWarningType {
+ SingleChime,
+ AuralWarning,
+ SyntheticVoice,
+}
+
+export enum FwsAuralVolume {
+ Full, // 0 dB
+ Attenuated, // -6dB
+ Silent, // -200 dB
+}
+
+interface FwsAural {
+ /** The LocalVar which triggers the playback. Not prefixed by L: here. Either localVarName or wwiseEventName has to be defined. */
+ localVarName?: string;
+ /** The Wwise event which triggers the playback. Either localVarName or wwiseEventName has to be defined. */
+ wwiseEventName?: string;
+ /** Sounds are queued based on type and priority (highest priority = gets queued first within same type) */
+ priority: number;
+ type: FwsAuralWarningType;
+ /** Length of audio in seconds, if non-repetitive */
+ length?: number;
+ /** If this is set, this sound is repeated periodically with the specified pause in seconds */
+ periodicWithPause?: number;
+ continuous?: boolean;
+}
+
+export const FwsAuralsList: Record = {
+ continuousRepetitiveChime: {
+ localVarName: 'A32NX_FWC_CRC',
+ priority: 5,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: true,
+ },
+ singleChime: {
+ localVarName: 'A32NX_FWC_SC',
+ length: 0.54,
+ priority: 0,
+ type: FwsAuralWarningType.SingleChime,
+ continuous: false,
+ },
+ cavalryChargeOnce: {
+ localVarName: 'A32NX_FWC_CAVALRY_CHARGE',
+ length: 0.9,
+ priority: 4,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ cavalryChargeCont: {
+ localVarName: 'A32NX_FWC_CAVALRY_CHARGE',
+ priority: 4,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: true,
+ },
+ tripleClick: {
+ localVarName: 'A32NX_FMA_TRIPLE_CLICK',
+ length: 0.62,
+ priority: 3,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ pause0p8s: {
+ localVarName: 'A32NX_AUDIO_PAUSE',
+ length: 0.8,
+ priority: 4,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ autoBrakeOff: {
+ localVarName: 'A32NX_AUDIO_AUTOBRAKE_OFF',
+ length: 1.5,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ runwayTooShort: {
+ localVarName: 'A32NX_AUDIO_ROW_RWY_TOO_SHORT',
+ length: 1.6,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: true,
+ },
+ keepMaxReverse: {
+ localVarName: 'A32NX_AUDIO_ROP_KEEP_MAX_REVERSE',
+ length: 1.4,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ setMaxReverse: {
+ localVarName: 'A32NX_AUDIO_ROW_SET_MAX_REVERSE',
+ length: 1.62,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ brakeMaxBraking: {
+ localVarName: 'A32NX_AUDIO_ROP_MAX_BRAKING',
+ length: 3.1,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: true,
+ },
+ stall: {
+ localVarName: 'A32NX_AUDIO_ROP_MAX_BRAKING',
+ length: 3.0,
+ priority: 5,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: true,
+ },
+ cChordOnce: {
+ localVarName: 'A32NX_ALT_DEVIATION',
+ length: 1.0,
+ priority: 3,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ cChordCont: {
+ localVarName: 'A32NX_ALT_DEVIATION',
+ priority: 3,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: true,
+ },
+ // Altitude callouts
+ minimums: {
+ wwiseEventName: 'aural_minimumnew',
+ length: 0.67,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ hundred_above: {
+ wwiseEventName: 'aural_100above',
+ length: 0.72,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ retard: {
+ wwiseEventName: 'new_retard',
+ length: 0.9,
+ periodicWithPause: 0.2,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_2500: {
+ wwiseEventName: 'new_2500',
+ length: 1.1,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_2500b: {
+ wwiseEventName: 'new_2_500',
+ length: 1.047,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_2000: {
+ wwiseEventName: 'new_2000',
+ length: 0.72,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_1000: {
+ wwiseEventName: 'new_1000',
+ length: 0.9,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_500: {
+ wwiseEventName: 'new_500',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_400: {
+ wwiseEventName: 'new_400',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_300: {
+ wwiseEventName: 'new_300',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_200: {
+ wwiseEventName: 'new_200',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_100: {
+ wwiseEventName: 'new_100',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_50: {
+ wwiseEventName: 'new_50',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_40: {
+ wwiseEventName: 'new_40',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_30: {
+ wwiseEventName: 'new_30',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_20: {
+ wwiseEventName: 'new_20',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_10: {
+ wwiseEventName: 'new_10',
+ length: 0.3,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_5: {
+ wwiseEventName: 'new_5',
+ length: 0.3,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+};
+
+// FIXME Not all sounds are added to this yet (e.g. CIDS chimes), consider adding them in the future
+// Also, single chimes are not filtered (in RL only once every two seconds)
+export class FwsSoundManager {
+ private readonly soundQueue = new Set();
+
+ private singleChimesPending = 0;
+
+ private currentSoundPlaying: keyof typeof FwsAuralsList | null = null;
+
+ /** in seconds */
+ private currentSoundPlayTimeRemaining = 0;
+
+ constructor(
+ private bus: EventBus,
+ private startupCompleted: Subscribable,
+ ) {
+ // Stop all sounds
+ Object.values(FwsAuralsList).forEach((a) => {
+ if (a.localVarName) {
+ SimVar.SetSimVarValue(`L:${a.localVarName}`, SimVarValueType.Bool, false);
+ }
+ });
+
+ const sub = this.bus.getSubscriber();
+ sub.on('enqueueSound').handle((s) => this.enqueueSound(s));
+ sub.on('dequeueSound').handle((s) => this.dequeueSound(s));
+ }
+
+ /** Add sound to queue. Don't add if already playing */
+ enqueueSound(soundKey: keyof typeof FwsAuralsList) {
+ const sound = FwsAuralsList[soundKey];
+ if (!sound || this.currentSoundPlaying === soundKey) {
+ return;
+ }
+
+ if (sound.type === FwsAuralWarningType.SyntheticVoice || sound.type === FwsAuralWarningType.AuralWarning) {
+ this.soundQueue.add(soundKey);
+ } else if (sound.type === FwsAuralWarningType.SingleChime) {
+ this.singleChimesPending++;
+ }
+ }
+
+ /** Remove sound from queue, e.g. when condition doesn't apply anymore. If sound is currently playing, stops sound immediately */
+ dequeueSound(soundKey: keyof typeof FwsAuralsList) {
+ // Check if this sound is currently playing
+ if (this.currentSoundPlaying === soundKey && FwsAuralsList[this.currentSoundPlaying]?.continuous) {
+ this.stopCurrentSound();
+ }
+ this.soundQueue.delete(soundKey);
+ }
+
+ private stopCurrentSound() {
+ // Only LVar sounds which are continuous can be stopped
+ if (
+ this.currentSoundPlaying &&
+ FwsAuralsList[this.currentSoundPlaying].localVarName &&
+ FwsAuralsList[this.currentSoundPlaying]?.continuous
+ ) {
+ SimVar.SetSimVarValue(`L:${FwsAuralsList[this.currentSoundPlaying].localVarName}`, SimVarValueType.Bool, false);
+ this.currentSoundPlaying = null;
+ this.currentSoundPlayTimeRemaining = 0;
+ }
+ }
+
+ /**
+ * Convenience function for FWS: If condition true and sound not already playing, add to queue. If not, dequeue sound
+ * */
+ handleSoundCondition(soundKey: keyof typeof FwsAuralsList, condition: boolean) {
+ if (condition && this.currentSoundPlaying !== soundKey) {
+ this.enqueueSound(soundKey);
+ } else if (!condition) {
+ this.dequeueSound(soundKey);
+ }
+ }
+
+ /** This only has an effect on sounds defining WwiseRTPC behavior/var for volume */
+ setVolume(volume: FwsAuralVolume) {
+ SimVar.SetSimVarValue('L:A32NX_FWS_AUDIO_VOLUME', SimVarValueType.Enum, volume);
+ }
+
+ /** Play now, not to be called from the outside */
+ private playSound(soundKey: keyof typeof FwsAuralsList) {
+ const sound = FwsAuralsList[soundKey];
+ if (!sound) {
+ return;
+ }
+
+ if (sound.localVarName) {
+ SimVar.SetSimVarValue(`L:${sound.localVarName}`, SimVarValueType.Bool, true);
+ } else if (sound.wwiseEventName) {
+ Coherent.call('PLAY_INSTRUMENT_SOUND', sound.wwiseEventName);
+ }
+ this.currentSoundPlaying = soundKey;
+ this.currentSoundPlayTimeRemaining = sound.continuous ? Infinity : sound.length;
+ this.soundQueue.delete(soundKey);
+ }
+ /** Find most important sound from soundQueue and play */
+ private selectAndPlayMostImportantSound(): keyof typeof FwsAuralsList | null {
+ if (!this.startupCompleted.get()) {
+ return;
+ }
+
+ // Logic for scheduling new sounds: Take sound from soundQueue of most important type
+ // (SyntheticVoice > AuralWarning > SingleChime) with highest priority, and play it
+ let selectedSoundKey: keyof typeof FwsAuralsList | null = null;
+ this.soundQueue.forEach((sk) => {
+ const s = FwsAuralsList[sk];
+ if (
+ selectedSoundKey === null ||
+ s.type > FwsAuralsList[selectedSoundKey].type ||
+ (s.type === FwsAuralsList[selectedSoundKey].type && s.priority > FwsAuralsList[selectedSoundKey].priority)
+ ) {
+ selectedSoundKey = sk;
+ }
+ });
+
+ if (selectedSoundKey) {
+ this.playSound(selectedSoundKey);
+ return selectedSoundKey;
+ }
+
+ // See if single chimes are left
+ if (this.singleChimesPending) {
+ this.playSound('singleChime');
+ this.singleChimesPending--;
+ return 'singleChime';
+ }
+
+ // Ok, nothing to play
+ return null;
+ }
+
+ onUpdate(deltaTime: number) {
+ // Either wait for the current sound to finish, or schedule the next sound
+ if (this.currentSoundPlaying && this.currentSoundPlayTimeRemaining > 0) {
+ if (this.currentSoundPlayTimeRemaining - deltaTime / 1_000 > 0) {
+ // Wait for sound to be finished
+ this.currentSoundPlayTimeRemaining -= deltaTime / 1_000;
+ } else {
+ // Sound finishes in this cycle
+ if (FwsAuralsList[this.currentSoundPlaying].localVarName) {
+ SimVar.SetSimVarValue(
+ `L:${FwsAuralsList[this.currentSoundPlaying].localVarName}`,
+ SimVarValueType.Bool,
+ false,
+ );
+ }
+ this.currentSoundPlaying = null;
+ this.currentSoundPlayTimeRemaining = 0;
+ }
+
+ // Interrupt if sound with higher category is present in queue and current sound is continuous
+ let shouldInterrupt = false;
+ let rescheduleSound: keyof typeof FwsAuralsList | null = null;
+ this.soundQueue.forEach((sk) => {
+ const s = FwsAuralsList[sk];
+ if (
+ s &&
+ this.currentSoundPlaying &&
+ FwsAuralsList[this.currentSoundPlaying]?.continuous &&
+ s.type > FwsAuralsList[this.currentSoundPlaying].type
+ ) {
+ shouldInterrupt = true;
+ }
+ });
+
+ if (shouldInterrupt) {
+ if (this.currentSoundPlaying && FwsAuralsList[this.currentSoundPlaying]?.continuous) {
+ rescheduleSound = this.currentSoundPlaying;
+ this.stopCurrentSound();
+ if (rescheduleSound) {
+ this.enqueueSound(rescheduleSound);
+ }
+ }
+ }
+ } else {
+ // Play next sound
+ this.selectAndPlayMostImportantSound();
+ }
+ }
+}
diff --git a/fbw-a32nx/src/systems/instruments/src/EWD/PseudoFWC.ts b/fbw-a32nx/src/systems/systems-host/systems/FWC/PseudoFWC.ts
similarity index 87%
rename from fbw-a32nx/src/systems/instruments/src/EWD/PseudoFWC.ts
rename to fbw-a32nx/src/systems/systems-host/systems/FWC/PseudoFWC.ts
index 88e4ab2b2e8..4266ca34ee1 100644
--- a/fbw-a32nx/src/systems/instruments/src/EWD/PseudoFWC.ts
+++ b/fbw-a32nx/src/systems/systems-host/systems/FWC/PseudoFWC.ts
@@ -13,23 +13,32 @@ import {
SimVarValueType,
SubscribableMapFunctions,
StallWarningEvents,
+ KeyEventManager,
+ GameStateProvider,
+ Wait,
+ KeyEvents,
} from '@microsoft/msfs-sdk';
import {
+ Arinc429LocalVarConsumerSubject,
Arinc429Register,
Arinc429RegisterSubject,
Arinc429SignStatusMatrix,
Arinc429Word,
+ Arinc429WordData,
NXDataStore,
NXLogicClockNode,
NXLogicConfirmNode,
NXLogicMemoryNode,
NXLogicPulseNode,
NXLogicTriggeredMonostableNode,
+ UpdateThrottler,
} from '@flybywiresim/fbw-sdk';
import { VerticalMode } from '@shared/autopilot';
-import { EwdSimvars } from 'instruments/src/EWD/shared/EwdSimvarPublisher';
-import { FuelSystemEvents } from '../MsfsAvionicsCommon/providers/FuelSystemPublisher';
+import { FuelSystemEvents } from '../../../instruments/src/MsfsAvionicsCommon/providers/FuelSystemPublisher';
+import { A32NXFcuBusEvents } from '../../../shared/src/publishers/A32NXFcuBusPublisher';
+import { FwsSoundManager } from 'systems-host/systems/FWC/FwsSoundManager';
+import { PseudoFwcSimvars } from 'instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher';
export function xor(a: boolean, b: boolean): boolean {
return !!((a ? 1 : 0) ^ (b ? 1 : 0));
@@ -68,19 +77,28 @@ enum FwcAuralWarning {
None,
SingleChime,
Crc,
+ CavalryCharge,
}
export class PseudoFWC {
- private readonly sub = this.bus.getSubscriber();
+ private readonly sub = this.bus.getSubscriber<
+ PseudoFwcSimvars & StallWarningEvents & KeyEvents & A32NXFcuBusEvents
+ >();
+
+ private readonly fwsUpdateThrottler = new UpdateThrottler(125); // has to be > 100 due to pulse nodes
+
+ private keyEventManager: KeyEventManager;
+
+ private readonly startupCompleted = Subject.create(false);
+
+ public readonly soundManager = new FwsSoundManager(this.bus, this.startupCompleted);
+
/** Time to inhibit master warnings and cautions during startup in ms */
private static readonly FWC_STARTUP_TIME = 5000;
/** Time to inhibit SCs after one is trigger in ms */
private static readonly AURAL_SC_INHIBIT_TIME = 2000;
- /** The time to play the single chime sound in ms */
- private static readonly AURAL_SC_PLAY_TIME = 500;
-
private static readonly EWD_MESSAGE_LINES = 7;
private static readonly ewdMessageSimVarsLeft = Array.from(
@@ -101,11 +119,16 @@ export class PseudoFWC {
Subject.create(''),
);
+ // Input buffering
+ public readonly toConfigInputBuffer = new NXLogicMemoryNode(false);
+ public readonly clearButtonInputBuffer = new NXLogicMemoryNode(false);
+ public readonly recallButtonInputBuffer = new NXLogicMemoryNode(false);
+ public readonly aThrDiscInputBuffer = new NXLogicMemoryNode(false);
+ public readonly apDiscInputBuffer = new NXLogicMemoryNode(false);
+
/* PSEUDO FWC VARIABLES */
private readonly startupTimer = new DebounceTimer();
- private readonly startupCompleted = Subject.create(false);
-
private readonly allCurrentFailures: string[] = [];
private readonly failuresLeft: string[] = [];
@@ -114,6 +137,15 @@ export class PseudoFWC {
private recallFailures: string[] = [];
+ private requestMasterCautionFromFaults = false;
+ private requestMasterCautionFromABrkOff = false;
+ private requestMasterCautionFromAThrOff = false;
+
+ private requestSingleChimeFromAThrOff = false;
+
+ private requestMasterWarningFromFaults = false;
+ private requestMasterWarningFromApOff = false;
+
private auralCrcKeys: string[] = [];
private auralScKeys: string[] = [];
@@ -124,8 +156,6 @@ export class PseudoFWC {
private readonly auralSingleChimeInhibitTimer = new DebounceTimer();
- private readonly auralSingleChimePlayingTimer = new DebounceTimer();
-
private readonly masterWarning = Subject.create(false);
private readonly masterCaution = Subject.create(false);
@@ -282,6 +312,76 @@ export class PseudoFWC {
private toSpeedsNotInsertedWarning = Subject.create(false);
+ /** If multiple AP discs are triggered between FWS cycles, memorize the amount */
+ public autoPilotInstinctiveDiscCountSinceLastFwsCycle = 0;
+
+ public readonly autoPilotDisengagedInstantPulse = new NXLogicPulseNode(false);
+
+ /** 1.8s according to references, but was raised to 1.9s to allow for triple click to finish */
+ public readonly autoPilotInstinctiveDiscPressedInLast1p5Sec = new NXLogicTriggeredMonostableNode(1.5, true);
+
+ /** 1.8s according to references, but was raised to 1.9s to allow for triple click to finish */
+ public readonly autoPilotInstinctiveDiscPressedTwiceInLast1p5Sec = new NXLogicTriggeredMonostableNode(1.5, true);
+
+ public readonly autoPilotInstinctiveDiscPressedPulse = new NXLogicPulseNode(true);
+
+ /** Stay in first warning stage for 1.8s. Raised to 1.9s to allow for triple click to finish */
+ public readonly autoPilotOffVoluntaryEndAfter1p5s = new NXLogicTriggeredMonostableNode(1.5, true);
+
+ public readonly autoPilotOffVoluntaryFirstCavalryChargeActive = new NXLogicTriggeredMonostableNode(0.8, true);
+
+ public readonly autoPilotOffVoluntaryFirstCavalryChargeActivePulse = new NXLogicPulseNode(false);
+
+ public readonly autoPilotOffVoluntaryDiscPulse = new NXLogicPulseNode(true);
+
+ public readonly autoPilotOffVoluntaryMemory = new NXLogicMemoryNode(true);
+
+ public readonly autoPilotOffInvoluntaryMemory = new NXLogicMemoryNode(false);
+
+ public readonly autoPilotOffAlertShown = Subject.create(false);
+
+ public readonly autoPilotOffInvoluntary = Subject.create(false);
+
+ public readonly autoPilotOffAlertShownMemory = new NXLogicMemoryNode(false);
+
+ public readonly autoPilotOffUnacknowledged = new NXLogicMemoryNode(false);
+
+ public readonly autoPilotOffShowMemo = Subject.create(false);
+
+ public readonly fmgc1DiscreteWord3 = Arinc429LocalVarConsumerSubject.create(this.sub.on('fmgc1DiscreteWord3'));
+
+ public readonly fmgc2DiscreteWord3 = Arinc429LocalVarConsumerSubject.create(this.sub.on('fmgc2DiscreteWord3'));
+
+ public readonly fmgc1DiscreteWord4 = Arinc429LocalVarConsumerSubject.create(this.sub.on('fmgc1DiscreteWord4'));
+
+ public readonly fmgc2DiscreteWord4 = Arinc429LocalVarConsumerSubject.create(this.sub.on('fmgc2DiscreteWord4'));
+
+ public readonly fmgcApproachCapability = Subject.create(0);
+
+ public readonly approachCapabilityDowngradeDebounce = new NXLogicTriggeredMonostableNode(0.5, true);
+
+ public readonly approachCapabilityDowngradeSuppress = new NXLogicTriggeredMonostableNode(3, true);
+
+ public readonly approachCapabilityDowngradeDebouncePulse = new NXLogicPulseNode(false);
+
+ public readonly autoThrustDisengagedInstantPulse = new NXLogicPulseNode(false);
+
+ public readonly autoThrustInstinctiveDiscPressed = new NXLogicTriggeredMonostableNode(1.5, true); // Save event for 1.5 sec
+
+ public readonly autoThrustOffVoluntaryMemoNode = new NXLogicTriggeredMonostableNode(9, false); // Emit memo for max. 9 sec
+
+ public readonly autoThrustOffVoluntaryCautionNode = new NXLogicTriggeredMonostableNode(3, false); // Emit master caution for max. 3 sec
+
+ public readonly autoThrustOffInvoluntaryNode = new NXLogicMemoryNode(false);
+
+ public autoThrustInhibitCaution = false; // Inhibit for 10 sec
+
+ public readonly autoThrustOffVoluntary = Subject.create(false);
+
+ public readonly autoThrustOffInvoluntary = Subject.create(false);
+
+ public autoThrustOffVoluntaryMemoInhibited = false;
+
/** TO CONF pressed in phase 2 or 3 SR */
private toConfigCheckedInPhase2Or3 = false;
@@ -289,6 +389,13 @@ export class PseudoFWC {
private toV2VRV2DisagreeWarning = Subject.create(false);
+ private readonly fcu1DiscreteWord2 = Arinc429LocalVarConsumerSubject.create(this.sub.on('a32nx_fcu_discrete_word_2'));
+ private readonly fcu2DiscreteWord2 = Arinc429LocalVarConsumerSubject.create(this.sub.on('a32nx_fcu_discrete_word_2'));
+
+ private readonly fcu12Fault = Subject.create(false);
+ private readonly fcu1Fault = Subject.create(false);
+ private readonly fcu2Fault = Subject.create(false);
+
/* 24 - ELECTRICAL */
private readonly ac1BusPowered = Subject.create(false);
@@ -668,6 +775,14 @@ export class PseudoFWC {
private onGroundImmediate = false;
+ public readonly autoBrakeDeactivatedNode = new NXLogicTriggeredMonostableNode(9, false); // When ABRK deactivated, emit this for 9 sec
+
+ public readonly autoBrakeOffAuralConfirmNode = new NXLogicConfirmNode(1, true);
+
+ public readonly autoBrakeOff = Subject.create(false);
+
+ public autoBrakeOffAuralTriggered = false;
+
/* NAVIGATION */
private readonly adirsRemainingAlignTime = Subject.create(0);
@@ -788,12 +903,22 @@ export class PseudoFWC {
private readonly throttle2Position = Subject.create(0);
+ public readonly allThrottleIdle = Subject.create(false);
+
private readonly engine1ValueSwitch = ConsumerValue.create(null, false);
private readonly engine2ValueSwitch = ConsumerValue.create(null, false);
private readonly autoThrustStatus = Subject.create(0);
+ private readonly atsDiscreteWord = Arinc429Register.empty();
+
+ private readonly ecu1MaintenanceWord6 = Arinc429Register.empty();
+
+ private readonly ecu2MaintenanceWord6 = Arinc429Register.empty();
+
+ private readonly thrLocked = Subject.create(false);
+
private readonly autothrustLeverWarningFlex = Subject.create(false);
private readonly autothrustLeverWarningToga = Subject.create(false);
@@ -936,10 +1061,34 @@ export class PseudoFWC {
}
init(): void {
+ Promise.all([
+ KeyEventManager.getManager(this.bus),
+ Wait.awaitSubscribable(GameStateProvider.get(), (state) => state === GameState.ingame, true),
+ ]).then(([keyEventManager]) => {
+ this.keyEventManager = keyEventManager;
+ this.registerKeyEvents();
+ });
+
+ this.sub
+ .on('key_intercept')
+ .atFrequency(50)
+ .handle((keyData) => {
+ switch (keyData.key) {
+ case 'A32NX.AUTO_THROTTLE_DISCONNECT':
+ this.autoThrottleInstinctiveDisconnect();
+ break;
+ case 'A32NX.FCU_AP_DISCONNECT_PUSH':
+ case 'A32NX.AUTOPILOT_DISENGAGE':
+ case 'AUTOPILOT_OFF':
+ this.autoPilotInstinctiveDisconnect();
+ break;
+ }
+ });
+
this.toConfigNormal.sub((normal) => SimVar.SetSimVarValue('L:A32NX_TO_CONFIG_NORMAL', 'bool', normal));
this.fwcFlightPhase.sub(() => this.flightPhaseEndedPulseNode.write(true, 0));
- this.auralCrcOutput.sub((crc) => SimVar.SetSimVarValue('L:A32NX_FWC_CRC', 'bool', crc));
+ this.auralCrcOutput.sub((crc) => this.soundManager.handleSoundCondition('continuousRepetitiveChime', crc), true);
this.masterCaution.sub((caution) => {
// Inhibit master warning/cautions until FWC startup has been completed
@@ -1007,6 +1156,14 @@ export class PseudoFWC {
});
}
+ private registerKeyEvents() {
+ this.keyEventManager.interceptKey('A32NX.AUTO_THROTTLE_DISCONNECT', true);
+ this.keyEventManager.interceptKey('A32NX.FCU_AP_DISCONNECT_PUSH', true);
+ this.keyEventManager.interceptKey('A32NX.AUTOPILOT_DISENGAGE', false); // internal event, for FWS only
+ this.keyEventManager.interceptKey('AUTOPILOT_OFF', true);
+ this.keyEventManager.interceptKey('AUTO_THROTTLE_ARM', true);
+ }
+
mapOrder(array, order): [] {
array.sort((a, b) => {
if (order.indexOf(a) > order.indexOf(b)) {
@@ -1084,11 +1241,45 @@ export class PseudoFWC {
/**
* Periodic update
*/
- onUpdate() {
- const deltaTime = this.instrument.deltaTime;
+ update(_deltaTime: number) {
+ const deltaTime = this.fwsUpdateThrottler.canUpdate(_deltaTime);
- // Inputs update
+ // Acquire discrete inputs at a higher frequency, buffer them until the next FWS cycle.
+ // T.O CONFIG button
+ if (SimVar.GetSimVarValue('L:A32NX_BTN_TOCONFIG', 'bool')) {
+ this.toConfigInputBuffer.write(true, false);
+ }
+
+ // CLR buttons
+ const clearButtonLeft = SimVar.GetSimVarValue('L:A32NX_BTN_CLR', 'bool');
+ const clearButtonRight = SimVar.GetSimVarValue('L:A32NX_BTN_CLR2', 'bool');
+ if (clearButtonLeft || clearButtonRight) {
+ this.clearButtonInputBuffer.write(true, false);
+ }
+
+ // RCL button
+ const recallButton = SimVar.GetSimVarValue('L:A32NX_BTN_RCL', 'bool');
+ if (recallButton) {
+ this.recallButtonInputBuffer.write(true, false);
+ }
+
+ // Enforce cycle time for the logic computation (otherwise pulse nodes would be broken)
+ if (deltaTime === -1 || _deltaTime === 0) {
+ return;
+ }
+ // Play sounds
+ this.soundManager.onUpdate(deltaTime);
+
+ // Write pulse nodes for buffered inputs
+ this.toConfigPulseNode.write(this.toConfigInputBuffer.read(), deltaTime);
+ this.clr1PulseNode.write(this.clearButtonInputBuffer.read(), deltaTime);
+ this.clr2PulseNode.write(this.clearButtonInputBuffer.read(), deltaTime);
+ this.rclUpPulseNode.write(this.recallButtonInputBuffer.read(), deltaTime);
+ this.autoThrustInstinctiveDiscPressed.write(this.aThrDiscInputBuffer.read(), deltaTime);
+ this.autoPilotInstinctiveDiscPressedPulse.write(this.apDiscInputBuffer.read(), deltaTime);
+
+ // Inputs update
this.flightPhaseEndedPulseNode.write(false, deltaTime);
this.fwcFlightPhase.set(SimVar.GetSimVarValue('L:A32NX_FWC_FLIGHT_PHASE', 'Enum'));
@@ -1102,10 +1293,11 @@ export class PseudoFWC {
this.flightPhase67.set([6, 7].includes(this.fwcFlightPhase.get()));
this.flightPhase78.set([7, 8].includes(this.fwcFlightPhase.get()));
const flightPhase567 = [5, 6, 7].includes(this.fwcFlightPhase.get());
+ const flightPhase167 = [1, 6, 7].includes(this.fwcFlightPhase.get());
// TO CONFIG button
this.toConfigTestRaw = SimVar.GetSimVarValue('L:A32NX_BTN_TOCONFIG', 'bool') > 0;
- this.toConfigPulseNode.write(this.toConfigTestRaw, deltaTime);
+ this.toConfigPulseNode.write(this.toConfigTestRaw, _deltaTime);
const toConfigTest = this.toConfigTriggerNode.write(this.toConfigPulseNode.read(), deltaTime);
if (toConfigTest !== this.toConfigTest) {
// temporary var for the old FWC stuff
@@ -1117,17 +1309,11 @@ export class PseudoFWC {
);
// CLR buttons
- const clearButtonLeft = SimVar.GetSimVarValue('L:A32NX_BTN_CLR', 'bool');
- const clearButtonRight = SimVar.GetSimVarValue('L:A32NX_BTN_CLR2', 'bool');
- this.clr1PulseNode.write(clearButtonLeft, deltaTime);
- this.clr2PulseNode.write(clearButtonRight, deltaTime);
const previousClrPulseUpTrigger = this.clrPulseUpTrigger.read();
this.clrPulseUpTrigger.write(this.clr1PulseNode.read() || this.clr2PulseNode.read(), deltaTime);
this.clrTriggerRisingEdge = !previousClrPulseUpTrigger && this.clrPulseUpTrigger.read();
// RCL button
- const recallButton = SimVar.GetSimVarValue('L:A32NX_BTN_RCL', 'bool');
- this.rclUpPulseNode.write(recallButton, deltaTime);
const previousRclUpTriggerNode = this.rclUpTriggerNode.read();
this.rclUpTriggerNode.write(recallButton, deltaTime);
@@ -1199,8 +1385,17 @@ export class PseudoFWC {
this.throttle1Position.set(SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:1', 'number'));
this.throttle2Position.set(SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:2', 'number'));
this.autoThrustStatus.set(SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_STATUS', 'enum'));
+ this.atsDiscreteWord.setFromSimVar('L:A32NX_FCU_ATS_DISCRETE_WORD');
+ this.ecu1MaintenanceWord6.setFromSimVar('L:A32NX_ECU_1_MAINTENANCE_WORD_6');
+ this.ecu2MaintenanceWord6.setFromSimVar('L:A32NX_ECU_2_MAINTENANCE_WORD_6');
this.autothrustLeverWarningFlex.set(SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_THRUST_LEVER_WARNING_FLEX', 'bool'));
this.autothrustLeverWarningToga.set(SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_THRUST_LEVER_WARNING_TOGA', 'bool'));
+ this.allThrottleIdle.set(this.throttle1Position.get() < 1 && this.throttle2Position.get() < 1);
+
+ const masterCautionButtonLeft = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERCAUT_L', 'bool');
+ const masterCautionButtonRight = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERCAUT_R', 'bool');
+ const masterWarningButtonLeft = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_L', 'bool');
+ const masterWarningButtonRight = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_R', 'bool');
/* HYDRAULICS acquisition */
@@ -1332,6 +1527,201 @@ export class PseudoFWC {
(onGroundCount > 1 && raInvalid);
this.aircraftOnGround.set(this.onGroundConf.write(this.onGroundImmediate, deltaTime));
+ // AP OFF
+ const apEngaged: boolean =
+ SimVar.GetSimVarValue('L:A32NX_FMGC_1_AP_ENGAGED', SimVarValueType.Bool) ||
+ SimVar.GetSimVarValue('L:A32NX_FMGC_2_AP_ENGAGED', SimVarValueType.Bool);
+ this.autoPilotDisengagedInstantPulse.write(apEngaged, deltaTime);
+
+ const apDiscPressedInLast1p8SecBeforeThisCycle = this.autoPilotInstinctiveDiscPressedInLast1p5Sec.read();
+ this.autoPilotInstinctiveDiscPressedInLast1p5Sec.write(this.autoPilotInstinctiveDiscPressedPulse.read(), deltaTime);
+
+ const voluntaryApDisc =
+ this.autoPilotDisengagedInstantPulse.read() && this.autoPilotInstinctiveDiscPressedInLast1p5Sec.read();
+ this.autoPilotOffVoluntaryEndAfter1p5s.write(voluntaryApDisc, deltaTime);
+ this.autoPilotOffVoluntaryDiscPulse.write(voluntaryApDisc, deltaTime);
+
+ this.autoPilotOffVoluntaryFirstCavalryChargeActive.write(this.autoPilotOffVoluntaryDiscPulse.read(), deltaTime);
+ this.autoPilotOffVoluntaryFirstCavalryChargeActivePulse.write(
+ this.autoPilotOffVoluntaryFirstCavalryChargeActive.read(),
+ deltaTime,
+ );
+
+ this.autoPilotInstinctiveDiscPressedTwiceInLast1p5Sec.write(
+ this.autoPilotInstinctiveDiscPressedPulse.read() &&
+ (this.autoPilotInstinctiveDiscCountSinceLastFwsCycle > 1 || apDiscPressedInLast1p8SecBeforeThisCycle),
+ deltaTime,
+ );
+
+ this.autoPilotOffVoluntaryMemory.write(
+ this.autoPilotOffVoluntaryDiscPulse.read(),
+ apEngaged ||
+ this.autoPilotInstinctiveDiscPressedTwiceInLast1p5Sec.read() ||
+ !this.autoPilotOffVoluntaryEndAfter1p5s.read(),
+ );
+
+ const discPbPressedAfterDisconnection =
+ !this.autoPilotDisengagedInstantPulse.read() &&
+ (this.autoPilotInstinctiveDiscPressedPulse.read() || masterWarningButtonLeft || masterWarningButtonRight);
+
+ this.autoPilotOffUnacknowledged.write(
+ this.autoPilotDisengagedInstantPulse.read(),
+ apEngaged || this.autoPilotInstinctiveDiscPressedTwiceInLast1p5Sec.read() || discPbPressedAfterDisconnection,
+ );
+
+ this.autoPilotOffInvoluntaryMemory.write(
+ !apEngaged && !this.autoPilotOffVoluntaryMemory.read() && this.autoPilotOffUnacknowledged.read(),
+ !this.autoPilotOffUnacknowledged.read(),
+ );
+
+ this.autoPilotOffAlertShownMemory.write(
+ this.autoPilotOffInvoluntaryMemory.read(),
+ this.fwcFlightPhase.get() === 1 || apEngaged,
+ );
+ this.autoPilotOffAlertShown.set(this.autoPilotOffAlertShownMemory.read());
+ this.autoPilotOffInvoluntary.set(this.autoPilotOffInvoluntaryMemory.read());
+ this.autoPilotOffShowMemo.set(this.autoPilotOffVoluntaryMemory.read() || this.autoPilotOffInvoluntaryMemory.read());
+
+ if (this.autoPilotDisengagedInstantPulse.read()) {
+ // Request quiet CRC one time
+ this.requestMasterWarningFromApOff = true;
+ this.soundManager.enqueueSound('cavalryChargeOnce'); // On the A320, play first cav charge completely no matter what
+ }
+ if (this.autoPilotOffVoluntaryFirstCavalryChargeActivePulse.read()) {
+ this.soundManager.dequeueSound('cavalryChargeOnce');
+ }
+ if (!this.autoPilotOffVoluntaryMemory.read() && !this.autoPilotOffInvoluntaryMemory.read()) {
+ this.requestMasterWarningFromApOff = false;
+ this.soundManager.dequeueSound('cavalryChargeOnce');
+ this.soundManager.dequeueSound('cavalryChargeCont');
+ }
+
+ this.autoPilotInstinctiveDiscPressedPulse.write(false, deltaTime);
+
+ // approach capability downgrade. Debounce first, then suppress for a certain amount of time
+ // (to avoid multiple triple clicks, and a delay which is too long)
+ let fmgcApproachCapability = 0;
+ const getApproachCapability = (dw3: Arinc429WordData, dw4: Arinc429WordData): number => {
+ let appCap = 0;
+ const landModeActive = dw4.bitValueOr(14, false);
+ const landModeArmed = dw3.bitValueOr(20, false);
+ const land2Capacity = dw4.bitValueOr(23, false);
+ const land3FailPassiveCapacity = dw4.bitValueOr(24, false);
+ const land3FailOperationalCapacity = dw4.bitValueOr(25, false);
+
+ if (land2Capacity) {
+ appCap = 2;
+ } else if (land3FailPassiveCapacity) {
+ appCap = 3;
+ } else if (land3FailOperationalCapacity) {
+ appCap = 4;
+ } else if (landModeActive || landModeArmed) {
+ appCap = 1;
+ } else {
+ appCap = 0;
+ }
+ return appCap;
+ };
+
+ if (this.fmgc1DiscreteWord3.get().isNormalOperation() && this.fmgc1DiscreteWord4.get().isNormalOperation()) {
+ fmgcApproachCapability = getApproachCapability(this.fmgc1DiscreteWord3.get(), this.fmgc1DiscreteWord4.get());
+ } else if (this.fmgc2DiscreteWord3.get().isNormalOperation() && this.fmgc2DiscreteWord4.get().isNormalOperation()) {
+ fmgcApproachCapability = getApproachCapability(this.fmgc2DiscreteWord3.get(), this.fmgc2DiscreteWord4.get());
+ }
+
+ const capabilityDowngrade =
+ fmgcApproachCapability < this.fmgcApproachCapability.get() && fmgcApproachCapability > 0;
+ this.approachCapabilityDowngradeDebounce.write(
+ capabilityDowngrade && flightPhase167 && !this.approachCapabilityDowngradeSuppress.read(),
+ deltaTime,
+ );
+ this.approachCapabilityDowngradeDebouncePulse.write(this.approachCapabilityDowngradeDebounce.read(), deltaTime);
+ this.approachCapabilityDowngradeSuppress.write(this.approachCapabilityDowngradeDebouncePulse.read(), deltaTime);
+ // Capability downgrade after debounce --> triple click
+ if (this.approachCapabilityDowngradeDebouncePulse.read()) {
+ this.soundManager.enqueueSound('pause0p8s');
+ this.soundManager.enqueueSound('tripleClick');
+ }
+ this.fmgcApproachCapability.set(fmgcApproachCapability);
+
+ // A/THR OFF
+ const aThrEngaged = this.atsDiscreteWord.bitValueOr(13, false);
+ this.autoThrustDisengagedInstantPulse.write(aThrEngaged, deltaTime);
+ this.autoThrustInstinctiveDiscPressed.write(false, deltaTime);
+
+ const below50ft = this.radioHeight1.valueOr(2500) < 50 && this.radioHeight2.valueOr(2500) < 50;
+
+ if (below50ft && this.allThrottleIdle.get()) {
+ this.autoThrustInhibitCaution = true;
+ }
+
+ const voluntaryAThrDisc =
+ !this.aircraftOnGround.get() &&
+ this.autoThrustDisengagedInstantPulse.read() &&
+ (this.autoThrustInstinctiveDiscPressed.read() || this.allThrottleIdle.get()) &&
+ !this.autoThrustInhibitCaution;
+
+ // Voluntary A/THR disconnect
+ this.autoThrustOffVoluntaryMemoNode.write(voluntaryAThrDisc && !aThrEngaged, deltaTime);
+ this.autoThrustOffVoluntaryCautionNode.write(voluntaryAThrDisc && !aThrEngaged, deltaTime);
+ this.thrLocked.set(
+ this.ecu1MaintenanceWord6.bitValueOr(12, false) || this.ecu2MaintenanceWord6.bitValueOr(12, false),
+ );
+
+ if (!this.autoThrustOffVoluntaryMemoNode.read()) {
+ this.autoThrustInhibitCaution = false;
+ }
+
+ if (
+ this.autoThrustOffVoluntaryCautionNode.read() &&
+ !this.autoThrustOffVoluntary.get() &&
+ !this.autoThrustInhibitCaution
+ ) {
+ // First triggered in this cycle, request master caution
+ this.requestMasterCautionFromAThrOff = true;
+ this.requestSingleChimeFromAThrOff = true;
+ } else if (!this.autoThrustOffVoluntaryCautionNode.read() || this.autoThrustInhibitCaution) {
+ this.requestMasterCautionFromAThrOff = false;
+ this.requestSingleChimeFromAThrOff = false;
+ }
+ this.autoThrustOffVoluntary.set(
+ this.autoThrustOffVoluntaryMemoNode.read() && !this.autoThrustInhibitCaution && !aThrEngaged,
+ );
+
+ // Involuntary A/THR disconnect
+ const involuntaryAThrDisc =
+ !this.aircraftOnGround.get() &&
+ this.autoThrustDisengagedInstantPulse.read() &&
+ !(this.autoThrustInstinctiveDiscPressed.read() || (below50ft && this.allThrottleIdle.get()));
+
+ this.autoThrustOffInvoluntaryNode.write(involuntaryAThrDisc, aThrEngaged || voluntaryAThrDisc);
+ this.autoThrustOffInvoluntary.set(this.autoThrustOffInvoluntaryNode.read());
+
+ // AUTO BRAKE OFF
+ this.autoBrakeDeactivatedNode.write(!!SimVar.GetSimVarValue('L:A32NX_AUTOBRAKES_ACTIVE', 'boolean'), deltaTime);
+
+ if (!this.autoBrakeDeactivatedNode.read()) {
+ this.requestMasterCautionFromABrkOff = false;
+ this.autoBrakeOffAuralTriggered = false;
+ }
+
+ this.autoBrakeOffAuralConfirmNode.write(this.autoBrakeDeactivatedNode.read(), deltaTime);
+
+ const autoBrakeOffShouldTrigger =
+ this.aircraftOnGround.get() && this.computedAirSpeedToNearest2.get() > 33 && this.autoBrakeDeactivatedNode.read();
+
+ if (autoBrakeOffShouldTrigger && !this.autoBrakeOff.get()) {
+ // Triggered in this cycle -> request master caution
+ this.requestMasterCautionFromABrkOff = true;
+ }
+
+ // FIXME double callout if ABRK fails
+ this.autoBrakeOff.set(autoBrakeOffShouldTrigger);
+ if (autoBrakeOffShouldTrigger && this.autoBrakeOffAuralConfirmNode.read() && !this.autoBrakeOffAuralTriggered) {
+ this.soundManager.enqueueSound('autoBrakeOff');
+ this.autoBrakeOffAuralTriggered = true;
+ }
+
// Engine Logic
this.thrustLeverNotSet.set(this.autothrustLeverWarningFlex.get() || this.autothrustLeverWarningToga.get());
// FIXME ECU doesn't have the necessary output words so we go purely on TLA
@@ -1379,6 +1769,14 @@ export class PseudoFWC {
overspeedWarning ||= adr1Discrete1.bitValueOr(9, false) || adr2Discrete1.bitValueOr(9, false);
this.overspeedWarning.set(overspeedWarning);
+ // In reality FWC1 takes 1B, and FWC2 2B.
+ const fcu1Healthy = this.fcu1DiscreteWord2.get().bitValueOr(24, false);
+ const fcu2Healthy = this.fcu1DiscreteWord2.get().bitValueOr(25, false);
+
+ this.fcu12Fault.set(!fcu1Healthy && !fcu2Healthy && this.dcESSBusPowered.get() && this.dc2BusPowered.get());
+ this.fcu1Fault.set(!fcu1Healthy && fcu2Healthy && this.dcESSBusPowered.get());
+ this.fcu2Fault.set(fcu1Healthy && !fcu2Healthy && this.dc2BusPowered.get());
+
// TO SPEEDS NOT INSERTED
const fmToSpeedsNotInserted = fm1DiscreteWord3.bitValueOr(18, false) && fm2DiscreteWord3.bitValueOr(18, false);
@@ -2161,18 +2559,17 @@ export class PseudoFWC {
}
/* MASTER CAUT/WARN BUTTONS */
-
- const masterCautionButtonLeft = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERCAUT_L', 'bool');
- const masterCautionButtonRight = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERCAUT_R', 'bool');
- const masterWarningButtonLeft = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_L', 'bool');
- const masterWarningButtonRight = SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_R', 'bool');
if (masterCautionButtonLeft || masterCautionButtonRight) {
- this.masterCaution.set(false);
this.auralSingleChimePending = false;
+ this.requestMasterCautionFromFaults = false;
+ this.requestMasterCautionFromABrkOff = false;
+ this.requestMasterCautionFromAThrOff = false;
+ this.autoThrustInhibitCaution = true;
}
if ((masterWarningButtonLeft || masterWarningButtonRight) && this.nonCancellableWarningCount === 0) {
- this.masterWarning.set(false);
- this.auralCrcActive.set(false);
+ this.requestMasterWarningFromFaults = this.nonCancellableWarningCount > 0;
+ this.requestMasterWarningFromApOff = false;
+ this.auralCrcActive.set(this.nonCancellableWarningCount > 0);
}
/* T.O. CONFIG CHECK */
@@ -2292,10 +2689,10 @@ export class PseudoFWC {
}
if (value.failure === 3) {
- this.masterWarning.set(true);
+ this.requestMasterWarningFromFaults = true;
}
if (value.failure === 2) {
- this.masterCaution.set(true);
+ this.requestMasterCautionFromFaults = true;
}
}
@@ -2361,6 +2758,10 @@ export class PseudoFWC {
}
auralScKeys.push(key);
}
+
+ if (value.auralWarning?.get() === FwcAuralWarning.CavalryCharge) {
+ this.soundManager.enqueueSound('cavalryChargeCont');
+ }
}
this.auralCrcKeys = auralCrcKeys;
@@ -2448,13 +2849,21 @@ export class PseudoFWC {
this.ewdMessageLinesLeft.forEach((l, i) => l.set(orderedMemoArrayLeft[i]));
if (orderedFailureArrayRight.length === 0) {
- this.masterCaution.set(false);
+ this.requestMasterCautionFromFaults = false;
if (this.nonCancellableWarningCount === 0) {
- this.masterWarning.set(false);
+ this.requestMasterWarningFromFaults = false;
}
}
}
+ this.masterCaution.set(
+ this.requestMasterCautionFromFaults ||
+ this.requestMasterCautionFromABrkOff ||
+ this.requestMasterCautionFromAThrOff,
+ );
+
+ this.masterWarning.set(this.requestMasterWarningFromFaults || this.requestMasterWarningFromApOff);
+
if (leftFailureSystemCount + rightFailureSystemCount === 0) {
SimVar.SetSimVarValue('L:A32NX_ECAM_SFAIL', 'number', -1);
}
@@ -2474,30 +2883,35 @@ export class PseudoFWC {
this.ewdMessageLinesRight.forEach((l, i) => l.set(orderedMemoArrayRight[i]));
- // This does not consider interrupting c-chord, priority of synthetic voice etc.
- // We shall wait for the rust FWC for those nice things!
- if (this.auralSingleChimePending && !this.auralCrcActive.get() && !this.auralSingleChimeInhibitTimer.isPending()) {
+ const chimeRequested =
+ (this.auralSingleChimePending || this.requestSingleChimeFromAThrOff) && !this.auralCrcActive.get();
+ if (chimeRequested && !this.auralSingleChimeInhibitTimer.isPending()) {
this.auralSingleChimePending = false;
- SimVar.SetSimVarValue('L:A32NX_FWC_SC', 'bool', true);
+ this.requestSingleChimeFromAThrOff = false;
+ this.soundManager.enqueueSound('singleChime');
// there can only be one SC per 2 seconds, non-cumulative, so clear any pending ones at the end of that inhibit period
this.auralSingleChimeInhibitTimer.schedule(
() => (this.auralSingleChimePending = false),
PseudoFWC.AURAL_SC_INHIBIT_TIME,
);
- this.auralSingleChimePlayingTimer.schedule(
- () => SimVar.SetSimVarValue('L:A32NX_FWC_SC', 'bool', false),
- PseudoFWC.AURAL_SC_PLAY_TIME,
- );
}
this.updateRowRopWarnings();
+
+ // Reset all buffered inputs
+ this.toConfigInputBuffer.write(false, true);
+ this.clearButtonInputBuffer.write(false, true);
+ this.recallButtonInputBuffer.write(false, true);
+ this.aThrDiscInputBuffer.write(false, true);
+ this.apDiscInputBuffer.write(false, true);
+ this.autoPilotInstinctiveDiscCountSinceLastFwsCycle = 0;
}
updateRowRopWarnings() {
const w = Arinc429Word.fromSimVarValue('L:A32NX_ROW_ROP_WORD_1');
// ROW
- SimVar.SetSimVarValue('L:A32NX_AUDIO_ROW_RWY_TOO_SHORT', 'bool', w.bitValueOr(15, false));
+ this.soundManager.handleSoundCondition('runwayTooShort', w.bitValueOr(15, false));
// ROP
// MAX BRAKING, only for manual braking, if maximum pedal braking is not applied
@@ -2505,26 +2919,105 @@ export class PseudoFWC {
SimVar.GetSimVarValue('L:A32NX_LEFT_BRAKE_PEDAL_INPUT', 'number') > 90 ||
SimVar.GetSimVarValue('L:A32NX_RIGHT_BRAKE_PEDAL_INPUT', 'number') > 90;
const maxBraking = w.bitValueOr(13, false) && !maxBrakingSet;
- SimVar.SetSimVarValue('L:A32NX_AUDIO_ROP_MAX_BRAKING', 'bool', maxBraking);
+ this.soundManager.handleSoundCondition('brakeMaxBraking', maxBraking);
// SET MAX REVERSE, if not already max. reverse set and !MAX_BRAKING
const maxReverseSet =
SimVar.GetSimVarValue('L:XMLVAR_Throttle1Position', 'number') < 0.1 &&
SimVar.GetSimVarValue('L:XMLVAR_Throttle2Position', 'number') < 0.1;
const maxReverse = (w.bitValueOr(12, false) || w.bitValueOr(13, false)) && !maxReverseSet;
- SimVar.SetSimVarValue('L:A32NX_AUDIO_ROW_SET_MAX_REVERSE', 'bool', !maxBraking && maxReverse);
+ this.soundManager.handleSoundCondition('setMaxReverse', !maxBraking && maxReverse);
// At 80kt, KEEP MAX REVERSE once, if max. reversers deployed
const ias = SimVar.GetSimVarValue('AIRSPEED INDICATED', 'knots');
- SimVar.SetSimVarValue(
- 'L:A32NX_AUDIO_ROP_KEEP_MAX_REVERSE',
- 'bool',
+ this.soundManager.handleSoundCondition(
+ 'keepMaxReverse',
ias <= 80 && ias > 4 && (w.bitValueOr(12, false) || w.bitValueOr(13, false)),
);
}
+ autoThrottleInstinctiveDisconnect() {
+ // When instinctive A/THR disc. p/b is pressed after ABRK deactivation, inhibit audio+memo, don't request master caution
+ // Unclear refs, whether this has to happen within the audio confirm node time (1s)
+ if (this.autoBrakeDeactivatedNode.read()) {
+ this.requestMasterCautionFromABrkOff = false;
+ }
+
+ this.aThrDiscInputBuffer.write(true, false);
+
+ if (this.autoThrustOffVoluntary.get()) {
+ // Pressed a second time -> silence
+ this.autoThrustInhibitCaution = true;
+ this.requestMasterCautionFromAThrOff = false;
+ }
+ }
+
+ autoPilotInstinctiveDisconnect() {
+ this.apDiscInputBuffer.write(true, false);
+ if (this.apDiscInputBuffer.read()) {
+ this.autoPilotInstinctiveDiscCountSinceLastFwsCycle++;
+ }
+ }
+
ewdMessageFailures: EWDMessageDict = {
+ // 22 - FLIGHT GUIDANCE
+ 220800001: {
+ // AP OFF involuntary
+ flightPhaseInhib: [],
+ simVarIsActive: this.autoPilotOffAlertShown,
+ auralWarning: this.autoPilotOffInvoluntary.map((a) => (a ? FwcAuralWarning.CavalryCharge : FwcAuralWarning.None)),
+ whichCodeToReturn: () => [0],
+ codesToReturn: ['220800001'],
+ memoInhibit: () => false,
+ failure: 3,
+ sysPage: -1,
+ side: 'LEFT',
+ },
+ 220800004: {
+ // A/THR OFF involuntary
+ flightPhaseInhib: [3, 4, 8],
+ simVarIsActive: this.autoThrustOffInvoluntary,
+ whichCodeToReturn: () => [0, this.thrLocked.get() ? 1 : null],
+ codesToReturn: ['220800004', '220800005'],
+ memoInhibit: () => false,
+ failure: 2,
+ sysPage: -1,
+ side: 'LEFT',
+ },
// 22 - AUTOFLIGHT
+ 2200202: {
+ // FCU 1+2 FAULT
+ flightPhaseInhib: [3, 4, 5, 7, 8],
+ simVarIsActive: this.fcu12Fault,
+ whichCodeToReturn: () => [0, 1],
+ codesToReturn: ['220020201', '220020202'],
+ memoInhibit: () => false,
+ failure: 2,
+ sysPage: -1,
+ side: 'LEFT',
+ },
+ 2200210: {
+ // FCU 1 FAULT
+ flightPhaseInhib: [3, 4, 5, 7, 8],
+ simVarIsActive: this.fcu1Fault,
+ whichCodeToReturn: () => [0, 1],
+ codesToReturn: ['220021001', '220021002'],
+ memoInhibit: () => false,
+ failure: 1,
+ sysPage: -1,
+ side: 'LEFT',
+ },
+ 2200215: {
+ // FCU 2 FAULT
+ flightPhaseInhib: [3, 4, 5, 7, 8],
+ simVarIsActive: this.fcu2Fault,
+ whichCodeToReturn: () => [0, 1],
+ codesToReturn: ['220021501', '220021502'],
+ memoInhibit: () => false,
+ failure: 1,
+ sysPage: -1,
+ side: 'LEFT',
+ },
2210700: {
// TO SPEEDS TOO LOW
flightPhaseInhib: [1, 4, 5, 6, 7, 8, 9, 10],
@@ -4282,6 +4775,18 @@ export class PseudoFWC {
sysPage: -1,
side: 'RIGHT',
},
+ // 32 LANDING GEAR
+ 320000001: {
+ // AUTO BRK OFF
+ flightPhaseInhib: [1, 2, 3, 4, 5, 6, 7, 10],
+ simVarIsActive: this.autoBrakeOff,
+ whichCodeToReturn: () => [0],
+ codesToReturn: ['320000001'],
+ memoInhibit: () => false,
+ failure: 0,
+ sysPage: -1,
+ side: 'RIGHT',
+ },
'0000040': {
// NW STRG DISC
flightPhaseInhib: [],
@@ -4580,5 +5085,28 @@ export class PseudoFWC {
sysPage: -1,
side: 'RIGHT',
},
+ // 22 - Flight guidance
+ 220000001: {
+ // A/THR OFF
+ flightPhaseInhib: [],
+ simVarIsActive: this.autoPilotOffShowMemo,
+ whichCodeToReturn: () => [0],
+ codesToReturn: ['220000001'],
+ memoInhibit: () => false,
+ failure: 0,
+ sysPage: -1,
+ side: 'RIGHT',
+ },
+ 220000002: {
+ // A/THR OFF
+ flightPhaseInhib: [],
+ simVarIsActive: this.autoThrustOffVoluntary,
+ whichCodeToReturn: () => [0],
+ codesToReturn: ['220000002'],
+ memoInhibit: () => false,
+ failure: 0,
+ sysPage: -1,
+ side: 'RIGHT',
+ },
};
}
diff --git a/fbw-a32nx/src/systems/systems-host/systems/atsu.ts b/fbw-a32nx/src/systems/systems-host/systems/atsu.ts
index 256c359a796..f129b08fe98 100644
--- a/fbw-a32nx/src/systems/systems-host/systems/atsu.ts
+++ b/fbw-a32nx/src/systems/systems-host/systems/atsu.ts
@@ -6,10 +6,10 @@ import { Atc } from '@datalink/atc';
import { Aoc } from '@datalink/aoc';
import { SimVarHandling } from '@datalink/common';
import { Router } from '@datalink/router';
-import { EventBus, EventSubscriber } from '@microsoft/msfs-sdk';
+import { EventBus, EventSubscriber, Instrument } from '@microsoft/msfs-sdk';
import { PowerSupplyBusTypes } from 'systems-host/systems/powersupply';
-export class AtsuSystem {
+export class AtsuSystem implements Instrument {
private readonly simVarHandling: SimVarHandling;
private readonly powerSupply: EventSubscriber;
@@ -40,18 +40,15 @@ export class AtsuSystem {
});
}
- public connectedCallback(): void {
+ public init(): void {
this.simVarHandling.initialize();
+ this.simVarHandling.startPublish();
this.router.initialize();
this.atc.initialize();
this.aoc.initialize();
}
- public startPublish(): void {
- this.simVarHandling.startPublish();
- }
-
- public update(): void {
+ public onUpdate(): void {
this.simVarHandling.update();
this.router.update();
}
diff --git a/fbw-a32nx/src/systems/systems-host/systems/powersupply.ts b/fbw-a32nx/src/systems/systems-host/systems/powersupply.ts
index 0fc4ca65137..796f174d292 100644
--- a/fbw-a32nx/src/systems/systems-host/systems/powersupply.ts
+++ b/fbw-a32nx/src/systems/systems-host/systems/powersupply.ts
@@ -3,6 +3,7 @@
// SPDX-License-Identifier: GPL-3.0
import {
+ BackplanePublisher,
EventBus,
EventSubscriber,
Publisher,
@@ -53,7 +54,7 @@ export interface PowerSupplyBusTypes {
dcBusEss: boolean;
}
-export class PowerSupplyBusses {
+export class PowerSupplyBusses implements BackplanePublisher {
private simVarPublisher: PowerSupplySimvarPublisher = null;
private subscriber: EventSubscriber = null;
@@ -94,22 +95,12 @@ export class PowerSupplyBusses {
.handle((powered: number) => this.publisher.pub('dcBusEss', powered !== 0, false, false));
}
- public connectedCallback(): void {
- this.initialize();
-
- this.simVarPublisher.subscribe('msfsAcBus1');
- this.simVarPublisher.subscribe('msfsAcBus2');
- this.simVarPublisher.subscribe('msfsAcBusEss');
- this.simVarPublisher.subscribe('msfsDcBus1');
- this.simVarPublisher.subscribe('msfsDcBus2');
- this.simVarPublisher.subscribe('msfsDcBusEss');
- }
-
public startPublish(): void {
+ this.initialize();
this.simVarPublisher.startPublish();
}
- public update(): void {
+ public onUpdate(): void {
this.simVarPublisher.onUpdate();
}
}
diff --git a/fbw-a32nx/src/wasm/fbw_a320/src/fcu/Fcu.cpp b/fbw-a32nx/src/wasm/fbw_a320/src/fcu/Fcu.cpp
index a0712c2f84a..03e33cb0e79 100644
--- a/fbw-a32nx/src/wasm/fbw_a320/src/fcu/Fcu.cpp
+++ b/fbw-a32nx/src/wasm/fbw_a320/src/fcu/Fcu.cpp
@@ -71,6 +71,9 @@ base_fcu_bus Fcu::getBusOutputs() {
return {};
}
+ Arinc429Utils::setBit(modelOutputs.bus_outputs.fcu_discrete_word_2, 24, monitoringHealthy[0]);
+ Arinc429Utils::setBit(modelOutputs.bus_outputs.fcu_discrete_word_2, 25, monitoringHealthy[1]);
+
return modelOutputs.bus_outputs;
}
diff --git a/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.cpp b/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.cpp
index 68c39bf1722..6789785aa13 100644
--- a/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.cpp
+++ b/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.cpp
@@ -291,6 +291,7 @@ bool SimConnectInterface::prepareSimInputSimConnectDataDefinitions() {
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTOPILOT_DISENGAGE_SET, "AUTOPILOT_DISENGAGE_SET", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTOPILOT_DISENGAGE_TOGGLE, "AUTOPILOT_DISENGAGE_TOGGLE", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::TOGGLE_FLIGHT_DIRECTOR, "TOGGLE_FLIGHT_DIRECTOR", true);
+ result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_AUTOPILOT_DISENGAGE, "A32NX.AUTOPILOT_DISENGAGE", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_FCU_AP_1_PUSH, "A32NX.FCU_AP_1_PUSH", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_FCU_AP_2_PUSH, "A32NX.FCU_AP_2_PUSH", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_FCU_AP_DISCONNECT_PUSH, "A32NX.FCU_AP_DISCONNECT_PUSH", false);
@@ -397,6 +398,7 @@ bool SimConnectInterface::prepareSimInputSimConnectDataDefinitions() {
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTO_THROTTLE_ARM, "AUTO_THROTTLE_ARM", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTO_THROTTLE_DISCONNECT, "AUTO_THROTTLE_DISCONNECT", true);
+ result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_AUTO_THROTTLE_DISCONNECT, "A32NX.AUTO_THROTTLE_DISCONNECT", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTO_THROTTLE_TO_GA, "AUTO_THROTTLE_TO_GA", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_ATHR_RESET_DISABLE, "A32NX.ATHR_RESET_DISABLE", false);
@@ -1810,6 +1812,9 @@ void SimConnectInterface::processEvent(const DWORD eventId, const DWORD data0, c
if (static_cast(data0) == 1) {
simInputAutopilot.AP_disconnect = 1;
std::cout << "WASM: event triggered: AUTOPILOT_DISENGAGE_SET" << std::endl;
+
+ // Re emitting masked event for autopilot disconnection
+ sendEvent(SimConnectInterface::Events::A32NX_AUTOPILOT_DISENGAGE, 0, SIMCONNECT_GROUP_PRIORITY_STANDARD);
}
break;
}
@@ -2436,6 +2441,9 @@ void SimConnectInterface::processEvent(const DWORD eventId, const DWORD data0, c
case Events::AUTO_THROTTLE_DISCONNECT: {
simInputThrottles.ATHR_disconnect = 1;
std::cout << "WASM: event triggered: AUTO_THROTTLE_DISCONNECT" << std::endl;
+
+ // Re emitting masked event
+ sendEvent(Events::A32NX_AUTO_THROTTLE_DISCONNECT, 0, SIMCONNECT_GROUP_PRIORITY_STANDARD);
break;
}
diff --git a/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.h b/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.h
index fe4f980c487..f644c9cfef3 100644
--- a/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.h
+++ b/fbw-a32nx/src/wasm/fbw_a320/src/interface/SimConnectInterface.h
@@ -47,6 +47,7 @@ class SimConnectInterface {
AUTOPILOT_DISENGAGE_SET,
AUTOPILOT_DISENGAGE_TOGGLE,
TOGGLE_FLIGHT_DIRECTOR,
+ A32NX_AUTOPILOT_DISENGAGE,
A32NX_FCU_AP_1_PUSH,
A32NX_FCU_AP_2_PUSH,
A32NX_FCU_AP_DISCONNECT_PUSH,
@@ -148,6 +149,7 @@ class SimConnectInterface {
BAROMETRIC,
AUTO_THROTTLE_ARM,
AUTO_THROTTLE_DISCONNECT,
+ A32NX_AUTO_THROTTLE_DISCONNECT,
AUTO_THROTTLE_TO_GA,
A32NX_ATHR_RESET_DISABLE,
A32NX_THROTTLE_MAPPING_SET_DEFAULTS,
diff --git a/fbw-a32nx/src/wasm/systems/a320_hydraulic_simulation_graphs/Cargo.toml b/fbw-a32nx/src/wasm/systems/a320_hydraulic_simulation_graphs/Cargo.toml
index 6dcc005da03..318ac01f5cf 100644
--- a/fbw-a32nx/src/wasm/systems/a320_hydraulic_simulation_graphs/Cargo.toml
+++ b/fbw-a32nx/src/wasm/systems/a320_hydraulic_simulation_graphs/Cargo.toml
@@ -13,8 +13,8 @@ systems = { path = "../../../../../fbw-common/src/wasm/systems/systems" }
a320_systems = { path = "../a320_systems" }
uom = "0.36.0"
rand = "0.8.0"
-ntest = "0.7.2"
-num-derive = "0.3.3"
+ntest = "0.9.3"
+num-derive = "0.4.2"
num-traits = "0.2.14"
plotlib = "0.5.1"
rustplotlib = "0.0.4"
diff --git a/fbw-a32nx/src/wasm/systems/a320_systems/Cargo.toml b/fbw-a32nx/src/wasm/systems/a320_systems/Cargo.toml
index 73db92ea2aa..aec30911938 100644
--- a/fbw-a32nx/src/wasm/systems/a320_systems/Cargo.toml
+++ b/fbw-a32nx/src/wasm/systems/a320_systems/Cargo.toml
@@ -6,11 +6,11 @@ edition = "2021"
[dependencies]
uom = "0.36.0"
-nalgebra = "0.25.0"
-ntest = "0.7.2"
+nalgebra = "0.33.0"
+ntest = "0.9.0"
systems = { path = "../../../../../fbw-common/src/wasm/systems/systems" }
[dev-dependencies]
-rstest = "0.10.0"
+rstest = "0.12.0"
rand = "0.8.0"
rand_pcg = "0.3.1"
diff --git a/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/cameras.cfg b/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/cameras.cfg
index 3f46840e6ab..e786fca7f18 100644
--- a/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/cameras.cfg
+++ b/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/cameras.cfg
@@ -38,8 +38,8 @@ SubCategory ="Pilot"
SubCategoryItem ="DefaultPilot"
PitchPanRate =20
HeadingPanRate =60
-InitialXyz= 0, 1.956999, 18.6
-InitialPbh= -11.397058, -0.007368, 0.244131
+InitialXyz= 0, 1.893, 18.6
+InitialPbh= -9.244958, -0.004128, 0.244043
NodesToHide =""
ClipMode ="Normal"
BoundingBoxRadius =0.1
@@ -165,8 +165,8 @@ SnapPbhReturn=1
InstancedBased=0
NoSortTitle=0
Transition=0
-InitialXyz= 0.92399, 1.957001, 18.596704
-InitialPbh= -11.397008, 0.000366, 0.136788
+InitialXyz= 1.043988, 1.893, 18.596704
+InitialPbh= -9.244958, -0.004128, 0.244043
Category ="Cockpit"
SubCategory ="Pilot"
SubCategoryItem ="CoPilot"
@@ -1464,7 +1464,7 @@ XYZRate =0.25
XYZAcceleratorTime =0
[CAMERADEFINITION.36]
-Title ="FixedOnPlane_WindowView01"
+Title ="FixedOnPlane_WindowView01"
UITitle ="TT:GAME.PANEL_CAMERA_FIXEDONPLANE_16"
Guid ="{D985C44F-5EC7-489D-A4CA-E9BB5AE4B7C2}"
Description=""
@@ -1684,4 +1684,4 @@ NoSortTitle = 0
Transition = 0
PanAcceleratorTime = 5
XYZRate = 0.25
-XYZAcceleratorTime = 0
\ No newline at end of file
+XYZAcceleratorTime = 0
diff --git a/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/model/behaviour/efis-cp.xml b/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/model/behaviour/efis-cp.xml
index f692bf6dd37..7bef6b09f52 100644
--- a/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/model/behaviour/efis-cp.xml
+++ b/fbw-a380x/src/base/flybywire-aircraft-a380-842/SimObjects/AirPlanes/FlyByWire_A380_842/model/behaviour/efis-cp.xml
@@ -20,7 +20,7 @@
- (#SIMVAR_NAME#, Enum) #SIMVAR_VALUE# == #INDICATOR_POWERED# and
+ (#SIMVAR_NAME#, Enum) #SIMVAR_VALUE# == (L:A32NX_OVHD_INTLT_ANN) 0 == or #INDICATOR_POWERED# and
diff --git a/fbw-a380x/src/base/flybywire-aircraft-a380-842/html_ui/Fonts/fbw-a380x/A380X_FCU.ttf b/fbw-a380x/src/base/flybywire-aircraft-a380-842/html_ui/Fonts/fbw-a380x/A380X_FCU.ttf
index 6469170783c..7d477945dd7 100644
Binary files a/fbw-a380x/src/base/flybywire-aircraft-a380-842/html_ui/Fonts/fbw-a380x/A380X_FCU.ttf and b/fbw-a380x/src/base/flybywire-aircraft-a380-842/html_ui/Fonts/fbw-a380x/A380X_FCU.ttf differ
diff --git a/fbw-a380x/src/fonts/A380X_FCU.sfd b/fbw-a380x/src/fonts/A380X_FCU.sfd
index 2a39043f653..7e8922de6e5 100644
--- a/fbw-a380x/src/fonts/A380X_FCU.sfd
+++ b/fbw-a380x/src/fonts/A380X_FCU.sfd
@@ -22,7 +22,7 @@ OS2Version: 4
OS2_WeightWidthSlopeOnly: 0
OS2_UseTypoMetrics: 1
CreationTime: 1603675803
-ModificationTime: 1732268502
+ModificationTime: 1733903687
PfmFamily: 17
TTFWeight: 400
TTFWidth: 5
@@ -59,6 +59,673 @@ OS2CodePages: 00000001.00000000
OS2UnicodeRanges: 00000003.00000000.00000000.00000000
MarkAttachClasses: 1
DEI: 91125
+TtTable: prep
+PUSHW_1
+ 511
+SCANCTRL
+PUSHB_1
+ 1
+SCANTYPE
+SVTCA[y-axis]
+MPPEM
+PUSHB_1
+ 8
+LT
+IF
+PUSHB_2
+ 1
+ 1
+INSTCTRL
+EIF
+PUSHB_2
+ 70
+ 6
+CALL
+IF
+POP
+PUSHB_1
+ 16
+EIF
+MPPEM
+PUSHB_1
+ 20
+GT
+IF
+POP
+PUSHB_1
+ 128
+EIF
+SCVTCI
+PUSHB_1
+ 6
+CALL
+NOT
+IF
+EIF
+PUSHB_1
+ 20
+CALL
+EndTTInstrs
+TtTable: fpgm
+PUSHB_1
+ 0
+FDEF
+PUSHB_1
+ 0
+SZP0
+MPPEM
+PUSHB_1
+ 42
+LT
+IF
+PUSHB_1
+ 74
+SROUND
+EIF
+PUSHB_1
+ 0
+SWAP
+MIAP[rnd]
+RTG
+PUSHB_1
+ 6
+CALL
+IF
+RTDG
+EIF
+MPPEM
+PUSHB_1
+ 42
+LT
+IF
+RDTG
+EIF
+DUP
+MDRP[rp0,rnd,grey]
+PUSHB_1
+ 1
+SZP0
+MDAP[no-rnd]
+RTG
+ENDF
+PUSHB_1
+ 1
+FDEF
+DUP
+MDRP[rp0,min,white]
+PUSHB_1
+ 12
+CALL
+ENDF
+PUSHB_1
+ 2
+FDEF
+MPPEM
+GT
+IF
+RCVT
+SWAP
+EIF
+POP
+ENDF
+PUSHB_1
+ 3
+FDEF
+ROUND[Black]
+RTG
+DUP
+PUSHB_1
+ 64
+LT
+IF
+POP
+PUSHB_1
+ 64
+EIF
+ENDF
+PUSHB_1
+ 4
+FDEF
+PUSHB_1
+ 6
+CALL
+IF
+POP
+SWAP
+POP
+ROFF
+IF
+MDRP[rp0,min,rnd,black]
+ELSE
+MDRP[min,rnd,black]
+EIF
+ELSE
+MPPEM
+GT
+IF
+IF
+MIRP[rp0,min,rnd,black]
+ELSE
+MIRP[min,rnd,black]
+EIF
+ELSE
+SWAP
+POP
+PUSHB_1
+ 5
+CALL
+IF
+PUSHB_1
+ 70
+SROUND
+EIF
+IF
+MDRP[rp0,min,rnd,black]
+ELSE
+MDRP[min,rnd,black]
+EIF
+EIF
+EIF
+RTG
+ENDF
+PUSHB_1
+ 5
+FDEF
+GFV
+NOT
+AND
+ENDF
+PUSHB_1
+ 6
+FDEF
+PUSHB_2
+ 34
+ 1
+GETINFO
+LT
+IF
+PUSHB_1
+ 32
+GETINFO
+NOT
+NOT
+ELSE
+PUSHB_1
+ 0
+EIF
+ENDF
+PUSHB_1
+ 7
+FDEF
+PUSHB_2
+ 36
+ 1
+GETINFO
+LT
+IF
+PUSHB_1
+ 64
+GETINFO
+NOT
+NOT
+ELSE
+PUSHB_1
+ 0
+EIF
+ENDF
+PUSHB_1
+ 8
+FDEF
+SRP2
+SRP1
+DUP
+IP
+MDAP[rnd]
+ENDF
+PUSHB_1
+ 9
+FDEF
+DUP
+RDTG
+PUSHB_1
+ 6
+CALL
+IF
+MDRP[rnd,grey]
+ELSE
+MDRP[min,rnd,black]
+EIF
+DUP
+PUSHB_1
+ 3
+CINDEX
+MD[grid]
+SWAP
+DUP
+PUSHB_1
+ 4
+MINDEX
+MD[orig]
+PUSHB_1
+ 0
+LT
+IF
+ROLL
+NEG
+ROLL
+SUB
+DUP
+PUSHB_1
+ 0
+LT
+IF
+SHPIX
+ELSE
+POP
+POP
+EIF
+ELSE
+ROLL
+ROLL
+SUB
+DUP
+PUSHB_1
+ 0
+GT
+IF
+SHPIX
+ELSE
+POP
+POP
+EIF
+EIF
+RTG
+ENDF
+PUSHB_1
+ 10
+FDEF
+PUSHB_1
+ 6
+CALL
+IF
+POP
+SRP0
+ELSE
+SRP0
+POP
+EIF
+ENDF
+PUSHB_1
+ 11
+FDEF
+DUP
+MDRP[rp0,white]
+PUSHB_1
+ 12
+CALL
+ENDF
+PUSHB_1
+ 12
+FDEF
+DUP
+MDAP[rnd]
+PUSHB_1
+ 7
+CALL
+NOT
+IF
+DUP
+DUP
+GC[orig]
+SWAP
+GC[cur]
+SUB
+ROUND[White]
+DUP
+IF
+DUP
+ABS
+DIV
+SHPIX
+ELSE
+POP
+POP
+EIF
+ELSE
+POP
+EIF
+ENDF
+PUSHB_1
+ 13
+FDEF
+SRP2
+SRP1
+DUP
+DUP
+IP
+MDAP[rnd]
+DUP
+ROLL
+DUP
+GC[orig]
+ROLL
+GC[cur]
+SUB
+SWAP
+ROLL
+DUP
+ROLL
+SWAP
+MD[orig]
+PUSHB_1
+ 0
+LT
+IF
+SWAP
+PUSHB_1
+ 0
+GT
+IF
+PUSHB_1
+ 64
+SHPIX
+ELSE
+POP
+EIF
+ELSE
+SWAP
+PUSHB_1
+ 0
+LT
+IF
+PUSHB_1
+ 64
+NEG
+SHPIX
+ELSE
+POP
+EIF
+EIF
+ENDF
+PUSHB_1
+ 14
+FDEF
+PUSHB_1
+ 6
+CALL
+IF
+RTDG
+MDRP[rp0,rnd,white]
+RTG
+POP
+POP
+ELSE
+DUP
+MDRP[rp0,rnd,white]
+ROLL
+MPPEM
+GT
+IF
+DUP
+ROLL
+SWAP
+MD[grid]
+DUP
+PUSHB_1
+ 0
+NEQ
+IF
+SHPIX
+ELSE
+POP
+POP
+EIF
+ELSE
+POP
+POP
+EIF
+EIF
+ENDF
+PUSHB_1
+ 15
+FDEF
+SWAP
+DUP
+MDRP[rp0,rnd,white]
+DUP
+MDAP[rnd]
+PUSHB_1
+ 7
+CALL
+NOT
+IF
+SWAP
+DUP
+IF
+MPPEM
+GTEQ
+ELSE
+POP
+PUSHB_1
+ 1
+EIF
+IF
+ROLL
+PUSHB_1
+ 4
+MINDEX
+MD[grid]
+SWAP
+ROLL
+SWAP
+DUP
+ROLL
+MD[grid]
+ROLL
+SWAP
+SUB
+SHPIX
+ELSE
+POP
+POP
+POP
+POP
+EIF
+ELSE
+POP
+POP
+POP
+POP
+POP
+EIF
+ENDF
+PUSHB_1
+ 16
+FDEF
+DUP
+MDRP[rp0,min,white]
+PUSHB_1
+ 18
+CALL
+ENDF
+PUSHB_1
+ 17
+FDEF
+DUP
+MDRP[rp0,white]
+PUSHB_1
+ 18
+CALL
+ENDF
+PUSHB_1
+ 18
+FDEF
+DUP
+MDAP[rnd]
+PUSHB_1
+ 7
+CALL
+NOT
+IF
+DUP
+DUP
+GC[orig]
+SWAP
+GC[cur]
+SUB
+ROUND[White]
+ROLL
+DUP
+GC[orig]
+SWAP
+GC[cur]
+SWAP
+SUB
+ROUND[White]
+ADD
+DUP
+IF
+DUP
+ABS
+DIV
+SHPIX
+ELSE
+POP
+POP
+EIF
+ELSE
+POP
+POP
+EIF
+ENDF
+PUSHB_1
+ 19
+FDEF
+DUP
+ROLL
+DUP
+ROLL
+SDPVTL[orthog]
+DUP
+PUSHB_1
+ 3
+CINDEX
+MD[orig]
+ABS
+SWAP
+ROLL
+SPVTL[orthog]
+PUSHB_1
+ 32
+LT
+IF
+ALIGNRP
+ELSE
+MDRP[grey]
+EIF
+ENDF
+PUSHB_1
+ 20
+FDEF
+PUSHB_4
+ 0
+ 64
+ 1
+ 64
+WS
+WS
+SVTCA[x-axis]
+MPPEM
+PUSHW_1
+ 4096
+MUL
+SVTCA[y-axis]
+MPPEM
+PUSHW_1
+ 4096
+MUL
+DUP
+ROLL
+DUP
+ROLL
+NEQ
+IF
+DUP
+ROLL
+DUP
+ROLL
+GT
+IF
+SWAP
+DIV
+DUP
+PUSHB_1
+ 0
+SWAP
+WS
+ELSE
+DIV
+DUP
+PUSHB_1
+ 1
+SWAP
+WS
+EIF
+DUP
+PUSHB_1
+ 64
+GT
+IF
+PUSHB_3
+ 0
+ 32
+ 0
+RS
+MUL
+WS
+PUSHB_3
+ 1
+ 32
+ 1
+RS
+MUL
+WS
+PUSHB_1
+ 32
+MUL
+PUSHB_1
+ 25
+NEG
+JMPR
+POP
+EIF
+ELSE
+POP
+POP
+EIF
+ENDF
+PUSHB_1
+ 21
+FDEF
+PUSHB_1
+ 1
+RS
+MUL
+SWAP
+PUSHB_1
+ 0
+RS
+MUL
+SWAP
+ENDF
+EndTTInstrs
+ShortTable: cvt 5
+ -193
+ 0
+ 377
+ 786
+ 793
+EndShort
ShortTable: maxp 16
1
0
@@ -68,11 +735,11 @@ ShortTable: maxp 16
0
0
2
- 0
- 1
1
+ 2
+ 22
0
- 64
+ 256
0
0
0
@@ -86,7 +753,7 @@ DisplaySize: -48
AntiAlias: 1
FitToEm: 0
WinInfo: 0 29 11
-BeginChars: 65539 37
+BeginChars: 65539 41
StartChar: .notdef
Encoding: 65536 -1 0
@@ -132,86 +799,86 @@ EndChar
StartChar: plus
Encoding: 43 43 3
-Width: 600
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-354 403 m 0,0,1
- 350 396 350 396 343 396 c 2,2,-1
- 257 396 l 2,3,4
- 250 396 250 396 246 403 c 0,5,6
- 235 421 235 421 226 437 c 0,7,8
- 221 446 221 446 221 457 c 128,-1,9
- 221 468 221 468 226 477 c 0,10,11
- 274 557 274 557 287 578 c 0,12,13
- 291 585 291 585 300 585 c 128,-1,14
- 309 585 309 585 313 578 c 0,15,16
- 320 567 320 567 343 528.5 c 128,-1,17
- 366 490 366 490 374 477 c 0,18,19
- 380 468 380 468 380 457.5 c 128,-1,20
- 380 447 380 447 374 437 c 0,21,22
- 361 415 361 415 354 403 c 0,0,1
-167 366 m 0,23,24
- 185 377 185 377 207 377 c 2,25,-1
- 427 377 l 2,26,27
- 434 377 434 377 440 372 c 0,28,29
- 455 355 455 355 487 321 c 0,30,31
- 496 311 496 311 496 298 c 0,32,33
- 496 284 496 284 486 274 c 0,34,35
- 461 248 461 248 442 230 c 0,36,37
- 435 222 435 222 423 222 c 2,38,-1
- 204 222 l 2,39,40
- 185 222 185 222 169 231 c 0,41,42
- 164 234 164 234 93 275 c 0,43,44
- 80 282 80 282 80 298 c 0,45,46
- 80 313 80 313 93 321 c 0,47,48
- 100 325 100 325 127 341.5 c 128,-1,49
- 154 358 154 358 167 366 c 0,23,24
-354 196 m 0,50,51
- 361 184 361 184 374 162 c 0,52,53
- 380 152 380 152 380 141.5 c 128,-1,54
- 380 131 380 131 374 122 c 0,55,56
- 330 48 330 48 313 21 c 0,57,58
- 309 14 309 14 300 14 c 128,-1,59
- 291 14 291 14 287 21 c 0,60,61
- 280 33 280 33 257 71 c 128,-1,62
- 234 109 234 109 226 122 c 0,63,64
- 221 131 221 131 221 142 c 128,-1,65
- 221 153 221 153 226 162 c 0,66,67
- 242 189 242 189 246 196 c 0,68,69
- 250 202 250 202 257 202 c 2,70,-1
- 343 202 l 2,71,72
- 350 202 350 202 354 196 c 0,50,51
+359 479 m 0,0,1
+ 355 473 355 473 350 473 c 2,2,-1
+ 281 473 l 2,3,4
+ 275 473 275 473 272 479 c 0,5,6
+ 267 488 267 488 256 506 c 0,7,8
+ 251 514 251 514 252 522 c 0,9,10
+ 253 532 253 532 256 538 c 0,11,12
+ 282 591 282 591 305 619 c 0,13,14
+ 309 624 309 624 316 624 c 128,-1,15
+ 323 624 323 624 326 619 c 0,16,17
+ 332 610 332 610 350 579 c 128,-1,18
+ 368 548 368 548 375 538 c 0,19,20
+ 380 531 380 531 380 522 c 0,21,22
+ 380 515 380 515 375 506 c 0,23,24
+ 369 496 369 496 359 479 c 0,0,1
+209 449 m 0,25,26
+ 224 458 224 458 241 458 c 2,27,-1
+ 417 458 l 2,28,29
+ 425 458 425 458 428 454 c 0,30,31
+ 440 440 440 440 465 413 c 0,32,33
+ 471 406 471 406 472 395 c 128,-1,34
+ 473 384 473 384 464 375 c 0,35,36
+ 446 358 446 358 429 340 c 0,37,38
+ 423 334 423 334 414 334 c 2,39,-1
+ 239 334 l 2,40,41
+ 225 334 225 334 211 341 c 0,42,43
+ 195 349 195 349 150 376 c 0,44,45
+ 141 381 141 381 140 395 c 0,46,47
+ 139 406 139 406 150 413 c 0,48,49
+ 156 416 156 416 177.5 429.5 c 128,-1,50
+ 199 443 199 443 209 449 c 0,25,26
+359 313 m 0,51,52
+ 364 303 364 303 375 286 c 0,53,54
+ 380 278 380 278 380 269 c 128,-1,55
+ 380 260 380 260 375 254 c 0,56,57
+ 340 195 340 195 326 173 c 0,58,59
+ 323 167 323 167 315.5 167 c 128,-1,60
+ 308 167 308 167 305 173 c 0,61,62
+ 299 183 299 183 281 213 c 128,-1,63
+ 263 243 263 243 256 254 c 0,64,65
+ 252 261 252 261 252 270 c 128,-1,66
+ 252 279 252 279 256 286 c 0,67,68
+ 269 308 269 308 272 313 c 128,-1,69
+ 275 318 275 318 281 318 c 2,70,-1
+ 350 318 l 2,71,72
+ 356 318 356 318 359 313 c 0,51,52
EndSplineSet
Validated: 1
EndChar
StartChar: hyphen
Encoding: 45 45 4
-Width: 600
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-167 363 m 0,0,1
- 185 374 185 374 207 374 c 2,2,-1
- 427 374 l 2,3,4
- 434 374 434 374 440 368 c 0,5,6
- 455 352 455 352 487 318 c 0,7,8
- 496 308 496 308 496 295 c 0,9,10
- 496 281 496 281 486 271 c 0,11,12
- 461 245 461 245 442 227 c 0,13,14
- 435 219 435 219 423 219 c 2,15,-1
- 204 219 l 2,16,17
- 185 219 185 219 169 228 c 0,18,19
- 164 231 164 231 93 272 c 0,20,21
- 80 279 80 279 80 295 c 0,22,23
- 80 310 80 310 93 318 c 0,24,25
- 100 322 100 322 127 338.5 c 128,-1,26
- 154 355 154 355 167 363 c 0,0,1
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
EndSplineSet
Validated: 1
EndChar
@@ -224,15 +891,15 @@ Flags: W
LayerCount: 2
Fore
SplineSet
--70 -100 m 128,-1,1
- -70 -71 -70 -71 -49 -50 c 128,-1,2
- -28 -29 -28 -29 1 -29 c 128,-1,3
- 30 -29 30 -29 51 -50 c 128,-1,4
- 72 -71 72 -71 72 -100 c 128,-1,5
- 72 -129 72 -129 51 -150 c 128,-1,6
- 30 -171 30 -171 1 -171 c 128,-1,7
- -28 -171 -28 -171 -49 -150 c 128,-1,0
- -70 -129 -70 -129 -70 -100 c 128,-1,1
+-56 58 m 132,-1,1
+ -56 81 -56 81 -39 98 c 132,-1,2
+ -22 115 -22 115 1 115 c 132,-1,3
+ 24 115 24 115 41 98 c 132,-1,4
+ 58 81 58 81 58 58 c 132,-1,5
+ 58 35 58 35 41 18 c 132,-1,6
+ 24 1 24 1 1 1 c 132,-1,7
+ -22 1 -22 1 -39 18 c 132,-1,0
+ -56 35 -56 35 -56 58 c 132,-1,1
EndSplineSet
Validated: 1
EndChar
@@ -265,1018 +932,1026 @@ EndChar
StartChar: zero
Encoding: 48 48 7
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-114 325 m 0,36,37
- 110 327 110 327 107 330 c 0,38,39
- 97 339 97 339 97 352 c 2,40,-1
- 97 645 l 2,41,42
- 97 681 97 681 115 711 c 0,43,44
- 115 712 115 712 121 723 c 0,45,46
- 127 733 127 733 139 733 c 0,47,48
- 147 733 147 733 152 727 c 0,49,50
- 158 722 158 722 196 684 c 128,-1,51
- 234 646 234 646 247 633 c 0,52,53
- 259 621 259 621 259 605 c 2,54,-1
- 259 388 l 2,55,56
- 259 377 259 377 249 372 c 0,57,58
- 238 365 238 365 204.5 346 c 128,-1,59
- 171 327 171 327 162 322 c 0,60,61
- 152 317 152 317 141 317 c 0,62,63
- 132 317 132 317 124 320 c 0,64,65
- 117 323 117 323 114 325 c 0,36,37
-153 743 m 0,66,67
- 151 751 151 751 153 754.5 c 128,-1,68
- 155 758 155 758 164 767 c 0,69,70
- 169 772 169 772 179 778 c 0,71,72
- 200 793 200 793 226 793 c 2,73,-1
- 555 793 l 1,74,-1
- 572 792 l 2,75,76
- 573 792 573 792 576 791.5 c 128,-1,77
- 579 791 579 791 581 791 c 0,78,79
- 589 790 589 790 594 785 c 0,80,81
- 600 779 600 779 598 771 c 0,82,83
- 593 761 593 761 542 647 c 0,84,85
- 536 633 536 633 521 633 c 2,86,-1
- 272 633 l 2,87,88
- 260 633 260 633 252 642 c 0,89,90
- 157 735 157 735 153 743 c 0,66,67
-695 278 m 0,91,92
- 700 273 700 273 702 265 c 0,93,94
- 703 258 703 258 703 251 c 2,95,-1
- 703 -45 l 2,96,97
- 703 -72 703 -72 692 -97 c 0,98,99
- 682 -119 682 -119 668 -138 c 0,100,101
- 655 -156 655 -156 638 -170 c 0,102,103
- 631 -175 631 -175 623 -175 c 0,104,105
- 608 -175 608 -175 602 -161 c 0,106,107
- 600 -157 600 -157 577.5 -107.5 c 128,-1,108
- 555 -58 555 -58 547 -40 c 0,109,110
- 541 -28 541 -28 541 -15 c 0,111,112
- 541 18 541 18 541 45.5 c 128,-1,113
- 541 73 541 73 541 94.5 c 128,-1,114
- 541 116 541 116 541 144 c 0,115,116
- 541 167 541 167 541 196 c 0,117,118
- 541 206 541 206 548 214 c 0,119,120
- 592 268 592 268 611 280 c 0,121,122
- 627 291 627 291 649 291 c 0,123,124
- 653 291 653 291 659 290.5 c 128,-1,125
- 665 290 665 290 666 290 c 0,126,127
- 685 289 685 289 695 278 c 0,91,92
-153 -143 m 0,128,129
- 157 -135 157 -135 252 -42 c 0,130,131
- 260 -34 260 -34 272 -34 c 2,132,-1
- 521 -34 l 2,133,134
- 536 -34 536 -34 542 -47 c 0,135,136
- 593 -161 593 -161 598 -172 c 0,137,138
- 600 -179 600 -179 594 -185 c 0,139,140
- 589 -190 589 -190 581 -191 c 0,141,142
- 580 -191 580 -191 576.5 -191.5 c 128,-1,143
- 573 -192 573 -192 572 -192 c 2,144,-1
- 555 -193 l 1,145,-1
- 226 -193 l 2,146,147
- 200 -193 200 -193 179 -178 c 0,148,149
- 169 -172 169 -172 164 -167 c 0,150,151
- 155 -158 155 -158 153 -154.5 c 128,-1,152
- 151 -151 151 -151 153 -143 c 0,128,129
-114 275 m 0,153,154
- 117 277 117 277 124 280 c 0,155,156
- 132 283 132 283 141 283 c 0,157,158
- 152 283 152 283 162 278 c 0,159,160
- 171 273 171 273 204.5 254 c 128,-1,161
- 238 235 238 235 249 228 c 0,162,163
- 259 223 259 223 259 212 c 2,164,-1
- 259 -6 l 2,165,166
- 259 -22 259 -22 247 -33 c 0,167,168
- 234 -46 234 -46 196 -84 c 128,-1,169
- 158 -122 158 -122 152 -127 c 0,170,171
- 147 -133 147 -133 139 -133 c 0,172,173
- 127 -133 127 -133 121 -123 c 256,174,175
- 115 -113 115 -113 115 -112 c 0,176,177
- 97 -81 97 -81 97 -45 c 2,178,-1
- 97 247 l 2,179,180
- 97 261 97 261 107 269 c 0,181,182
- 110 272 110 272 114 275 c 0,153,154
+554 411 m 0,0,1
+ 546 402 546 402 531 402 c 0,2,3
+ 530 402 530 402 525 401.5 c 128,-1,4
+ 520 401 520 401 517 401 c 0,5,6
+ 499 401 499 401 487 410 c 0,7,8
+ 472 420 472 420 436 462 c 0,9,10
+ 430 468 430 468 431 477 c 0,11,12
+ 431 500 431 500 431 519 c 0,13,14
+ 431 541 431 541 431 558 c 128,-1,15
+ 431 575 431 575 431 597 c 128,-1,16
+ 431 619 431 619 431 646 c 0,17,18
+ 431 656 431 656 436 666 c 0,19,20
+ 462 724 462 724 480 763 c 0,21,22
+ 485 773 485 773 496 773 c 0,23,24
+ 502 773 502 773 508 770 c 0,25,26
+ 520 761 520 761 532 744 c 0,27,28
+ 546 726 546 726 552 711 c 0,29,30
+ 560 693 560 693 560 673 c 0,31,32
+ 560 671 560 671 560 669 c 2,33,-1
+ 560 433 l 2,34,35
+ 560 427 560 427 560 422 c 0,36,37
+ 558 415 558 415 554 411 c 0,0,1
+89 416 m 0,38,39
+ 86 418 86 418 84 420 c 0,40,41
+ 76 427 76 427 76 438 c 2,42,-1
+ 76 672 l 2,43,44
+ 76 701 76 701 90 725 c 0,45,46
+ 90 726 90 726 95 735 c 0,47,48
+ 100 743 100 743 109 743 c 0,49,50
+ 115 743 115 743 120 738 c 0,51,52
+ 125 734 125 734 155 703.5 c 128,-1,53
+ 185 673 185 673 196 663 c 0,54,55
+ 206 653 206 653 205 640 c 2,56,-1
+ 205 467 l 2,57,58
+ 205 458 205 458 197 454 c 0,59,60
+ 188 448 188 448 161.5 433 c 128,-1,61
+ 135 418 135 418 128 414 c 0,62,63
+ 120 410 120 410 111 410 c 0,64,65
+ 104 410 104 410 97 412 c 0,66,67
+ 91 414 91 414 89 416 c 0,38,39
+120 751 m 0,68,69
+ 118 757 118 757 120 760 c 128,-1,70
+ 122 763 122 763 129 770 c 0,71,72
+ 133 774 133 774 141 779 c 0,73,74
+ 158 791 158 791 179 791 c 2,75,-1
+ 442 791 l 1,76,-1
+ 456 790 l 2,77,78
+ 457 790 457 790 459 789.5 c 128,-1,79
+ 461 789 461 789 463 789 c 0,80,81
+ 469 788 469 788 473 784 c 0,82,83
+ 478 779 478 779 476 773 c 0,84,85
+ 472 765 472 765 432 674 c 0,86,87
+ 427 663 427 663 415 663 c 2,88,-1
+ 216 663 l 2,89,90
+ 206 663 206 663 200 670 c 0,91,92
+ 123 745 123 745 120 751 c 0,68,69
+554 379 m 0,93,94
+ 558 375 558 375 560 368 c 0,95,96
+ 561 362 561 362 560 357 c 2,97,-1
+ 560 120 l 2,98,99
+ 560 98 560 98 552 79 c 0,100,101
+ 544 61 544 61 532 46 c 0,102,103
+ 522 32 522 32 508 20 c 0,104,105
+ 502 16 502 16 496 16 c 0,106,107
+ 484 16 484 16 480 27 c 0,108,109
+ 478 30 478 30 460 70 c 128,-1,110
+ 442 110 442 110 436 124 c 0,111,112
+ 431 134 431 134 431 144 c 0,113,114
+ 431 170 431 170 431 192.5 c 128,-1,115
+ 431 215 431 215 431 232 c 128,-1,116
+ 431 249 431 249 431 271 c 0,117,118
+ 431 289 431 289 431 313 c 0,119,120
+ 431 321 431 321 436 327 c 0,121,122
+ 471 370 471 370 487 380 c 0,123,124
+ 500 389 500 389 517 389 c 0,125,126
+ 520 389 520 389 525 388.5 c 128,-1,127
+ 530 388 530 388 531 388 c 0,128,129
+ 546 388 546 388 554 379 c 0,93,94
+120 42 m 0,130,131
+ 123 48 123 48 200 123 c 0,132,133
+ 206 129 206 129 216 129 c 2,134,-1
+ 415 129 l 2,135,136
+ 427 129 427 129 432 119 c 0,137,138
+ 473 28 473 28 476 19 c 0,139,140
+ 478 13 478 13 473 8 c 0,141,142
+ 469 4 469 4 463 3 c 0,143,144
+ 462 3 462 3 459 3 c 128,-1,145
+ 456 3 456 3 456 3 c 2,146,-1
+ 442 2 l 1,147,-1
+ 179 2 l 2,148,149
+ 158 2 158 2 141 14 c 0,150,151
+ 133 19 133 19 129 23 c 0,152,153
+ 122 30 122 30 120 33 c 128,-1,154
+ 118 36 118 36 120 42 c 0,130,131
+89 376 m 0,155,156
+ 91 378 91 378 97 380 c 128,-1,157
+ 103 382 103 382 111 383 c 0,158,159
+ 120 383 120 383 128 379 c 0,160,161
+ 135 375 135 375 161.5 359.5 c 128,-1,162
+ 188 344 188 344 197 339 c 0,163,164
+ 205 335 205 335 205 326 c 2,165,-1
+ 205 151 l 2,166,167
+ 205 138 205 138 196 130 c 0,168,169
+ 186 120 186 120 155 89.5 c 128,-1,170
+ 124 59 124 59 120 55 c 0,171,172
+ 116 50 116 50 109 50 c 0,173,174
+ 99 50 99 50 95 58 c 256,175,176
+ 90 66 90 66 90 67 c 0,177,178
+ 76 92 76 92 76 120 c 2,179,-1
+ 76 354 l 2,180,181
+ 76 365 76 365 84 371 c 0,182,183
+ 86 374 86 374 89 376 c 0,155,156
EndSplineSet
Validated: 1
EndChar
StartChar: one
Encoding: 49 49 8
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 2,2,3
- 666 307 666 307 660 306.5 c 128,-1,4
- 654 306 654 306 650 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 593 329 593 329 548 382 c 0,9,10
- 542 390 542 390 542 401 c 0,11,12
- 542 430 542 430 542 453 c 0,13,14
- 542 481 542 481 542 502.5 c 128,-1,15
- 542 524 542 524 542 551.5 c 128,-1,16
- 542 579 542 579 542 612 c 0,17,18
- 542 625 542 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 609 771 609 771 624 771 c 0,23,24
- 632 771 632 771 638 767 c 0,25,26
- 656 753 656 753 669 735 c 0,27,28
- 683 716 683 716 693 694 c 0,29,30
- 704 669 704 669 704 641 c 2,31,-1
- 704 346 l 2,32,33
- 704 339 704 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-695 278 m 0,36,37
- 700 273 700 273 702 265 c 0,38,39
- 704 258 704 258 704 251 c 2,40,-1
- 704 -45 l 2,41,42
- 704 -72 704 -72 693 -97 c 0,43,44
- 683 -119 683 -119 669 -138 c 0,45,46
- 656 -156 656 -156 638 -170 c 0,47,48
- 632 -175 632 -175 624 -175 c 0,49,50
- 609 -175 609 -175 602 -161 c 0,51,52
- 601 -157 601 -157 578 -107.5 c 128,-1,53
- 555 -58 555 -58 547 -40 c 0,54,55
- 542 -28 542 -28 542 -15 c 0,56,57
- 542 18 542 18 542 45.5 c 128,-1,58
- 542 73 542 73 542 94.5 c 128,-1,59
- 542 116 542 116 542 144 c 0,60,61
- 542 167 542 167 542 196 c 0,62,63
- 542 206 542 206 548 214 c 0,64,65
- 593 268 593 268 611 280 c 0,66,67
- 627 291 627 291 650 291 c 0,68,69
- 654 291 654 291 660 290.5 c 128,-1,70
- 666 290 666 290 666 290 c 2,71,72
- 685 289 685 289 695 278 c 0,36,37
+554 411 m 0,0,1
+ 546 402 546 402 531 402 c 0,2,3
+ 530 402 530 402 525 401.5 c 128,-1,4
+ 520 401 520 401 517 401 c 0,5,6
+ 499 401 499 401 487 410 c 0,7,8
+ 472 420 472 420 436 462 c 0,9,10
+ 430 468 430 468 431 477 c 0,11,12
+ 431 500 431 500 431 519 c 0,13,14
+ 431 541 431 541 431 558 c 128,-1,15
+ 431 575 431 575 431 597 c 128,-1,16
+ 431 619 431 619 431 646 c 0,17,18
+ 431 656 431 656 436 666 c 0,19,20
+ 462 724 462 724 480 763 c 0,21,22
+ 485 773 485 773 496 773 c 0,23,24
+ 502 773 502 773 508 770 c 0,25,26
+ 520 761 520 761 532 744 c 0,27,28
+ 546 726 546 726 552 711 c 0,29,30
+ 560 693 560 693 560 673 c 0,31,32
+ 560 671 560 671 560 669 c 2,33,-1
+ 560 433 l 2,34,35
+ 560 427 560 427 560 422 c 0,36,37
+ 558 415 558 415 554 411 c 0,0,1
+554 379 m 0,38,39
+ 558 375 558 375 560 368 c 0,40,41
+ 561 362 561 362 560 357 c 2,42,-1
+ 560 120 l 2,43,44
+ 560 98 560 98 552 79 c 0,45,46
+ 544 61 544 61 532 46 c 0,47,48
+ 522 32 522 32 508 20 c 0,49,50
+ 502 16 502 16 496 16 c 0,51,52
+ 484 16 484 16 480 27 c 0,53,54
+ 478 30 478 30 460 70 c 128,-1,55
+ 442 110 442 110 436 124 c 0,56,57
+ 431 134 431 134 431 144 c 0,58,59
+ 431 170 431 170 431 192.5 c 128,-1,60
+ 431 215 431 215 431 232 c 128,-1,61
+ 431 249 431 249 431 271 c 0,62,63
+ 431 289 431 289 431 313 c 0,64,65
+ 431 321 431 321 436 327 c 0,66,67
+ 471 370 471 370 487 380 c 0,68,69
+ 500 389 500 389 517 389 c 0,70,71
+ 520 389 520 389 525 388.5 c 128,-1,72
+ 530 388 530 388 531 388 c 0,73,74
+ 546 388 546 388 554 379 c 0,38,39
EndSplineSet
Validated: 1
EndChar
StartChar: two
Encoding: 50 50 9
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-267 366 m 0,36,37
- 285 377 285 377 307 377 c 2,38,-1
- 527 377 l 2,39,40
- 534 377 534 377 540 372 c 0,41,42
- 555 355 555 355 587 321 c 0,43,44
- 596 311 596 311 596 298 c 0,45,46
- 596 284 596 284 586 274 c 0,47,48
- 561 248 561 248 542 230 c 0,49,50
- 535 222 535 222 523 222 c 2,51,-1
- 304 222 l 2,52,53
- 285 222 285 222 269 231 c 0,54,55
- 264 234 264 234 193 275 c 0,56,57
- 180 282 180 282 180 298 c 0,58,59
- 180 313 180 313 193 321 c 0,60,61
- 200 325 200 325 227 341.5 c 128,-1,62
- 254 358 254 358 267 366 c 0,36,37
-153 743 m 0,63,64
- 151 751 151 751 153 754.5 c 128,-1,65
- 155 758 155 758 164 767 c 0,66,67
- 169 772 169 772 179 778 c 0,68,69
- 200 793 200 793 226 793 c 2,70,-1
- 555 793 l 1,71,-1
- 572 792 l 2,72,73
- 573 792 573 792 576 791.5 c 128,-1,74
- 579 791 579 791 581 791 c 0,75,76
- 589 790 589 790 594 785 c 0,77,78
- 601 779 601 779 598 771 c 0,79,80
- 593 761 593 761 542 647 c 0,81,82
- 536 633 536 633 521 633 c 2,83,-1
- 272 633 l 2,84,85
- 260 633 260 633 252 642 c 0,86,87
- 157 735 157 735 153 743 c 0,63,64
-153 -143 m 0,88,89
- 157 -135 157 -135 252 -42 c 0,90,91
- 260 -34 260 -34 272 -34 c 2,92,-1
- 521 -34 l 2,93,94
- 536 -34 536 -34 542 -47 c 0,95,96
- 593 -161 593 -161 598 -172 c 0,97,98
- 601 -179 601 -179 594 -185 c 0,99,100
- 589 -190 589 -190 581 -191 c 0,101,102
- 580 -191 580 -191 576.5 -191.5 c 128,-1,103
- 573 -192 573 -192 572 -192 c 2,104,-1
- 555 -193 l 1,105,-1
- 226 -193 l 2,106,107
- 200 -193 200 -193 179 -178 c 0,108,109
- 169 -172 169 -172 164 -167 c 0,110,111
- 155 -158 155 -158 153 -154.5 c 128,-1,112
- 151 -151 151 -151 153 -143 c 0,88,89
-114 275 m 0,113,114
- 117 277 117 277 124 280 c 0,115,116
- 132 283 132 283 141 283 c 0,117,118
- 152 283 152 283 162 278 c 0,119,120
- 171 273 171 273 204.5 254 c 128,-1,121
- 238 235 238 235 249 228 c 0,122,123
- 259 223 259 223 259 212 c 2,124,-1
- 259 -6 l 2,125,126
- 259 -22 259 -22 247 -33 c 0,127,128
- 234 -46 234 -46 196 -84 c 128,-1,129
- 158 -122 158 -122 152 -127 c 0,130,131
- 147 -133 147 -133 139 -133 c 0,132,133
- 127 -133 127 -133 121 -123 c 256,134,135
- 115 -113 115 -113 115 -112 c 0,136,137
- 97 -81 97 -81 97 -45 c 2,138,-1
- 97 247 l 2,139,140
- 97 261 97 261 107 269 c 0,141,142
- 110 272 110 272 114 275 c 0,113,114
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 411 m 0,26,27
+ 546 402 546 402 531 402 c 0,28,29
+ 530 402 530 402 525 401.5 c 128,-1,30
+ 520 401 520 401 517 401 c 0,31,32
+ 499 401 499 401 487 410 c 0,33,34
+ 472 420 472 420 436 462 c 0,35,36
+ 430 468 430 468 431 477 c 0,37,38
+ 431 500 431 500 431 519 c 0,39,40
+ 431 541 431 541 431 558 c 128,-1,41
+ 431 575 431 575 431 597 c 128,-1,42
+ 431 619 431 619 431 646 c 0,43,44
+ 431 656 431 656 436 666 c 0,45,46
+ 462 724 462 724 480 763 c 0,47,48
+ 485 773 485 773 496 773 c 0,49,50
+ 502 773 502 773 508 770 c 0,51,52
+ 520 761 520 761 532 744 c 0,53,54
+ 546 726 546 726 552 711 c 0,55,56
+ 560 693 560 693 560 673 c 0,57,58
+ 560 671 560 671 560 669 c 2,59,-1
+ 560 433 l 2,60,61
+ 560 427 560 427 560 422 c 0,62,63
+ 558 415 558 415 554 411 c 0,26,27
+120 751 m 0,64,65
+ 118 757 118 757 120 760 c 128,-1,66
+ 122 763 122 763 129 770 c 0,67,68
+ 133 774 133 774 141 779 c 0,69,70
+ 158 791 158 791 179 791 c 2,71,-1
+ 442 791 l 1,72,-1
+ 456 790 l 2,73,74
+ 457 790 457 790 459 789.5 c 128,-1,75
+ 461 789 461 789 463 789 c 0,76,77
+ 469 788 469 788 473 784 c 0,78,79
+ 478 779 478 779 476 773 c 0,80,81
+ 472 765 472 765 432 674 c 0,82,83
+ 427 663 427 663 415 663 c 2,84,-1
+ 216 663 l 2,85,86
+ 206 663 206 663 200 670 c 0,87,88
+ 123 745 123 745 120 751 c 0,64,65
+120 42 m 0,89,90
+ 123 48 123 48 200 123 c 0,91,92
+ 206 129 206 129 216 129 c 2,93,-1
+ 415 129 l 2,94,95
+ 427 129 427 129 432 119 c 0,96,97
+ 473 28 473 28 476 19 c 0,98,99
+ 478 13 478 13 473 8 c 0,100,101
+ 469 4 469 4 463 3 c 0,102,103
+ 462 3 462 3 459 3 c 128,-1,104
+ 456 3 456 3 456 3 c 2,105,-1
+ 442 2 l 1,106,-1
+ 179 2 l 2,107,108
+ 158 2 158 2 141 14 c 0,109,110
+ 133 19 133 19 129 23 c 0,111,112
+ 122 30 122 30 120 33 c 128,-1,113
+ 118 36 118 36 120 42 c 0,89,90
+89 376 m 0,114,115
+ 91 378 91 378 97 380 c 128,-1,116
+ 103 382 103 382 111 383 c 0,117,118
+ 120 383 120 383 128 379 c 0,119,120
+ 135 375 135 375 161.5 359.5 c 128,-1,121
+ 188 344 188 344 197 339 c 0,122,123
+ 205 335 205 335 205 326 c 2,124,-1
+ 205 151 l 2,125,126
+ 205 138 205 138 196 130 c 0,127,128
+ 186 120 186 120 155 89.5 c 128,-1,129
+ 124 59 124 59 120 55 c 0,130,131
+ 116 50 116 50 109 50 c 0,132,133
+ 99 50 99 50 95 58 c 256,134,135
+ 90 66 90 66 90 67 c 0,136,137
+ 76 92 76 92 76 120 c 2,138,-1
+ 76 354 l 2,139,140
+ 76 365 76 365 84 371 c 0,141,142
+ 86 374 86 374 89 376 c 0,114,115
EndSplineSet
Validated: 1
EndChar
StartChar: three
Encoding: 51 51 10
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-267 366 m 0,36,37
- 285 377 285 377 307 377 c 2,38,-1
- 527 377 l 2,39,40
- 535 377 535 377 540 372 c 0,41,42
- 555 355 555 355 587 321 c 0,43,44
- 596 311 596 311 596 298 c 0,45,46
- 596 284 596 284 586 274 c 0,47,48
- 561 248 561 248 542 230 c 0,49,50
- 535 222 535 222 523 222 c 2,51,-1
- 304 222 l 2,52,53
- 285 222 285 222 269 231 c 0,54,55
- 264 234 264 234 193 275 c 0,56,57
- 180 282 180 282 180 298 c 0,58,59
- 180 313 180 313 193 321 c 0,60,61
- 200 325 200 325 227 341.5 c 128,-1,62
- 254 358 254 358 267 366 c 0,36,37
-153 743 m 0,63,64
- 151 751 151 751 153 754.5 c 128,-1,65
- 155 758 155 758 164 767 c 0,66,67
- 169 772 169 772 179 778 c 0,68,69
- 200 793 200 793 226 793 c 2,70,-1
- 555 793 l 1,71,-1
- 572 792 l 2,72,73
- 573 792 573 792 576 791.5 c 128,-1,74
- 579 791 579 791 581 791 c 0,75,76
- 589 790 589 790 594 785 c 0,77,78
- 601 779 601 779 598 771 c 0,79,80
- 593 761 593 761 542 647 c 0,81,82
- 536 633 536 633 521 633 c 2,83,-1
- 272 633 l 2,84,85
- 260 633 260 633 252 642 c 0,86,87
- 157 735 157 735 153 743 c 0,63,64
-695 278 m 0,88,89
- 700 273 700 273 702 265 c 0,90,91
- 703 258 703 258 703 251 c 2,92,-1
- 703 -45 l 2,93,94
- 703 -72 703 -72 692 -97 c 0,95,96
- 682 -119 682 -119 668 -138 c 0,97,98
- 655 -156 655 -156 638 -170 c 0,99,100
- 631 -175 631 -175 623 -175 c 0,101,102
- 608 -175 608 -175 602 -161 c 0,103,104
- 600 -157 600 -157 577.5 -107.5 c 128,-1,105
- 555 -58 555 -58 547 -40 c 0,106,107
- 541 -28 541 -28 541 -15 c 0,108,109
- 541 18 541 18 541 45.5 c 128,-1,110
- 541 73 541 73 541 94.5 c 128,-1,111
- 541 116 541 116 541 144 c 0,112,113
- 541 167 541 167 541 196 c 0,114,115
- 541 206 541 206 548 214 c 0,116,117
- 592 268 592 268 611 280 c 0,118,119
- 627 291 627 291 649 291 c 0,120,121
- 653 291 653 291 659 290.5 c 128,-1,122
- 665 290 665 290 666 290 c 0,123,124
- 685 289 685 289 695 278 c 0,88,89
-153 -143 m 0,125,126
- 157 -135 157 -135 252 -42 c 0,127,128
- 260 -34 260 -34 272 -34 c 2,129,-1
- 521 -34 l 2,130,131
- 536 -34 536 -34 542 -47 c 0,132,133
- 593 -161 593 -161 598 -172 c 0,134,135
- 601 -179 601 -179 594 -185 c 0,136,137
- 589 -190 589 -190 581 -191 c 0,138,139
- 580 -191 580 -191 576.5 -191.5 c 128,-1,140
- 573 -192 573 -192 572 -192 c 2,141,-1
- 555 -193 l 1,142,-1
- 226 -193 l 2,143,144
- 200 -193 200 -193 179 -178 c 0,145,146
- 169 -172 169 -172 164 -167 c 0,147,148
- 155 -158 155 -158 153 -154.5 c 128,-1,149
- 151 -151 151 -151 153 -143 c 0,125,126
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 411 m 0,26,27
+ 546 402 546 402 531 402 c 0,28,29
+ 530 402 530 402 525 401.5 c 128,-1,30
+ 520 401 520 401 517 401 c 0,31,32
+ 499 401 499 401 487 410 c 0,33,34
+ 472 420 472 420 436 462 c 0,35,36
+ 430 468 430 468 431 477 c 0,37,38
+ 431 500 431 500 431 519 c 0,39,40
+ 431 541 431 541 431 558 c 128,-1,41
+ 431 575 431 575 431 597 c 128,-1,42
+ 431 619 431 619 431 646 c 0,43,44
+ 431 656 431 656 436 666 c 0,45,46
+ 462 724 462 724 480 763 c 0,47,48
+ 485 773 485 773 496 773 c 0,49,50
+ 502 773 502 773 508 770 c 0,51,52
+ 520 761 520 761 532 744 c 0,53,54
+ 546 726 546 726 552 711 c 0,55,56
+ 560 693 560 693 560 673 c 0,57,58
+ 560 671 560 671 560 669 c 2,59,-1
+ 560 433 l 2,60,61
+ 560 427 560 427 560 422 c 0,62,63
+ 558 415 558 415 554 411 c 0,26,27
+120 751 m 0,64,65
+ 118 757 118 757 120 760 c 128,-1,66
+ 122 763 122 763 129 770 c 0,67,68
+ 133 774 133 774 141 779 c 0,69,70
+ 158 791 158 791 179 791 c 2,71,-1
+ 442 791 l 1,72,-1
+ 456 790 l 2,73,74
+ 457 790 457 790 459 789.5 c 128,-1,75
+ 461 789 461 789 463 789 c 0,76,77
+ 469 788 469 788 473 784 c 0,78,79
+ 478 779 478 779 476 773 c 0,80,81
+ 472 765 472 765 432 674 c 0,82,83
+ 427 663 427 663 415 663 c 2,84,-1
+ 216 663 l 2,85,86
+ 206 663 206 663 200 670 c 0,87,88
+ 123 745 123 745 120 751 c 0,64,65
+554 379 m 0,89,90
+ 558 375 558 375 560 368 c 0,91,92
+ 561 362 561 362 560 357 c 2,93,-1
+ 560 120 l 2,94,95
+ 560 98 560 98 552 79 c 0,96,97
+ 544 61 544 61 532 46 c 0,98,99
+ 522 32 522 32 508 20 c 0,100,101
+ 502 16 502 16 496 16 c 0,102,103
+ 484 16 484 16 480 27 c 0,104,105
+ 478 30 478 30 460 70 c 128,-1,106
+ 442 110 442 110 436 124 c 0,107,108
+ 431 134 431 134 431 144 c 0,109,110
+ 431 170 431 170 431 192.5 c 128,-1,111
+ 431 215 431 215 431 232 c 128,-1,112
+ 431 249 431 249 431 271 c 0,113,114
+ 431 289 431 289 431 313 c 0,115,116
+ 431 321 431 321 436 327 c 0,117,118
+ 471 370 471 370 487 380 c 0,119,120
+ 500 389 500 389 517 389 c 0,121,122
+ 520 389 520 389 525 388.5 c 128,-1,123
+ 530 388 530 388 531 388 c 0,124,125
+ 546 388 546 388 554 379 c 0,89,90
+120 42 m 0,126,127
+ 123 48 123 48 200 123 c 0,128,129
+ 206 129 206 129 216 129 c 2,130,-1
+ 415 129 l 2,131,132
+ 427 129 427 129 432 119 c 0,133,134
+ 473 28 473 28 476 19 c 0,135,136
+ 478 13 478 13 473 8 c 0,137,138
+ 469 4 469 4 463 3 c 0,139,140
+ 462 3 462 3 459 3 c 128,-1,141
+ 456 3 456 3 456 3 c 2,142,-1
+ 442 2 l 1,143,-1
+ 179 2 l 2,144,145
+ 158 2 158 2 141 14 c 0,146,147
+ 133 19 133 19 129 23 c 0,148,149
+ 122 30 122 30 120 33 c 128,-1,150
+ 118 36 118 36 120 42 c 0,126,127
EndSplineSet
Validated: 1
EndChar
StartChar: four
Encoding: 52 52 11
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-267 366 m 0,36,37
- 285 377 285 377 307 377 c 2,38,-1
- 527 377 l 2,39,40
- 534 377 534 377 540 372 c 0,41,42
- 555 355 555 355 587 321 c 0,43,44
- 596 311 596 311 596 298 c 0,45,46
- 596 284 596 284 586 274 c 0,47,48
- 561 248 561 248 542 230 c 0,49,50
- 535 222 535 222 523 222 c 2,51,-1
- 304 222 l 2,52,53
- 285 222 285 222 269 231 c 0,54,55
- 264 234 264 234 193 275 c 0,56,57
- 180 282 180 282 180 298 c 0,58,59
- 180 313 180 313 193 321 c 0,60,61
- 200 325 200 325 227 341.5 c 128,-1,62
- 254 358 254 358 267 366 c 0,36,37
-114 325 m 256,63,64
- 111 327 111 327 107 330 c 0,65,66
- 97 339 97 339 97 352 c 2,67,-1
- 97 645 l 2,68,69
- 97 681 97 681 115 711 c 0,70,71
- 115 712 115 712 121 723 c 0,72,73
- 127 733 127 733 139 733 c 0,74,75
- 147 733 147 733 152 727 c 0,76,77
- 158 722 158 722 196 684 c 128,-1,78
- 234 646 234 646 247 633 c 0,79,80
- 259 621 259 621 259 605 c 2,81,-1
- 259 388 l 2,82,83
- 259 377 259 377 249 372 c 0,84,85
- 238 365 238 365 204.5 346 c 128,-1,86
- 171 327 171 327 162 322 c 0,87,88
- 152 317 152 317 141 317 c 0,89,90
- 132 317 132 317 124 320 c 0,91,92
- 117 323 117 323 114 325 c 256,63,64
-695 278 m 0,93,94
- 700 273 700 273 702 265 c 0,95,96
- 703 258 703 258 703 251 c 2,97,-1
- 703 -45 l 2,98,99
- 703 -72 703 -72 692 -97 c 0,100,101
- 682 -119 682 -119 668 -138 c 0,102,103
- 655 -156 655 -156 638 -170 c 0,104,105
- 631 -175 631 -175 623 -175 c 0,106,107
- 608 -175 608 -175 602 -161 c 0,108,109
- 600 -157 600 -157 577.5 -107.5 c 128,-1,110
- 555 -58 555 -58 547 -40 c 0,111,112
- 541 -28 541 -28 541 -15 c 0,113,114
- 541 18 541 18 541 45.5 c 128,-1,115
- 541 73 541 73 541 94.5 c 128,-1,116
- 541 116 541 116 541 144 c 0,117,118
- 541 167 541 167 541 196 c 0,119,120
- 541 206 541 206 548 214 c 0,121,122
- 592 268 592 268 611 280 c 0,123,124
- 627 291 627 291 649 291 c 0,125,126
- 653 291 653 291 659 290.5 c 128,-1,127
- 665 290 665 290 666 290 c 0,128,129
- 685 289 685 289 695 278 c 0,93,94
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 411 m 0,26,27
+ 546 402 546 402 531 402 c 0,28,29
+ 530 402 530 402 525 401.5 c 128,-1,30
+ 520 401 520 401 517 401 c 0,31,32
+ 499 401 499 401 487 410 c 0,33,34
+ 472 420 472 420 436 462 c 0,35,36
+ 430 468 430 468 431 477 c 0,37,38
+ 431 500 431 500 431 519 c 0,39,40
+ 431 541 431 541 431 558 c 128,-1,41
+ 431 575 431 575 431 597 c 128,-1,42
+ 431 619 431 619 431 646 c 0,43,44
+ 431 656 431 656 436 666 c 0,45,46
+ 462 724 462 724 480 763 c 0,47,48
+ 485 773 485 773 496 773 c 0,49,50
+ 502 773 502 773 508 770 c 0,51,52
+ 520 761 520 761 532 744 c 0,53,54
+ 546 726 546 726 552 711 c 0,55,56
+ 560 693 560 693 560 673 c 0,57,58
+ 560 671 560 671 560 669 c 2,59,-1
+ 560 433 l 2,60,61
+ 560 427 560 427 560 422 c 0,62,63
+ 558 415 558 415 554 411 c 0,26,27
+89 416 m 0,64,65
+ 86 418 86 418 84 420 c 0,66,67
+ 76 427 76 427 76 438 c 2,68,-1
+ 76 672 l 2,69,70
+ 76 701 76 701 90 725 c 0,71,72
+ 90 726 90 726 95 735 c 0,73,74
+ 100 743 100 743 109 743 c 0,75,76
+ 115 743 115 743 120 738 c 0,77,78
+ 125 734 125 734 155 703.5 c 128,-1,79
+ 185 673 185 673 196 663 c 0,80,81
+ 206 653 206 653 205 640 c 2,82,-1
+ 205 467 l 2,83,84
+ 205 458 205 458 197 454 c 0,85,86
+ 188 448 188 448 161.5 433 c 128,-1,87
+ 135 418 135 418 128 414 c 0,88,89
+ 120 410 120 410 111 410 c 0,90,91
+ 104 410 104 410 97 412 c 0,92,93
+ 91 414 91 414 89 416 c 0,64,65
+554 379 m 0,94,95
+ 558 375 558 375 560 368 c 0,96,97
+ 561 362 561 362 560 357 c 2,98,-1
+ 560 120 l 2,99,100
+ 560 98 560 98 552 79 c 0,101,102
+ 544 61 544 61 532 46 c 0,103,104
+ 522 32 522 32 508 20 c 0,105,106
+ 502 16 502 16 496 16 c 0,107,108
+ 484 16 484 16 480 27 c 0,109,110
+ 478 30 478 30 460 70 c 128,-1,111
+ 442 110 442 110 436 124 c 0,112,113
+ 431 134 431 134 431 144 c 0,114,115
+ 431 170 431 170 431 192.5 c 128,-1,116
+ 431 215 431 215 431 232 c 128,-1,117
+ 431 249 431 249 431 271 c 0,118,119
+ 431 289 431 289 431 313 c 0,120,121
+ 431 321 431 321 436 327 c 0,122,123
+ 471 370 471 370 487 380 c 0,124,125
+ 500 389 500 389 517 389 c 0,126,127
+ 520 389 520 389 525 388.5 c 128,-1,128
+ 530 388 530 388 531 388 c 0,129,130
+ 546 388 546 388 554 379 c 0,94,95
EndSplineSet
Validated: 1
EndChar
StartChar: five
Encoding: 53 53 12
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-267 366 m 0,0,1
- 285 377 285 377 307 377 c 2,2,-1
- 527 377 l 2,3,4
- 535 377 535 377 540 372 c 0,5,6
- 555 355 555 355 587 321 c 0,7,8
- 596 311 596 311 596 298 c 0,9,10
- 596 284 596 284 586 274 c 0,11,12
- 561 248 561 248 542 230 c 0,13,14
- 535 222 535 222 523 222 c 2,15,-1
- 304 222 l 2,16,17
- 285 222 285 222 269 231 c 0,18,19
- 264 234 264 234 193 275 c 0,20,21
- 180 282 180 282 180 298 c 0,22,23
- 180 313 180 313 193 321 c 0,24,25
- 200 325 200 325 227 341.5 c 128,-1,26
- 254 358 254 358 267 366 c 0,0,1
-114 325 m 256,27,28
- 111 327 111 327 107 330 c 0,29,30
- 97 339 97 339 97 352 c 2,31,-1
- 97 645 l 2,32,33
- 97 681 97 681 115 711 c 0,34,35
- 115 712 115 712 121 723 c 0,36,37
- 127 733 127 733 139 733 c 0,38,39
- 147 733 147 733 152 727 c 0,40,41
- 158 722 158 722 196 684 c 128,-1,42
- 234 646 234 646 247 633 c 0,43,44
- 259 621 259 621 259 605 c 2,45,-1
- 259 388 l 2,46,47
- 259 377 259 377 249 372 c 0,48,49
- 238 365 238 365 204.5 346 c 128,-1,50
- 171 327 171 327 162 322 c 0,51,52
- 152 317 152 317 141 317 c 0,53,54
- 132 317 132 317 124 320 c 0,55,56
- 117 323 117 323 114 325 c 256,27,28
-153 743 m 0,57,58
- 151 751 151 751 153 754.5 c 128,-1,59
- 155 758 155 758 164 767 c 0,60,61
- 169 772 169 772 179 778 c 0,62,63
- 200 793 200 793 226 793 c 2,64,-1
- 555 793 l 1,65,-1
- 572 792 l 2,66,67
- 573 792 573 792 576 791.5 c 128,-1,68
- 579 791 579 791 581 791 c 0,69,70
- 589 790 589 790 594 785 c 0,71,72
- 601 779 601 779 598 771 c 0,73,74
- 593 761 593 761 542 647 c 0,75,76
- 536 633 536 633 521 633 c 2,77,-1
- 272 633 l 2,78,79
- 260 633 260 633 252 642 c 0,80,81
- 157 735 157 735 153 743 c 0,57,58
-695 278 m 0,82,83
- 700 273 700 273 702 265 c 0,84,85
- 703 258 703 258 703 251 c 2,86,-1
- 703 -45 l 2,87,88
- 703 -72 703 -72 692 -97 c 0,89,90
- 682 -119 682 -119 668 -138 c 0,91,92
- 655 -156 655 -156 638 -170 c 0,93,94
- 631 -175 631 -175 623 -175 c 0,95,96
- 608 -175 608 -175 602 -161 c 0,97,98
- 600 -157 600 -157 577.5 -107.5 c 128,-1,99
- 555 -58 555 -58 547 -40 c 0,100,101
- 541 -28 541 -28 541 -15 c 0,102,103
- 541 18 541 18 541 45.5 c 128,-1,104
- 541 73 541 73 541 94.5 c 128,-1,105
- 541 116 541 116 541 144 c 0,106,107
- 541 167 541 167 541 196 c 0,108,109
- 541 206 541 206 548 214 c 0,110,111
- 592 268 592 268 611 280 c 0,112,113
- 627 291 627 291 649 291 c 0,114,115
- 653 291 653 291 659 290.5 c 128,-1,116
- 665 290 665 290 666 290 c 0,117,118
- 685 289 685 289 695 278 c 0,82,83
-153 -143 m 0,119,120
- 157 -135 157 -135 252 -42 c 0,121,122
- 260 -34 260 -34 272 -34 c 2,123,-1
- 521 -34 l 2,124,125
- 536 -34 536 -34 542 -47 c 0,126,127
- 593 -161 593 -161 598 -172 c 0,128,129
- 601 -179 601 -179 594 -185 c 0,130,131
- 589 -190 589 -190 581 -191 c 0,132,133
- 580 -191 580 -191 576.5 -191.5 c 128,-1,134
- 573 -192 573 -192 572 -192 c 2,135,-1
- 555 -193 l 1,136,-1
- 226 -193 l 2,137,138
- 200 -193 200 -193 179 -178 c 0,139,140
- 169 -172 169 -172 164 -167 c 0,141,142
- 155 -158 155 -158 153 -154.5 c 128,-1,143
- 151 -151 151 -151 153 -143 c 0,119,120
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+89 416 m 0,26,27
+ 86 418 86 418 84 420 c 0,28,29
+ 76 427 76 427 76 438 c 2,30,-1
+ 76 672 l 2,31,32
+ 76 701 76 701 90 725 c 0,33,34
+ 90 726 90 726 95 735 c 0,35,36
+ 100 743 100 743 109 743 c 0,37,38
+ 115 743 115 743 120 738 c 0,39,40
+ 125 734 125 734 155 703.5 c 128,-1,41
+ 185 673 185 673 196 663 c 0,42,43
+ 206 653 206 653 205 640 c 2,44,-1
+ 205 467 l 2,45,46
+ 205 458 205 458 197 454 c 0,47,48
+ 188 448 188 448 161.5 433 c 128,-1,49
+ 135 418 135 418 128 414 c 0,50,51
+ 120 410 120 410 111 410 c 0,52,53
+ 104 410 104 410 97 412 c 0,54,55
+ 91 414 91 414 89 416 c 0,26,27
+120 751 m 0,56,57
+ 118 757 118 757 120 760 c 128,-1,58
+ 122 763 122 763 129 770 c 0,59,60
+ 133 774 133 774 141 779 c 0,61,62
+ 158 791 158 791 179 791 c 2,63,-1
+ 442 791 l 1,64,-1
+ 456 790 l 2,65,66
+ 457 790 457 790 459 789.5 c 128,-1,67
+ 461 789 461 789 463 789 c 0,68,69
+ 469 788 469 788 473 784 c 0,70,71
+ 478 779 478 779 476 773 c 0,72,73
+ 472 765 472 765 432 674 c 0,74,75
+ 427 663 427 663 415 663 c 2,76,-1
+ 216 663 l 2,77,78
+ 206 663 206 663 200 670 c 0,79,80
+ 123 745 123 745 120 751 c 0,56,57
+554 379 m 0,81,82
+ 558 375 558 375 560 368 c 0,83,84
+ 561 362 561 362 560 357 c 2,85,-1
+ 560 120 l 2,86,87
+ 560 98 560 98 552 79 c 0,88,89
+ 544 61 544 61 532 46 c 0,90,91
+ 522 32 522 32 508 20 c 0,92,93
+ 502 16 502 16 496 16 c 0,94,95
+ 484 16 484 16 480 27 c 0,96,97
+ 478 30 478 30 460 70 c 128,-1,98
+ 442 110 442 110 436 124 c 0,99,100
+ 431 134 431 134 431 144 c 0,101,102
+ 431 170 431 170 431 192.5 c 128,-1,103
+ 431 215 431 215 431 232 c 128,-1,104
+ 431 249 431 249 431 271 c 0,105,106
+ 431 289 431 289 431 313 c 0,107,108
+ 431 321 431 321 436 327 c 0,109,110
+ 471 370 471 370 487 380 c 0,111,112
+ 500 389 500 389 517 389 c 0,113,114
+ 520 389 520 389 525 388.5 c 128,-1,115
+ 530 388 530 388 531 388 c 0,116,117
+ 546 388 546 388 554 379 c 0,81,82
+120 42 m 0,118,119
+ 123 48 123 48 200 123 c 0,120,121
+ 206 129 206 129 216 129 c 2,122,-1
+ 415 129 l 2,123,124
+ 427 129 427 129 432 119 c 0,125,126
+ 473 28 473 28 476 19 c 0,127,128
+ 478 13 478 13 473 8 c 0,129,130
+ 469 4 469 4 463 3 c 0,131,132
+ 462 3 462 3 459 3 c 128,-1,133
+ 456 3 456 3 456 3 c 2,134,-1
+ 442 2 l 1,135,-1
+ 179 2 l 2,136,137
+ 158 2 158 2 141 14 c 0,138,139
+ 133 19 133 19 129 23 c 0,140,141
+ 122 30 122 30 120 33 c 128,-1,142
+ 118 36 118 36 120 42 c 0,118,119
EndSplineSet
Validated: 1
EndChar
StartChar: six
Encoding: 54 54 13
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-267 366 m 0,0,1
- 285 377 285 377 307 377 c 2,2,-1
- 527 377 l 2,3,4
- 535 377 535 377 540 372 c 0,5,6
- 555 355 555 355 587 321 c 0,7,8
- 596 311 596 311 596 298 c 0,9,10
- 596 284 596 284 586 274 c 0,11,12
- 561 248 561 248 542 230 c 0,13,14
- 535 222 535 222 523 222 c 2,15,-1
- 304 222 l 2,16,17
- 285 222 285 222 269 231 c 0,18,19
- 264 234 264 234 193 275 c 0,20,21
- 180 282 180 282 180 298 c 0,22,23
- 180 313 180 313 193 321 c 0,24,25
- 200 325 200 325 227 341.5 c 128,-1,26
- 254 358 254 358 267 366 c 0,0,1
-114 325 m 256,27,28
- 111 327 111 327 107 330 c 0,29,30
- 97 339 97 339 97 352 c 2,31,-1
- 97 645 l 2,32,33
- 97 681 97 681 115 711 c 0,34,35
- 115 712 115 712 121 723 c 0,36,37
- 127 733 127 733 139 733 c 0,38,39
- 147 733 147 733 152 727 c 0,40,41
- 158 722 158 722 196 684 c 128,-1,42
- 234 646 234 646 247 633 c 0,43,44
- 259 621 259 621 259 605 c 2,45,-1
- 259 388 l 2,46,47
- 259 377 259 377 249 372 c 0,48,49
- 238 365 238 365 204.5 346 c 128,-1,50
- 171 327 171 327 162 322 c 0,51,52
- 152 317 152 317 141 317 c 0,53,54
- 132 317 132 317 124 320 c 0,55,56
- 117 323 117 323 114 325 c 256,27,28
-153 743 m 0,57,58
- 151 751 151 751 153 754.5 c 128,-1,59
- 155 758 155 758 164 767 c 0,60,61
- 169 772 169 772 179 778 c 0,62,63
- 200 793 200 793 226 793 c 2,64,-1
- 555 793 l 1,65,-1
- 572 792 l 2,66,67
- 573 792 573 792 576 791.5 c 128,-1,68
- 579 791 579 791 581 791 c 0,69,70
- 589 790 589 790 594 785 c 0,71,72
- 601 779 601 779 598 771 c 0,73,74
- 593 761 593 761 542 647 c 0,75,76
- 536 633 536 633 521 633 c 2,77,-1
- 272 633 l 2,78,79
- 260 633 260 633 252 642 c 0,80,81
- 157 735 157 735 153 743 c 0,57,58
-695 278 m 0,82,83
- 700 273 700 273 702 265 c 0,84,85
- 703 258 703 258 703 251 c 2,86,-1
- 703 -45 l 2,87,88
- 703 -72 703 -72 692 -97 c 0,89,90
- 682 -119 682 -119 668 -138 c 0,91,92
- 655 -156 655 -156 638 -170 c 0,93,94
- 631 -175 631 -175 623 -175 c 0,95,96
- 608 -175 608 -175 602 -161 c 0,97,98
- 600 -157 600 -157 577.5 -107.5 c 128,-1,99
- 555 -58 555 -58 547 -40 c 0,100,101
- 541 -28 541 -28 541 -15 c 0,102,103
- 541 18 541 18 541 45.5 c 128,-1,104
- 541 73 541 73 541 94.5 c 128,-1,105
- 541 116 541 116 541 144 c 0,106,107
- 541 167 541 167 541 196 c 0,108,109
- 541 206 541 206 548 214 c 0,110,111
- 592 268 592 268 611 280 c 0,112,113
- 627 291 627 291 649 291 c 0,114,115
- 653 291 653 291 659 290.5 c 128,-1,116
- 665 290 665 290 666 290 c 0,117,118
- 685 289 685 289 695 278 c 0,82,83
-153 -143 m 0,119,120
- 157 -135 157 -135 252 -42 c 0,121,122
- 260 -34 260 -34 272 -34 c 2,123,-1
- 521 -34 l 2,124,125
- 536 -34 536 -34 542 -47 c 0,126,127
- 593 -161 593 -161 598 -172 c 0,128,129
- 601 -179 601 -179 594 -185 c 0,130,131
- 589 -190 589 -190 581 -191 c 0,132,133
- 580 -191 580 -191 576.5 -191.5 c 128,-1,134
- 573 -192 573 -192 572 -192 c 2,135,-1
- 555 -193 l 1,136,-1
- 226 -193 l 2,137,138
- 200 -193 200 -193 179 -178 c 0,139,140
- 169 -172 169 -172 164 -167 c 0,141,142
- 155 -158 155 -158 153 -154.5 c 128,-1,143
- 151 -151 151 -151 153 -143 c 0,119,120
-114 275 m 0,144,145
- 117 277 117 277 124 280 c 0,146,147
- 132 283 132 283 141 283 c 0,148,149
- 152 283 152 283 162 278 c 0,150,151
- 171 273 171 273 204.5 254 c 128,-1,152
- 238 235 238 235 249 228 c 0,153,154
- 259 223 259 223 259 212 c 2,155,-1
- 259 -6 l 2,156,157
- 259 -22 259 -22 247 -33 c 0,158,159
- 234 -46 234 -46 196 -84 c 128,-1,160
- 158 -122 158 -122 152 -127 c 0,161,162
- 147 -133 147 -133 139 -133 c 0,163,164
- 127 -133 127 -133 121 -123 c 256,165,166
- 115 -113 115 -113 115 -112 c 0,167,168
- 97 -81 97 -81 97 -45 c 2,169,-1
- 97 247 l 2,170,171
- 97 261 97 261 107 269 c 0,172,173
- 110 272 110 272 114 275 c 0,144,145
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+89 416 m 0,26,27
+ 86 418 86 418 84 420 c 0,28,29
+ 76 427 76 427 76 438 c 2,30,-1
+ 76 672 l 2,31,32
+ 76 701 76 701 90 725 c 0,33,34
+ 90 726 90 726 95 735 c 0,35,36
+ 100 743 100 743 109 743 c 0,37,38
+ 115 743 115 743 120 738 c 0,39,40
+ 125 734 125 734 155 703.5 c 128,-1,41
+ 185 673 185 673 196 663 c 0,42,43
+ 206 653 206 653 205 640 c 2,44,-1
+ 205 467 l 2,45,46
+ 205 458 205 458 197 454 c 0,47,48
+ 188 448 188 448 161.5 433 c 128,-1,49
+ 135 418 135 418 128 414 c 0,50,51
+ 120 410 120 410 111 410 c 0,52,53
+ 104 410 104 410 97 412 c 0,54,55
+ 91 414 91 414 89 416 c 0,26,27
+120 751 m 0,56,57
+ 118 757 118 757 120 760 c 128,-1,58
+ 122 763 122 763 129 770 c 0,59,60
+ 133 774 133 774 141 779 c 0,61,62
+ 158 791 158 791 179 791 c 2,63,-1
+ 442 791 l 1,64,-1
+ 456 790 l 2,65,66
+ 457 790 457 790 459 789.5 c 128,-1,67
+ 461 789 461 789 463 789 c 0,68,69
+ 469 788 469 788 473 784 c 0,70,71
+ 478 779 478 779 476 773 c 0,72,73
+ 472 765 472 765 432 674 c 0,74,75
+ 427 663 427 663 415 663 c 2,76,-1
+ 216 663 l 2,77,78
+ 206 663 206 663 200 670 c 0,79,80
+ 123 745 123 745 120 751 c 0,56,57
+554 379 m 0,81,82
+ 558 375 558 375 560 368 c 0,83,84
+ 561 362 561 362 560 357 c 2,85,-1
+ 560 120 l 2,86,87
+ 560 98 560 98 552 79 c 0,88,89
+ 544 61 544 61 532 46 c 0,90,91
+ 522 32 522 32 508 20 c 0,92,93
+ 502 16 502 16 496 16 c 0,94,95
+ 484 16 484 16 480 27 c 0,96,97
+ 478 30 478 30 460 70 c 128,-1,98
+ 442 110 442 110 436 124 c 0,99,100
+ 431 134 431 134 431 144 c 0,101,102
+ 431 170 431 170 431 192.5 c 128,-1,103
+ 431 215 431 215 431 232 c 128,-1,104
+ 431 249 431 249 431 271 c 0,105,106
+ 431 289 431 289 431 313 c 0,107,108
+ 431 321 431 321 436 327 c 0,109,110
+ 471 370 471 370 487 380 c 0,111,112
+ 500 389 500 389 517 389 c 0,113,114
+ 520 389 520 389 525 388.5 c 128,-1,115
+ 530 388 530 388 531 388 c 0,116,117
+ 546 388 546 388 554 379 c 0,81,82
+120 42 m 0,118,119
+ 123 48 123 48 200 123 c 0,120,121
+ 206 129 206 129 216 129 c 2,122,-1
+ 415 129 l 2,123,124
+ 427 129 427 129 432 119 c 0,125,126
+ 473 28 473 28 476 19 c 0,127,128
+ 478 13 478 13 473 8 c 0,129,130
+ 469 4 469 4 463 3 c 0,131,132
+ 462 3 462 3 459 3 c 128,-1,133
+ 456 3 456 3 456 3 c 2,134,-1
+ 442 2 l 1,135,-1
+ 179 2 l 2,136,137
+ 158 2 158 2 141 14 c 0,138,139
+ 133 19 133 19 129 23 c 0,140,141
+ 122 30 122 30 120 33 c 128,-1,142
+ 118 36 118 36 120 42 c 0,118,119
+89 376 m 0,143,144
+ 91 378 91 378 97 380 c 128,-1,145
+ 103 382 103 382 111 383 c 0,146,147
+ 120 383 120 383 128 379 c 0,148,149
+ 135 375 135 375 161.5 359.5 c 128,-1,150
+ 188 344 188 344 197 339 c 0,151,152
+ 205 335 205 335 205 326 c 2,153,-1
+ 205 151 l 2,154,155
+ 205 138 205 138 196 130 c 0,156,157
+ 186 120 186 120 155 89.5 c 128,-1,158
+ 124 59 124 59 120 55 c 0,159,160
+ 116 50 116 50 109 50 c 0,161,162
+ 99 50 99 50 95 58 c 256,163,164
+ 90 66 90 66 90 67 c 0,165,166
+ 76 92 76 92 76 120 c 2,167,-1
+ 76 354 l 2,168,169
+ 76 365 76 365 84 371 c 0,170,171
+ 86 374 86 374 89 376 c 0,143,144
EndSplineSet
Validated: 1
EndChar
StartChar: seven
Encoding: 55 55 14
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-153 743 m 0,36,37
- 151 751 151 751 153 754.5 c 128,-1,38
- 155 758 155 758 164 767 c 0,39,40
- 169 772 169 772 179 778 c 0,41,42
- 200 793 200 793 226 793 c 2,43,-1
- 555 793 l 1,44,-1
- 572 792 l 2,45,46
- 573 792 573 792 576 791.5 c 128,-1,47
- 579 791 579 791 581 791 c 0,48,49
- 589 790 589 790 594 785 c 0,50,51
- 601 779 601 779 598 771 c 0,52,53
- 593 761 593 761 542 647 c 0,54,55
- 536 633 536 633 521 633 c 2,56,-1
- 272 633 l 2,57,58
- 260 633 260 633 252 642 c 0,59,60
- 157 735 157 735 153 743 c 0,36,37
-695 278 m 0,61,62
- 700 273 700 273 702 265 c 0,63,64
- 703 258 703 258 703 251 c 2,65,-1
- 703 -45 l 2,66,67
- 703 -72 703 -72 692 -97 c 0,68,69
- 682 -119 682 -119 668 -138 c 0,70,71
- 655 -156 655 -156 638 -170 c 0,72,73
- 631 -175 631 -175 623 -175 c 0,74,75
- 608 -175 608 -175 602 -161 c 0,76,77
- 600 -157 600 -157 577.5 -107.5 c 128,-1,78
- 555 -58 555 -58 547 -40 c 0,79,80
- 541 -28 541 -28 541 -15 c 0,81,82
- 541 18 541 18 541 45.5 c 128,-1,83
- 541 73 541 73 541 94.5 c 128,-1,84
- 541 116 541 116 541 144 c 0,85,86
- 541 167 541 167 541 196 c 0,87,88
- 541 206 541 206 548 214 c 0,89,90
- 592 268 592 268 611 280 c 0,91,92
- 627 291 627 291 649 291 c 0,93,94
- 653 291 653 291 659 290.5 c 128,-1,95
- 665 290 665 290 666 290 c 0,96,97
- 685 289 685 289 695 278 c 0,61,62
+554 411 m 0,0,1
+ 546 402 546 402 531 402 c 0,2,3
+ 530 402 530 402 525 401.5 c 128,-1,4
+ 520 401 520 401 517 401 c 0,5,6
+ 499 401 499 401 487 410 c 0,7,8
+ 472 420 472 420 436 462 c 0,9,10
+ 430 468 430 468 431 477 c 0,11,12
+ 431 500 431 500 431 519 c 0,13,14
+ 431 541 431 541 431 558 c 128,-1,15
+ 431 575 431 575 431 597 c 128,-1,16
+ 431 619 431 619 431 646 c 0,17,18
+ 431 656 431 656 436 666 c 0,19,20
+ 462 724 462 724 480 763 c 0,21,22
+ 485 773 485 773 496 773 c 0,23,24
+ 502 773 502 773 508 770 c 0,25,26
+ 520 761 520 761 532 744 c 0,27,28
+ 546 726 546 726 552 711 c 0,29,30
+ 560 693 560 693 560 673 c 0,31,32
+ 560 671 560 671 560 669 c 2,33,-1
+ 560 433 l 2,34,35
+ 560 427 560 427 560 422 c 0,36,37
+ 558 415 558 415 554 411 c 0,0,1
+120 751 m 0,38,39
+ 118 757 118 757 120 760 c 128,-1,40
+ 122 763 122 763 129 770 c 0,41,42
+ 133 774 133 774 141 779 c 0,43,44
+ 158 791 158 791 179 791 c 2,45,-1
+ 442 791 l 1,46,-1
+ 456 790 l 2,47,48
+ 457 790 457 790 459 789.5 c 128,-1,49
+ 461 789 461 789 463 789 c 0,50,51
+ 469 788 469 788 473 784 c 0,52,53
+ 478 779 478 779 476 773 c 0,54,55
+ 472 765 472 765 432 674 c 0,56,57
+ 427 663 427 663 415 663 c 2,58,-1
+ 216 663 l 2,59,60
+ 206 663 206 663 200 670 c 0,61,62
+ 123 745 123 745 120 751 c 0,38,39
+554 379 m 0,63,64
+ 558 375 558 375 560 368 c 0,65,66
+ 561 362 561 362 560 357 c 2,67,-1
+ 560 120 l 2,68,69
+ 560 98 560 98 552 79 c 0,70,71
+ 544 61 544 61 532 46 c 0,72,73
+ 522 32 522 32 508 20 c 0,74,75
+ 502 16 502 16 496 16 c 0,76,77
+ 484 16 484 16 480 27 c 0,78,79
+ 478 30 478 30 460 70 c 128,-1,80
+ 442 110 442 110 436 124 c 0,81,82
+ 431 134 431 134 431 144 c 0,83,84
+ 431 170 431 170 431 192.5 c 128,-1,85
+ 431 215 431 215 431 232 c 128,-1,86
+ 431 249 431 249 431 271 c 0,87,88
+ 431 289 431 289 431 313 c 0,89,90
+ 431 321 431 321 436 327 c 0,91,92
+ 471 370 471 370 487 380 c 0,93,94
+ 500 389 500 389 517 389 c 0,95,96
+ 520 389 520 389 525 388.5 c 128,-1,97
+ 530 388 530 388 531 388 c 0,98,99
+ 546 388 546 388 554 379 c 0,63,64
EndSplineSet
Validated: 1
EndChar
StartChar: eight
Encoding: 56 56 15
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-267 366 m 0,36,37
- 285 377 285 377 307 377 c 2,38,-1
- 527 377 l 2,39,40
- 534 377 534 377 540 372 c 0,41,42
- 555 355 555 355 587 321 c 0,43,44
- 596 311 596 311 596 298 c 0,45,46
- 596 284 596 284 586 274 c 0,47,48
- 561 248 561 248 542 230 c 0,49,50
- 535 222 535 222 523 222 c 2,51,-1
- 304 222 l 2,52,53
- 285 222 285 222 269 231 c 0,54,55
- 264 234 264 234 193 275 c 0,56,57
- 180 282 180 282 180 298 c 0,58,59
- 180 313 180 313 193 321 c 0,60,61
- 200 325 200 325 227 341.5 c 128,-1,62
- 254 358 254 358 267 366 c 0,36,37
-114 325 m 256,63,64
- 111 327 111 327 107 330 c 0,65,66
- 97 339 97 339 97 352 c 2,67,-1
- 97 645 l 2,68,69
- 97 681 97 681 115 711 c 0,70,71
- 115 712 115 712 121 723 c 0,72,73
- 127 733 127 733 139 733 c 0,74,75
- 147 733 147 733 152 727 c 0,76,77
- 158 722 158 722 196 684 c 128,-1,78
- 234 646 234 646 247 633 c 0,79,80
- 259 621 259 621 259 605 c 2,81,-1
- 259 388 l 2,82,83
- 259 377 259 377 249 372 c 0,84,85
- 238 365 238 365 204.5 346 c 128,-1,86
- 171 327 171 327 162 322 c 0,87,88
- 152 317 152 317 141 317 c 0,89,90
- 132 317 132 317 124 320 c 0,91,92
- 117 323 117 323 114 325 c 256,63,64
-153 743 m 0,93,94
- 151 751 151 751 153 754.5 c 128,-1,95
- 155 758 155 758 164 767 c 0,96,97
- 169 772 169 772 179 778 c 0,98,99
- 200 793 200 793 226 793 c 2,100,-1
- 555 793 l 1,101,-1
- 572 792 l 2,102,103
- 573 792 573 792 576 791.5 c 128,-1,104
- 579 791 579 791 581 791 c 0,105,106
- 589 790 589 790 594 785 c 0,107,108
- 601 779 601 779 598 771 c 0,109,110
- 593 761 593 761 542 647 c 0,111,112
- 536 633 536 633 521 633 c 2,113,-1
- 272 633 l 2,114,115
- 260 633 260 633 252 642 c 0,116,117
- 157 735 157 735 153 743 c 0,93,94
-695 278 m 0,118,119
- 700 273 700 273 702 265 c 0,120,121
- 703 258 703 258 703 251 c 2,122,-1
- 703 -45 l 2,123,124
- 703 -72 703 -72 692 -97 c 0,125,126
- 682 -119 682 -119 668 -138 c 0,127,128
- 655 -156 655 -156 638 -170 c 0,129,130
- 631 -175 631 -175 623 -175 c 0,131,132
- 608 -175 608 -175 602 -161 c 0,133,134
- 600 -157 600 -157 577.5 -107.5 c 128,-1,135
- 555 -58 555 -58 547 -40 c 0,136,137
- 541 -28 541 -28 541 -15 c 0,138,139
- 541 18 541 18 541 45.5 c 128,-1,140
- 541 73 541 73 541 94.5 c 128,-1,141
- 541 116 541 116 541 144 c 0,142,143
- 541 167 541 167 541 196 c 0,144,145
- 541 206 541 206 548 214 c 0,146,147
- 592 268 592 268 611 280 c 0,148,149
- 627 291 627 291 649 291 c 0,150,151
- 653 291 653 291 659 290.5 c 128,-1,152
- 665 290 665 290 666 290 c 0,153,154
- 685 289 685 289 695 278 c 0,118,119
-153 -143 m 0,155,156
- 157 -135 157 -135 252 -42 c 0,157,158
- 260 -34 260 -34 272 -34 c 2,159,-1
- 521 -34 l 2,160,161
- 536 -34 536 -34 542 -47 c 0,162,163
- 593 -161 593 -161 598 -172 c 0,164,165
- 601 -179 601 -179 594 -185 c 0,166,167
- 589 -190 589 -190 581 -191 c 0,168,169
- 580 -191 580 -191 576.5 -191.5 c 128,-1,170
- 573 -192 573 -192 572 -192 c 2,171,-1
- 555 -193 l 1,172,-1
- 226 -193 l 2,173,174
- 200 -193 200 -193 179 -178 c 0,175,176
- 169 -172 169 -172 164 -167 c 0,177,178
- 155 -158 155 -158 153 -154.5 c 128,-1,179
- 151 -151 151 -151 153 -143 c 0,155,156
-114 275 m 0,180,181
- 117 277 117 277 124 280 c 0,182,183
- 132 283 132 283 141 283 c 0,184,185
- 152 283 152 283 162 278 c 0,186,187
- 171 273 171 273 204.5 254 c 128,-1,188
- 238 235 238 235 249 228 c 0,189,190
- 259 223 259 223 259 212 c 2,191,-1
- 259 -6 l 2,192,193
- 259 -22 259 -22 247 -33 c 0,194,195
- 234 -46 234 -46 196 -84 c 128,-1,196
- 158 -122 158 -122 152 -127 c 0,197,198
- 147 -133 147 -133 139 -133 c 0,199,200
- 127 -133 127 -133 121 -123 c 256,201,202
- 115 -113 115 -113 115 -112 c 0,203,204
- 97 -81 97 -81 97 -45 c 2,205,-1
- 97 247 l 2,206,207
- 97 261 97 261 107 269 c 0,208,209
- 110 272 110 272 114 275 c 0,180,181
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 411 m 0,26,27
+ 546 402 546 402 531 402 c 0,28,29
+ 530 402 530 402 525 401.5 c 128,-1,30
+ 520 401 520 401 517 401 c 0,31,32
+ 499 401 499 401 487 410 c 0,33,34
+ 472 420 472 420 436 462 c 0,35,36
+ 430 468 430 468 431 477 c 0,37,38
+ 431 500 431 500 431 519 c 0,39,40
+ 431 541 431 541 431 558 c 128,-1,41
+ 431 575 431 575 431 597 c 128,-1,42
+ 431 619 431 619 431 646 c 0,43,44
+ 431 656 431 656 436 666 c 0,45,46
+ 462 724 462 724 480 763 c 0,47,48
+ 485 773 485 773 496 773 c 0,49,50
+ 502 773 502 773 508 770 c 0,51,52
+ 520 761 520 761 532 744 c 0,53,54
+ 546 726 546 726 552 711 c 0,55,56
+ 560 693 560 693 560 673 c 0,57,58
+ 560 671 560 671 560 669 c 2,59,-1
+ 560 433 l 2,60,61
+ 560 427 560 427 560 422 c 0,62,63
+ 558 415 558 415 554 411 c 0,26,27
+89 416 m 0,64,65
+ 86 418 86 418 84 420 c 0,66,67
+ 76 427 76 427 76 438 c 2,68,-1
+ 76 672 l 2,69,70
+ 76 701 76 701 90 725 c 0,71,72
+ 90 726 90 726 95 735 c 0,73,74
+ 100 743 100 743 109 743 c 0,75,76
+ 115 743 115 743 120 738 c 0,77,78
+ 125 734 125 734 155 703.5 c 128,-1,79
+ 185 673 185 673 196 663 c 0,80,81
+ 206 653 206 653 205 640 c 2,82,-1
+ 205 467 l 2,83,84
+ 205 458 205 458 197 454 c 0,85,86
+ 188 448 188 448 161.5 433 c 128,-1,87
+ 135 418 135 418 128 414 c 0,88,89
+ 120 410 120 410 111 410 c 0,90,91
+ 104 410 104 410 97 412 c 0,92,93
+ 91 414 91 414 89 416 c 0,64,65
+120 751 m 0,94,95
+ 118 757 118 757 120 760 c 128,-1,96
+ 122 763 122 763 129 770 c 0,97,98
+ 133 774 133 774 141 779 c 0,99,100
+ 158 791 158 791 179 791 c 2,101,-1
+ 442 791 l 1,102,-1
+ 456 790 l 2,103,104
+ 457 790 457 790 459 789.5 c 128,-1,105
+ 461 789 461 789 463 789 c 0,106,107
+ 469 788 469 788 473 784 c 0,108,109
+ 478 779 478 779 476 773 c 0,110,111
+ 472 765 472 765 432 674 c 0,112,113
+ 427 663 427 663 415 663 c 2,114,-1
+ 216 663 l 2,115,116
+ 206 663 206 663 200 670 c 0,117,118
+ 123 745 123 745 120 751 c 0,94,95
+554 379 m 0,119,120
+ 558 375 558 375 560 368 c 0,121,122
+ 561 362 561 362 560 357 c 2,123,-1
+ 560 120 l 2,124,125
+ 560 98 560 98 552 79 c 0,126,127
+ 544 61 544 61 532 46 c 0,128,129
+ 522 32 522 32 508 20 c 0,130,131
+ 502 16 502 16 496 16 c 0,132,133
+ 484 16 484 16 480 27 c 0,134,135
+ 478 30 478 30 460 70 c 128,-1,136
+ 442 110 442 110 436 124 c 0,137,138
+ 431 134 431 134 431 144 c 0,139,140
+ 431 170 431 170 431 192.5 c 128,-1,141
+ 431 215 431 215 431 232 c 128,-1,142
+ 431 249 431 249 431 271 c 0,143,144
+ 431 289 431 289 431 313 c 0,145,146
+ 431 321 431 321 436 327 c 0,147,148
+ 471 370 471 370 487 380 c 0,149,150
+ 500 389 500 389 517 389 c 0,151,152
+ 520 389 520 389 525 388.5 c 128,-1,153
+ 530 388 530 388 531 388 c 0,154,155
+ 546 388 546 388 554 379 c 0,119,120
+120 42 m 0,156,157
+ 123 48 123 48 200 123 c 0,158,159
+ 206 129 206 129 216 129 c 2,160,-1
+ 415 129 l 2,161,162
+ 427 129 427 129 432 119 c 0,163,164
+ 473 28 473 28 476 19 c 0,165,166
+ 478 13 478 13 473 8 c 0,167,168
+ 469 4 469 4 463 3 c 0,169,170
+ 462 3 462 3 459 3 c 128,-1,171
+ 456 3 456 3 456 3 c 2,172,-1
+ 442 2 l 1,173,-1
+ 179 2 l 2,174,175
+ 158 2 158 2 141 14 c 0,176,177
+ 133 19 133 19 129 23 c 0,178,179
+ 122 30 122 30 120 33 c 128,-1,180
+ 118 36 118 36 120 42 c 0,156,157
+89 376 m 0,181,182
+ 91 378 91 378 97 380 c 128,-1,183
+ 103 382 103 382 111 383 c 0,184,185
+ 120 383 120 383 128 379 c 0,186,187
+ 135 375 135 375 161.5 359.5 c 128,-1,188
+ 188 344 188 344 197 339 c 0,189,190
+ 205 335 205 335 205 326 c 2,191,-1
+ 205 151 l 2,192,193
+ 205 138 205 138 196 130 c 0,194,195
+ 186 120 186 120 155 89.5 c 128,-1,196
+ 124 59 124 59 120 55 c 0,197,198
+ 116 50 116 50 109 50 c 0,199,200
+ 99 50 99 50 95 58 c 256,201,202
+ 90 66 90 66 90 67 c 0,203,204
+ 76 92 76 92 76 120 c 2,205,-1
+ 76 354 l 2,206,207
+ 76 365 76 365 84 371 c 0,208,209
+ 86 374 86 374 89 376 c 0,181,182
EndSplineSet
Validated: 1
EndChar
StartChar: nine
Encoding: 57 57 16
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-695 319 m 0,0,1
- 685 308 685 308 666 307 c 0,2,3
- 665 307 665 307 659 306.5 c 128,-1,4
- 653 306 653 306 649 306 c 0,5,6
- 627 306 627 306 611 317 c 0,7,8
- 592 329 592 329 548 382 c 0,9,10
- 541 390 541 390 541 401 c 0,11,12
- 541 430 541 430 541 453 c 0,13,14
- 541 481 541 481 541 502.5 c 128,-1,15
- 541 524 541 524 541 551.5 c 128,-1,16
- 541 579 541 579 541 612 c 0,17,18
- 541 625 541 625 547 637 c 0,19,20
- 580 710 580 710 602 758 c 0,21,22
- 608 771 608 771 623 771 c 0,23,24
- 631 771 631 771 638 767 c 0,25,26
- 655 753 655 753 668 735 c 0,27,28
- 682 716 682 716 692 694 c 0,29,30
- 703 669 703 669 703 641 c 2,31,-1
- 703 346 l 2,32,33
- 703 339 703 339 702 332 c 0,34,35
- 700 324 700 324 695 319 c 0,0,1
-267 366 m 0,36,37
- 285 377 285 377 307 377 c 2,38,-1
- 527 377 l 2,39,40
- 534 377 534 377 540 372 c 0,41,42
- 555 355 555 355 587 321 c 0,43,44
- 596 311 596 311 596 298 c 0,45,46
- 596 284 596 284 586 274 c 0,47,48
- 561 248 561 248 542 230 c 0,49,50
- 535 222 535 222 523 222 c 2,51,-1
- 304 222 l 2,52,53
- 285 222 285 222 269 231 c 0,54,55
- 264 234 264 234 193 275 c 0,56,57
- 180 282 180 282 180 298 c 0,58,59
- 180 313 180 313 193 321 c 0,60,61
- 200 325 200 325 227 341.5 c 128,-1,62
- 254 358 254 358 267 366 c 0,36,37
-114 325 m 256,63,64
- 111 327 111 327 107 330 c 0,65,66
- 97 339 97 339 97 352 c 2,67,-1
- 97 645 l 2,68,69
- 97 681 97 681 115 711 c 0,70,71
- 115 712 115 712 121 723 c 0,72,73
- 127 733 127 733 139 733 c 0,74,75
- 147 733 147 733 152 727 c 0,76,77
- 158 722 158 722 196 684 c 128,-1,78
- 234 646 234 646 247 633 c 0,79,80
- 259 621 259 621 259 605 c 2,81,-1
- 259 388 l 2,82,83
- 259 377 259 377 249 372 c 0,84,85
- 238 365 238 365 204.5 346 c 128,-1,86
- 171 327 171 327 162 322 c 0,87,88
- 152 317 152 317 141 317 c 0,89,90
- 132 317 132 317 124 320 c 0,91,92
- 117 323 117 323 114 325 c 256,63,64
-153 743 m 0,93,94
- 151 751 151 751 153 754.5 c 128,-1,95
- 155 758 155 758 164 767 c 0,96,97
- 169 772 169 772 179 778 c 0,98,99
- 200 793 200 793 226 793 c 2,100,-1
- 555 793 l 1,101,-1
- 572 792 l 2,102,103
- 573 792 573 792 576 791.5 c 128,-1,104
- 579 791 579 791 581 791 c 0,105,106
- 589 790 589 790 594 785 c 0,107,108
- 601 779 601 779 598 771 c 0,109,110
- 593 761 593 761 542 647 c 0,111,112
- 536 633 536 633 521 633 c 2,113,-1
- 272 633 l 2,114,115
- 260 633 260 633 252 642 c 0,116,117
- 157 735 157 735 153 743 c 0,93,94
-695 278 m 0,118,119
- 700 273 700 273 702 265 c 0,120,121
- 703 258 703 258 703 251 c 2,122,-1
- 703 -45 l 2,123,124
- 703 -72 703 -72 692 -97 c 0,125,126
- 682 -119 682 -119 668 -138 c 0,127,128
- 655 -156 655 -156 638 -170 c 0,129,130
- 631 -175 631 -175 623 -175 c 0,131,132
- 608 -175 608 -175 602 -161 c 0,133,134
- 600 -157 600 -157 577.5 -107.5 c 128,-1,135
- 555 -58 555 -58 547 -40 c 0,136,137
- 541 -28 541 -28 541 -15 c 0,138,139
- 541 18 541 18 541 45.5 c 128,-1,140
- 541 73 541 73 541 94.5 c 128,-1,141
- 541 116 541 116 541 144 c 0,142,143
- 541 167 541 167 541 196 c 0,144,145
- 541 206 541 206 548 214 c 0,146,147
- 592 268 592 268 611 280 c 0,148,149
- 627 291 627 291 649 291 c 0,150,151
- 653 291 653 291 659 290.5 c 128,-1,152
- 665 290 665 290 666 290 c 0,153,154
- 685 289 685 289 695 278 c 0,118,119
-153 -143 m 0,155,156
- 157 -135 157 -135 252 -42 c 0,157,158
- 260 -34 260 -34 272 -34 c 2,159,-1
- 521 -34 l 2,160,161
- 536 -34 536 -34 542 -47 c 0,162,163
- 593 -161 593 -161 598 -172 c 0,164,165
- 601 -179 601 -179 594 -185 c 0,166,167
- 589 -190 589 -190 581 -191 c 0,168,169
- 580 -191 580 -191 576.5 -191.5 c 128,-1,170
- 573 -192 573 -192 572 -192 c 2,171,-1
- 555 -193 l 1,172,-1
- 226 -193 l 2,173,174
- 200 -193 200 -193 179 -178 c 0,175,176
- 169 -172 169 -172 164 -167 c 0,177,178
- 155 -158 155 -158 153 -154.5 c 128,-1,179
- 151 -151 151 -151 153 -143 c 0,155,156
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 411 m 0,26,27
+ 546 402 546 402 531 402 c 0,28,29
+ 530 402 530 402 525 401.5 c 128,-1,30
+ 520 401 520 401 517 401 c 0,31,32
+ 499 401 499 401 487 410 c 0,33,34
+ 472 420 472 420 436 462 c 0,35,36
+ 430 468 430 468 431 477 c 0,37,38
+ 431 500 431 500 431 519 c 0,39,40
+ 431 541 431 541 431 558 c 128,-1,41
+ 431 575 431 575 431 597 c 128,-1,42
+ 431 619 431 619 431 646 c 0,43,44
+ 431 656 431 656 436 666 c 0,45,46
+ 462 724 462 724 480 763 c 0,47,48
+ 485 773 485 773 496 773 c 0,49,50
+ 502 773 502 773 508 770 c 0,51,52
+ 520 761 520 761 532 744 c 0,53,54
+ 546 726 546 726 552 711 c 0,55,56
+ 560 693 560 693 560 673 c 0,57,58
+ 560 671 560 671 560 669 c 2,59,-1
+ 560 433 l 2,60,61
+ 560 427 560 427 560 422 c 0,62,63
+ 558 415 558 415 554 411 c 0,26,27
+89 416 m 0,64,65
+ 86 418 86 418 84 420 c 0,66,67
+ 76 427 76 427 76 438 c 2,68,-1
+ 76 672 l 2,69,70
+ 76 701 76 701 90 725 c 0,71,72
+ 90 726 90 726 95 735 c 0,73,74
+ 100 743 100 743 109 743 c 0,75,76
+ 115 743 115 743 120 738 c 0,77,78
+ 125 734 125 734 155 703.5 c 128,-1,79
+ 185 673 185 673 196 663 c 0,80,81
+ 206 653 206 653 205 640 c 2,82,-1
+ 205 467 l 2,83,84
+ 205 458 205 458 197 454 c 0,85,86
+ 188 448 188 448 161.5 433 c 128,-1,87
+ 135 418 135 418 128 414 c 0,88,89
+ 120 410 120 410 111 410 c 0,90,91
+ 104 410 104 410 97 412 c 0,92,93
+ 91 414 91 414 89 416 c 0,64,65
+120 751 m 0,94,95
+ 118 757 118 757 120 760 c 128,-1,96
+ 122 763 122 763 129 770 c 0,97,98
+ 133 774 133 774 141 779 c 0,99,100
+ 158 791 158 791 179 791 c 2,101,-1
+ 442 791 l 1,102,-1
+ 456 790 l 2,103,104
+ 457 790 457 790 459 789.5 c 128,-1,105
+ 461 789 461 789 463 789 c 0,106,107
+ 469 788 469 788 473 784 c 0,108,109
+ 478 779 478 779 476 773 c 0,110,111
+ 472 765 472 765 432 674 c 0,112,113
+ 427 663 427 663 415 663 c 2,114,-1
+ 216 663 l 2,115,116
+ 206 663 206 663 200 670 c 0,117,118
+ 123 745 123 745 120 751 c 0,94,95
+554 379 m 0,119,120
+ 558 375 558 375 560 368 c 0,121,122
+ 561 362 561 362 560 357 c 2,123,-1
+ 560 120 l 2,124,125
+ 560 98 560 98 552 79 c 0,126,127
+ 544 61 544 61 532 46 c 0,128,129
+ 522 32 522 32 508 20 c 0,130,131
+ 502 16 502 16 496 16 c 0,132,133
+ 484 16 484 16 480 27 c 0,134,135
+ 478 30 478 30 460 70 c 128,-1,136
+ 442 110 442 110 436 124 c 0,137,138
+ 431 134 431 134 431 144 c 0,139,140
+ 431 170 431 170 431 192.5 c 128,-1,141
+ 431 215 431 215 431 232 c 128,-1,142
+ 431 249 431 249 431 271 c 0,143,144
+ 431 289 431 289 431 313 c 0,145,146
+ 431 321 431 321 436 327 c 0,147,148
+ 471 370 471 370 487 380 c 0,149,150
+ 500 389 500 389 517 389 c 0,151,152
+ 520 389 520 389 525 388.5 c 128,-1,153
+ 530 388 530 388 531 388 c 0,154,155
+ 546 388 546 388 554 379 c 0,119,120
+120 42 m 0,156,157
+ 123 48 123 48 200 123 c 0,158,159
+ 206 129 206 129 216 129 c 2,160,-1
+ 415 129 l 2,161,162
+ 427 129 427 129 432 119 c 0,163,164
+ 473 28 473 28 476 19 c 0,165,166
+ 478 13 478 13 473 8 c 0,167,168
+ 469 4 469 4 463 3 c 0,169,170
+ 462 3 462 3 459 3 c 128,-1,171
+ 456 3 456 3 456 3 c 2,172,-1
+ 442 2 l 1,173,-1
+ 179 2 l 2,174,175
+ 158 2 158 2 141 14 c 0,176,177
+ 133 19 133 19 129 23 c 0,178,179
+ 122 30 122 30 120 33 c 128,-1,180
+ 118 36 118 36 120 42 c 0,156,157
EndSplineSet
Validated: 1
EndChar
@@ -1715,100 +2390,100 @@ EndChar
StartChar: S
Encoding: 83 83 26
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-267 366 m 0,0,1
- 285 377 285 377 307 377 c 2,2,-1
- 527 377 l 2,3,4
- 535 377 535 377 540 372 c 0,5,6
- 555 355 555 355 587 321 c 0,7,8
- 596 311 596 311 596 298 c 0,9,10
- 596 284 596 284 586 274 c 0,11,12
- 561 248 561 248 542 230 c 0,13,14
- 535 222 535 222 523 222 c 2,15,-1
- 304 222 l 2,16,17
- 285 222 285 222 269 231 c 0,18,19
- 264 234 264 234 193 275 c 0,20,21
- 180 282 180 282 180 298 c 0,22,23
- 180 313 180 313 193 321 c 0,24,25
- 200 325 200 325 227 341.5 c 128,-1,26
- 254 358 254 358 267 366 c 0,0,1
-114 325 m 256,27,28
- 111 327 111 327 107 330 c 0,29,30
- 97 339 97 339 97 352 c 2,31,-1
- 97 645 l 2,32,33
- 97 681 97 681 115 711 c 0,34,35
- 115 712 115 712 121 723 c 0,36,37
- 127 733 127 733 139 733 c 0,38,39
- 147 733 147 733 152 727 c 0,40,41
- 158 722 158 722 196 684 c 128,-1,42
- 234 646 234 646 247 633 c 0,43,44
- 259 621 259 621 259 605 c 2,45,-1
- 259 388 l 2,46,47
- 259 377 259 377 249 372 c 0,48,49
- 238 365 238 365 204.5 346 c 128,-1,50
- 171 327 171 327 162 322 c 0,51,52
- 152 317 152 317 141 317 c 0,53,54
- 132 317 132 317 124 320 c 0,55,56
- 117 323 117 323 114 325 c 256,27,28
-153 743 m 0,57,58
- 151 751 151 751 153 754.5 c 128,-1,59
- 155 758 155 758 164 767 c 0,60,61
- 169 772 169 772 179 778 c 0,62,63
- 200 793 200 793 226 793 c 2,64,-1
- 555 793 l 1,65,-1
- 572 792 l 2,66,67
- 573 792 573 792 576 791.5 c 128,-1,68
- 579 791 579 791 581 791 c 0,69,70
- 589 790 589 790 594 785 c 0,71,72
- 601 779 601 779 598 771 c 0,73,74
- 593 761 593 761 542 647 c 0,75,76
- 536 633 536 633 521 633 c 2,77,-1
- 272 633 l 2,78,79
- 260 633 260 633 252 642 c 0,80,81
- 157 735 157 735 153 743 c 0,57,58
-695 278 m 0,82,83
- 700 273 700 273 702 265 c 0,84,85
- 703 258 703 258 703 251 c 2,86,-1
- 703 -45 l 2,87,88
- 703 -72 703 -72 692 -97 c 0,89,90
- 682 -119 682 -119 668 -138 c 0,91,92
- 655 -156 655 -156 638 -170 c 0,93,94
- 631 -175 631 -175 623 -175 c 0,95,96
- 608 -175 608 -175 602 -161 c 0,97,98
- 600 -157 600 -157 577.5 -107.5 c 128,-1,99
- 555 -58 555 -58 547 -40 c 0,100,101
- 541 -28 541 -28 541 -15 c 0,102,103
- 541 18 541 18 541 45.5 c 128,-1,104
- 541 73 541 73 541 94.5 c 128,-1,105
- 541 116 541 116 541 144 c 0,106,107
- 541 167 541 167 541 196 c 0,108,109
- 541 206 541 206 548 214 c 0,110,111
- 592 268 592 268 611 280 c 0,112,113
- 627 291 627 291 649 291 c 0,114,115
- 653 291 653 291 659 290.5 c 128,-1,116
- 665 290 665 290 666 290 c 0,117,118
- 685 289 685 289 695 278 c 0,82,83
-153 -143 m 0,119,120
- 157 -135 157 -135 252 -42 c 0,121,122
- 260 -34 260 -34 272 -34 c 2,123,-1
- 521 -34 l 2,124,125
- 536 -34 536 -34 542 -47 c 0,126,127
- 593 -161 593 -161 598 -172 c 0,128,129
- 601 -179 601 -179 594 -185 c 0,130,131
- 589 -190 589 -190 581 -191 c 0,132,133
- 580 -191 580 -191 576.5 -191.5 c 128,-1,134
- 573 -192 573 -192 572 -192 c 2,135,-1
- 555 -193 l 1,136,-1
- 226 -193 l 2,137,138
- 200 -193 200 -193 179 -178 c 0,139,140
- 169 -172 169 -172 164 -167 c 0,141,142
- 155 -158 155 -158 153 -154.5 c 128,-1,143
- 151 -151 151 -151 153 -143 c 0,119,120
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+89 416 m 0,26,27
+ 86 418 86 418 84 420 c 0,28,29
+ 76 427 76 427 76 438 c 2,30,-1
+ 76 672 l 2,31,32
+ 76 701 76 701 90 725 c 0,33,34
+ 90 726 90 726 95 735 c 0,35,36
+ 100 743 100 743 109 743 c 0,37,38
+ 115 743 115 743 120 738 c 0,39,40
+ 125 734 125 734 155 703.5 c 128,-1,41
+ 185 673 185 673 196 663 c 0,42,43
+ 206 653 206 653 205 640 c 2,44,-1
+ 205 467 l 2,45,46
+ 205 458 205 458 197 454 c 0,47,48
+ 188 448 188 448 161.5 433 c 128,-1,49
+ 135 418 135 418 128 414 c 0,50,51
+ 120 410 120 410 111 410 c 0,52,53
+ 104 410 104 410 97 412 c 0,54,55
+ 91 414 91 414 89 416 c 0,26,27
+120 751 m 0,56,57
+ 118 757 118 757 120 760 c 128,-1,58
+ 122 763 122 763 129 770 c 0,59,60
+ 133 774 133 774 141 779 c 0,61,62
+ 158 791 158 791 179 791 c 2,63,-1
+ 442 791 l 1,64,-1
+ 456 790 l 2,65,66
+ 457 790 457 790 459 789.5 c 128,-1,67
+ 461 789 461 789 463 789 c 0,68,69
+ 469 788 469 788 473 784 c 0,70,71
+ 478 779 478 779 476 773 c 0,72,73
+ 472 765 472 765 432 674 c 0,74,75
+ 427 663 427 663 415 663 c 2,76,-1
+ 216 663 l 2,77,78
+ 206 663 206 663 200 670 c 0,79,80
+ 123 745 123 745 120 751 c 0,56,57
+554 379 m 0,81,82
+ 558 375 558 375 560 368 c 0,83,84
+ 561 362 561 362 560 357 c 2,85,-1
+ 560 120 l 2,86,87
+ 560 98 560 98 552 79 c 0,88,89
+ 544 61 544 61 532 46 c 0,90,91
+ 522 32 522 32 508 20 c 0,92,93
+ 502 16 502 16 496 16 c 0,94,95
+ 484 16 484 16 480 27 c 0,96,97
+ 478 30 478 30 460 70 c 128,-1,98
+ 442 110 442 110 436 124 c 0,99,100
+ 431 134 431 134 431 144 c 0,101,102
+ 431 170 431 170 431 192.5 c 128,-1,103
+ 431 215 431 215 431 232 c 128,-1,104
+ 431 249 431 249 431 271 c 0,105,106
+ 431 289 431 289 431 313 c 0,107,108
+ 431 321 431 321 436 327 c 0,109,110
+ 471 370 471 370 487 380 c 0,111,112
+ 500 389 500 389 517 389 c 0,113,114
+ 520 389 520 389 525 388.5 c 128,-1,115
+ 530 388 530 388 531 388 c 0,116,117
+ 546 388 546 388 554 379 c 0,81,82
+120 42 m 0,118,119
+ 123 48 123 48 200 123 c 0,120,121
+ 206 129 206 129 216 129 c 2,122,-1
+ 415 129 l 2,123,124
+ 427 129 427 129 432 119 c 0,125,126
+ 473 28 473 28 476 19 c 0,127,128
+ 478 13 478 13 473 8 c 0,129,130
+ 469 4 469 4 463 3 c 0,131,132
+ 462 3 462 3 459 3 c 128,-1,133
+ 456 3 456 3 456 3 c 2,134,-1
+ 442 2 l 1,135,-1
+ 179 2 l 2,136,137
+ 158 2 158 2 141 14 c 0,138,139
+ 133 19 133 19 129 23 c 0,140,141
+ 122 30 122 30 120 33 c 128,-1,142
+ 118 36 118 36 120 42 c 0,118,119
EndSplineSet
Validated: 1
EndChar
@@ -1863,84 +2538,84 @@ EndChar
StartChar: o
Encoding: 111 111 29
-Width: 800
+Width: 640
GlyphClass: 1
Flags: W
LayerCount: 2
Fore
SplineSet
-270 366 m 0,0,1
- 288 377 288 377 310 377 c 2,2,-1
- 530 377 l 2,3,4
- 538 377 538 377 543 372 c 0,5,6
- 558 355 558 355 590 321 c 0,7,8
- 599 311 599 311 599 298 c 0,9,10
- 599 284 599 284 589 274 c 0,11,12
- 564 248 564 248 545 230 c 0,13,14
- 538 222 538 222 526 222 c 2,15,-1
- 307 222 l 2,16,17
- 288 222 288 222 272 231 c 0,18,19
- 267 234 267 234 196 275 c 0,20,21
- 183 282 183 282 183 298 c 0,22,23
- 183 313 183 313 196 321 c 0,24,25
- 203 325 203 325 230 341.5 c 128,-1,26
- 257 358 257 358 270 366 c 0,0,1
-698 278 m 0,27,28
- 703 273 703 273 705 265 c 0,29,30
- 706 258 706 258 706 251 c 2,31,-1
- 706 -45 l 2,32,33
- 706 -72 706 -72 695 -97 c 0,34,35
- 685 -119 685 -119 671 -138 c 0,36,37
- 658 -156 658 -156 641 -170 c 0,38,39
- 634 -175 634 -175 626 -175 c 0,40,41
- 611 -175 611 -175 605 -161 c 0,42,43
- 603 -157 603 -157 580.5 -107.5 c 128,-1,44
- 558 -58 558 -58 550 -40 c 0,45,46
- 544 -28 544 -28 544 -15 c 0,47,48
- 544 18 544 18 544 45.5 c 128,-1,49
- 544 73 544 73 544 94.5 c 128,-1,50
- 544 116 544 116 544 144 c 0,51,52
- 544 167 544 167 544 196 c 0,53,54
- 544 206 544 206 551 214 c 0,55,56
- 595 268 595 268 614 280 c 0,57,58
- 630 291 630 291 652 291 c 0,59,60
- 656 291 656 291 662 290.5 c 128,-1,61
- 668 290 668 290 669 290 c 0,62,63
- 688 289 688 289 698 278 c 0,27,28
-156 -143 m 0,64,65
- 160 -135 160 -135 255 -42 c 0,66,67
- 263 -34 263 -34 275 -34 c 2,68,-1
- 524 -34 l 2,69,70
- 539 -34 539 -34 545 -47 c 0,71,72
- 596 -161 596 -161 601 -172 c 0,73,74
- 604 -179 604 -179 597 -185 c 0,75,76
- 592 -190 592 -190 584 -191 c 0,77,78
- 583 -191 583 -191 579.5 -191.5 c 128,-1,79
- 576 -192 576 -192 575 -192 c 2,80,-1
- 558 -193 l 1,81,-1
- 229 -193 l 2,82,83
- 203 -193 203 -193 182 -178 c 0,84,85
- 172 -172 172 -172 167 -167 c 0,86,87
- 158 -158 158 -158 156 -154.5 c 128,-1,88
- 154 -151 154 -151 156 -143 c 0,64,65
-117 275 m 0,89,90
- 120 277 120 277 127 280 c 0,91,92
- 135 283 135 283 144 283 c 0,93,94
- 155 283 155 283 165 278 c 0,95,96
- 174 273 174 273 207.5 254 c 128,-1,97
- 241 235 241 235 252 228 c 0,98,99
- 262 223 262 223 262 212 c 2,100,-1
- 262 -6 l 2,101,102
- 262 -22 262 -22 250 -33 c 0,103,104
- 237 -46 237 -46 199 -84 c 128,-1,105
- 161 -122 161 -122 155 -127 c 0,106,107
- 150 -133 150 -133 142 -133 c 0,108,109
- 130 -133 130 -133 124 -123 c 256,110,111
- 118 -113 118 -113 118 -112 c 0,112,113
- 100 -81 100 -81 100 -45 c 2,114,-1
- 100 247 l 2,115,116
- 100 261 100 261 110 269 c 0,117,118
- 113 272 113 272 117 275 c 0,89,90
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 379 m 0,26,27
+ 558 375 558 375 560 368 c 0,28,29
+ 561 362 561 362 560 357 c 2,30,-1
+ 560 120 l 2,31,32
+ 560 98 560 98 552 79 c 0,33,34
+ 544 61 544 61 532 46 c 0,35,36
+ 522 32 522 32 508 20 c 0,37,38
+ 502 16 502 16 496 16 c 0,39,40
+ 484 16 484 16 480 27 c 0,41,42
+ 478 30 478 30 460 70 c 128,-1,43
+ 442 110 442 110 436 124 c 0,44,45
+ 431 134 431 134 431 144 c 0,46,47
+ 431 170 431 170 431 192.5 c 128,-1,48
+ 431 215 431 215 431 232 c 128,-1,49
+ 431 249 431 249 431 271 c 0,50,51
+ 431 289 431 289 431 313 c 0,52,53
+ 431 321 431 321 436 327 c 0,54,55
+ 471 370 471 370 487 380 c 0,56,57
+ 500 389 500 389 517 389 c 0,58,59
+ 520 389 520 389 525 388.5 c 128,-1,60
+ 530 388 530 388 531 388 c 0,61,62
+ 546 388 546 388 554 379 c 0,26,27
+120 42 m 0,63,64
+ 123 48 123 48 200 123 c 0,65,66
+ 206 129 206 129 216 129 c 2,67,-1
+ 415 129 l 2,68,69
+ 427 129 427 129 432 119 c 0,70,71
+ 473 28 473 28 476 19 c 0,72,73
+ 478 13 478 13 473 8 c 0,74,75
+ 469 4 469 4 463 3 c 0,76,77
+ 462 3 462 3 459 3 c 128,-1,78
+ 456 3 456 3 456 3 c 2,79,-1
+ 442 2 l 1,80,-1
+ 179 2 l 2,81,82
+ 158 2 158 2 141 14 c 0,83,84
+ 133 19 133 19 129 23 c 0,85,86
+ 122 30 122 30 120 33 c 128,-1,87
+ 118 36 118 36 120 42 c 0,63,64
+89 376 m 0,88,89
+ 91 378 91 378 97 380 c 128,-1,90
+ 103 382 103 382 111 383 c 0,91,92
+ 120 383 120 383 128 379 c 0,93,94
+ 135 375 135 375 161.5 359.5 c 128,-1,95
+ 188 344 188 344 197 339 c 0,96,97
+ 205 335 205 335 205 326 c 2,98,-1
+ 205 151 l 2,99,100
+ 205 138 205 138 196 130 c 0,101,102
+ 186 120 186 120 155 89.5 c 128,-1,103
+ 124 59 124 59 120 55 c 0,104,105
+ 116 50 116 50 109 50 c 0,106,107
+ 99 50 99 50 95 58 c 256,108,109
+ 90 66 90 66 90 67 c 0,110,111
+ 76 92 76 92 76 120 c 2,112,-1
+ 76 354 l 2,113,114
+ 76 365 76 365 84 371 c 0,115,116
+ 86 374 86 374 89 376 c 0,88,89
EndSplineSet
Validated: 1
EndChar
@@ -1974,225 +2649,215 @@ Flags: W
LayerCount: 2
Fore
SplineSet
-172 689 m 128,-1,1
- 172 713 172 713 155 730 c 128,-1,2
- 138 747 138 747 114 747 c 128,-1,3
- 90 747 90 747 73 730 c 128,-1,4
- 56 713 56 713 56 689 c 128,-1,5
- 56 665 56 665 73 648 c 128,-1,6
- 90 631 90 631 114 631 c 128,-1,7
- 138 631 138 631 155 648 c 128,-1,0
- 172 665 172 665 172 689 c 128,-1,1
-223 689 m 128,-1,9
- 223 644 223 644 191 612 c 128,-1,10
- 159 580 159 580 114 580 c 128,-1,11
- 69 580 69 580 37 612 c 128,-1,12
- 5 644 5 644 5 689 c 128,-1,13
- 5 734 5 734 37 766 c 128,-1,14
- 69 798 69 798 114 798 c 128,-1,15
- 159 798 159 798 191 766 c 128,-1,8
- 223 734 223 734 223 689 c 128,-1,9
+160 709 m 0,0,1
+ 160 730 160 730 147 742 c 0,2,3
+ 133 755 133 755 114 755 c 0,4,5
+ 93 755 93 755 81 742 c 0,6,7
+ 68 728 68 728 68 709 c 0,8,9
+ 68 688 68 688 81 676 c 0,10,11
+ 95 663 95 663 114 663 c 128,-1,12
+ 133 663 133 663 146.5 676.5 c 128,-1,13
+ 160 690 160 690 160 709 c 0,0,1
+201 709 m 0,14,15
+ 201 671 201 671 176 647 c 0,16,17
+ 150 622 150 622 114 622 c 128,-1,18
+ 78 622 78 622 52 648 c 0,19,20
+ 27 673 27 673 27 709 c 0,21,22
+ 27 747 27 747 52 771 c 0,23,24
+ 78 796 78 796 114 796 c 128,-1,25
+ 150 796 150 796 175.5 770.5 c 128,-1,26
+ 201 745 201 745 201 709 c 0,14,15
EndSplineSet
Validated: 1
EndChar
StartChar: d
Encoding: 100 100 32
-Width: 800
+Width: 640
Flags: W
-HStem: -193 159<243.48 548.143> 222 155<252.811 557.993>
-VStem: 100 162<-42.5625 234.938> 544 162<-74.7422 231.322 368.678 404 615 674.742>
LayerCount: 2
Fore
SplineSet
-698 322 m 0,0,1
- 687 310 687 310 669 310 c 0,2,3
- 666 310 666 310 662 310 c 0,4,5
- 656 309 656 309 652 309 c 0,6,7
- 630 309 630 309 614 320 c 0,8,9
- 602 327 602 327 551 386 c 0,10,11
- 544 394 544 394 544 404 c 2,12,13
- 544 404 544 404 544 456 c 1,14,-1
- 544 506 l 1,15,-1
- 544 554 l 1,16,-1
- 544 615 l 2,17,18
- 544 628 544 628 550 640 c 0,19,20
- 558 658 558 658 580.5 707.5 c 128,-1,21
- 603 757 603 757 605 761 c 0,22,23
- 611 775 611 775 626 775 c 0,24,25
- 634 775 634 775 641 770 c 0,26,27
- 657 757 657 757 671 738 c 128,-1,28
- 685 719 685 719 695 697 c 0,29,30
- 706 672 706 672 706 645 c 2,31,32
- 706 645 706 645 706 349 c 2,33,34
- 706 339 706 339 705 335 c 0,35,36
- 703 327 703 327 698 322 c 0,0,1
-270 366 m 0,37,38
- 288 377 288 377 310 377 c 2,39,-1
- 530 377 l 2,40,41
- 538 377 538 377 543 372 c 0,42,43
- 558 355 558 355 590 321 c 0,44,45
- 599 311 599 311 599 298 c 0,46,47
- 599 284 599 284 589 274 c 0,48,49
- 564 248 564 248 545 230 c 0,50,51
- 538 222 538 222 526 222 c 2,52,-1
- 307 222 l 2,53,54
- 288 222 288 222 272 231 c 0,55,56
- 267 234 267 234 196 275 c 0,57,58
- 183 282 183 282 183 298 c 0,59,60
- 183 313 183 313 196 321 c 0,61,62
- 203 325 203 325 230 341.5 c 128,-1,63
- 257 358 257 358 270 366 c 0,37,38
-698 278 m 0,64,65
- 703 273 703 273 705 265 c 0,66,67
- 706 258 706 258 706 251 c 2,68,-1
- 706 -45 l 2,69,70
- 706 -72 706 -72 695 -97 c 0,71,72
- 685 -119 685 -119 671 -138 c 0,73,74
- 658 -156 658 -156 641 -170 c 0,75,76
- 634 -175 634 -175 626 -175 c 0,77,78
- 611 -175 611 -175 605 -161 c 0,79,80
- 603 -157 603 -157 580.5 -107.5 c 128,-1,81
- 558 -58 558 -58 550 -40 c 0,82,83
- 544 -28 544 -28 544 -15 c 0,84,85
- 544 18 544 18 544 45.5 c 128,-1,86
- 544 73 544 73 544 94.5 c 128,-1,87
- 544 116 544 116 544 144 c 0,88,89
- 544 167 544 167 544 196 c 0,90,91
- 544 206 544 206 551 214 c 0,92,93
- 595 268 595 268 614 280 c 0,94,95
- 630 291 630 291 652 291 c 0,96,97
- 656 291 656 291 662 290.5 c 128,-1,98
- 668 290 668 290 669 290 c 0,99,100
- 688 289 688 289 698 278 c 0,64,65
-156 -143 m 0,101,102
- 160 -135 160 -135 255 -42 c 0,103,104
- 263 -34 263 -34 275 -34 c 2,105,-1
- 524 -34 l 2,106,107
- 539 -34 539 -34 545 -47 c 0,108,109
- 596 -161 596 -161 601 -172 c 0,110,111
- 604 -179 604 -179 597 -185 c 0,112,113
- 592 -190 592 -190 584 -191 c 0,114,115
- 583 -191 583 -191 579.5 -191.5 c 128,-1,116
- 576 -192 576 -192 575 -192 c 2,117,-1
- 558 -193 l 1,118,-1
- 229 -193 l 2,119,120
- 203 -193 203 -193 182 -178 c 0,121,122
- 172 -172 172 -172 167 -167 c 0,123,124
- 158 -158 158 -158 156 -154.5 c 128,-1,125
- 154 -151 154 -151 156 -143 c 0,101,102
-117 275 m 0,126,127
- 120 277 120 277 127 280 c 0,128,129
- 135 283 135 283 144 283 c 0,130,131
- 155 283 155 283 165 278 c 0,132,133
- 174 273 174 273 207.5 254 c 128,-1,134
- 241 235 241 235 252 228 c 0,135,136
- 262 223 262 223 262 212 c 2,137,-1
- 262 -6 l 2,138,139
- 262 -22 262 -22 250 -33 c 0,140,141
- 237 -46 237 -46 199 -84 c 128,-1,142
- 161 -122 161 -122 155 -127 c 0,143,144
- 150 -133 150 -133 142 -133 c 0,145,146
- 130 -133 130 -133 124 -123 c 256,147,148
- 118 -113 118 -113 118 -112 c 0,149,150
- 100 -81 100 -81 100 -45 c 2,151,-1
- 100 247 l 2,152,153
- 100 261 100 261 110 269 c 0,154,155
- 113 272 113 272 117 275 c 0,126,127
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+554 411 m 0,26,27
+ 546 402 546 402 531 402 c 0,28,29
+ 530 402 530 402 525 401.5 c 128,-1,30
+ 520 401 520 401 517 401 c 0,31,32
+ 499 401 499 401 487 410 c 0,33,34
+ 472 420 472 420 436 462 c 0,35,36
+ 430 468 430 468 431 477 c 0,37,38
+ 431 500 431 500 431 519 c 0,39,40
+ 431 541 431 541 431 558 c 128,-1,41
+ 431 575 431 575 431 597 c 128,-1,42
+ 431 619 431 619 431 646 c 0,43,44
+ 431 656 431 656 436 666 c 0,45,46
+ 462 724 462 724 480 763 c 0,47,48
+ 485 773 485 773 496 773 c 0,49,50
+ 502 773 502 773 508 770 c 0,51,52
+ 520 761 520 761 532 744 c 0,53,54
+ 546 726 546 726 552 711 c 0,55,56
+ 560 693 560 693 560 673 c 0,57,58
+ 560 671 560 671 560 669 c 2,59,-1
+ 560 433 l 2,60,61
+ 560 427 560 427 560 422 c 0,62,63
+ 558 415 558 415 554 411 c 0,26,27
+554 379 m 0,64,65
+ 558 375 558 375 560 368 c 0,66,67
+ 561 362 561 362 560 357 c 2,68,-1
+ 560 120 l 2,69,70
+ 560 98 560 98 552 79 c 0,71,72
+ 544 61 544 61 532 46 c 0,73,74
+ 522 32 522 32 508 20 c 0,75,76
+ 502 16 502 16 496 16 c 0,77,78
+ 484 16 484 16 480 27 c 0,79,80
+ 478 30 478 30 460 70 c 128,-1,81
+ 442 110 442 110 436 124 c 0,82,83
+ 431 134 431 134 431 144 c 0,84,85
+ 431 170 431 170 431 192.5 c 128,-1,86
+ 431 215 431 215 431 232 c 128,-1,87
+ 431 249 431 249 431 271 c 0,88,89
+ 431 289 431 289 431 313 c 0,90,91
+ 431 321 431 321 436 327 c 0,92,93
+ 471 370 471 370 487 380 c 0,94,95
+ 500 389 500 389 517 389 c 0,96,97
+ 520 389 520 389 525 388.5 c 128,-1,98
+ 530 388 530 388 531 388 c 0,99,100
+ 546 388 546 388 554 379 c 0,64,65
+120 42 m 0,101,102
+ 123 48 123 48 200 123 c 0,103,104
+ 206 129 206 129 216 129 c 2,105,-1
+ 415 129 l 2,106,107
+ 427 129 427 129 432 119 c 0,108,109
+ 473 28 473 28 476 19 c 0,110,111
+ 478 13 478 13 473 8 c 0,112,113
+ 469 4 469 4 463 3 c 0,114,115
+ 462 3 462 3 459 3 c 128,-1,116
+ 456 3 456 3 456 3 c 2,117,-1
+ 442 2 l 1,118,-1
+ 179 2 l 2,119,120
+ 158 2 158 2 141 14 c 0,121,122
+ 133 19 133 19 129 23 c 0,123,124
+ 122 30 122 30 120 33 c 128,-1,125
+ 118 36 118 36 120 42 c 0,101,102
+89 376 m 0,126,127
+ 91 378 91 378 97 380 c 128,-1,128
+ 103 382 103 382 111 383 c 0,129,130
+ 120 383 120 383 128 379 c 0,131,132
+ 135 375 135 375 161.5 359.5 c 128,-1,133
+ 188 344 188 344 197 339 c 0,134,135
+ 205 335 205 335 205 326 c 2,136,-1
+ 205 151 l 2,137,138
+ 205 138 205 138 196 130 c 0,139,140
+ 186 120 186 120 155 89.5 c 128,-1,141
+ 124 59 124 59 120 55 c 0,142,143
+ 116 50 116 50 109 50 c 0,144,145
+ 99 50 99 50 95 58 c 256,146,147
+ 90 66 90 66 90 67 c 0,148,149
+ 76 92 76 92 76 120 c 2,150,-1
+ 76 354 l 2,151,152
+ 76 365 76 365 84 371 c 0,153,154
+ 86 374 86 374 89 376 c 0,126,127
EndSplineSet
Validated: 1
EndChar
StartChar: t
Encoding: 116 116 33
-Width: 800
+Width: 640
Flags: W
LayerCount: 2
Fore
SplineSet
-102 322 m 0,0,1
- 97 327 97 327 95 335 c 0,2,3
- 94 342 94 342 94 349 c 2,4,-1
- 94 645 l 2,5,6
- 94 672 94 672 105 697 c 0,7,8
- 115 719 115 719 129 738 c 0,9,10
- 142 756 142 756 159 770 c 0,11,12
- 166 775 166 775 174 775 c 0,13,14
- 189 775 189 775 195 761 c 0,15,16
- 197 757 197 757 219.5 707.5 c 128,-1,17
- 242 658 242 658 250 640 c 0,18,19
- 256 628 256 628 256 615 c 2,20,-1
- 256 554 l 1,21,-1
- 256 506 l 1,22,-1
- 256 456 l 1,23,-1
- 256 404 l 2,24,25
- 256 394 256 394 249 386 c 0,26,27
- 205 332 205 332 186 320 c 0,28,29
- 170 309 170 309 148 309 c 0,30,31
- 144 309 144 309 138 309.5 c 128,-1,32
- 132 310 132 310 131 310 c 0,33,34
- 112 311 112 311 102 322 c 0,0,1
-530 366 m 0,35,36
- 543 358 543 358 570 341.5 c 128,-1,37
- 597 325 597 325 604 321 c 0,38,39
- 617 313 617 313 617 298 c 0,40,41
- 617 282 617 282 604 275 c 0,42,43
- 533 234 533 234 528 231 c 0,44,45
- 512 222 512 222 493 222 c 2,46,47
- 493 222 493 222 274 222 c 2,48,49
- 262 222 262 222 255 230 c 0,50,51
- 236 248 236 248 211 274 c 0,52,53
- 201 284 201 284 201 298 c 0,54,55
- 201 311 201 311 210 321 c 0,56,57
- 242 355 242 355 257 372 c 0,58,59
- 262 377 262 377 270 377 c 2,60,61
- 270 377 270 377 490 377 c 2,62,63
- 512 377 512 377 530 366 c 0,35,36
-102 278 m 0,64,65
- 112 289 112 289 131 290 c 0,66,67
- 132 290 132 290 138 290.5 c 128,-1,68
- 144 291 144 291 148 291 c 0,69,70
- 170 291 170 291 186 280 c 0,71,72
- 205 268 205 268 249 214 c 0,73,74
- 256 206 256 206 256 196 c 0,75,76
- 256 167 256 167 256 144 c 0,77,78
- 256 116 256 116 256 94.5 c 128,-1,79
- 256 73 256 73 256 45.5 c 128,-1,80
- 256 18 256 18 256 -15 c 0,81,82
- 256 -28 256 -28 250 -40 c 0,83,84
- 242 -58 242 -58 219.5 -107.5 c 128,-1,85
- 197 -157 197 -157 195 -161 c 0,86,87
- 189 -175 189 -175 174 -175 c 0,88,89
- 166 -175 166 -175 159 -170 c 0,90,91
- 142 -156 142 -156 129 -138 c 0,92,93
- 115 -119 115 -119 105 -97 c 0,94,95
- 94 -72 94 -72 94 -45 c 2,96,97
- 94 -45 94 -45 94 251 c 2,98,99
- 94 258 94 258 95 265 c 0,100,101
- 97 273 97 273 102 278 c 0,64,65
-644 -143 m 0,102,103
- 646 -151 646 -151 644 -154.5 c 128,-1,104
- 642 -158 642 -158 633 -167 c 0,105,106
- 628 -172 628 -172 618 -178 c 0,107,108
- 597 -193 597 -193 571 -193 c 2,109,110
- 571 -193 571 -193 242 -193 c 1,111,-1
- 225 -192 l 2,112,113
- 224 -192 224 -192 220.5 -191.5 c 128,-1,114
- 217 -191 217 -191 216 -191 c 0,115,116
- 208 -190 208 -190 203 -185 c 0,117,118
- 196 -179 196 -179 199 -172 c 0,119,120
- 204 -161 204 -161 255 -47 c 0,121,122
- 261 -34 261 -34 276 -34 c 2,123,124
- 276 -34 276 -34 525 -34 c 2,125,126
- 537 -34 537 -34 545 -42 c 0,127,128
- 640 -135 640 -135 644 -143 c 0,102,103
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+89 416 m 0,26,27
+ 86 418 86 418 84 420 c 0,28,29
+ 76 427 76 427 76 438 c 2,30,-1
+ 76 672 l 2,31,32
+ 76 701 76 701 90 725 c 0,33,34
+ 90 726 90 726 95 735 c 0,35,36
+ 100 743 100 743 109 743 c 0,37,38
+ 115 743 115 743 120 738 c 0,39,40
+ 125 734 125 734 155 703.5 c 128,-1,41
+ 185 673 185 673 196 663 c 0,42,43
+ 206 653 206 653 205 640 c 2,44,-1
+ 205 467 l 2,45,46
+ 205 458 205 458 197 454 c 0,47,48
+ 188 448 188 448 161.5 433 c 128,-1,49
+ 135 418 135 418 128 414 c 0,50,51
+ 120 410 120 410 111 410 c 0,52,53
+ 104 410 104 410 97 412 c 0,54,55
+ 91 414 91 414 89 416 c 0,26,27
+120 42 m 0,56,57
+ 123 48 123 48 200 123 c 0,58,59
+ 206 129 206 129 216 129 c 2,60,-1
+ 415 129 l 2,61,62
+ 427 129 427 129 432 119 c 0,63,64
+ 473 28 473 28 476 19 c 0,65,66
+ 478 13 478 13 473 8 c 0,67,68
+ 469 4 469 4 463 3 c 0,69,70
+ 462 3 462 3 459 3 c 128,-1,71
+ 456 3 456 3 456 3 c 2,72,-1
+ 442 2 l 1,73,-1
+ 179 2 l 2,74,75
+ 158 2 158 2 141 14 c 0,76,77
+ 133 19 133 19 129 23 c 0,78,79
+ 122 30 122 30 120 33 c 128,-1,80
+ 118 36 118 36 120 42 c 0,56,57
+89 376 m 0,81,82
+ 91 378 91 378 97 380 c 128,-1,83
+ 103 382 103 382 111 383 c 0,84,85
+ 120 383 120 383 128 379 c 0,86,87
+ 135 375 135 375 161.5 359.5 c 128,-1,88
+ 188 344 188 344 197 339 c 0,89,90
+ 205 335 205 335 205 326 c 2,91,-1
+ 205 151 l 2,92,93
+ 205 138 205 138 196 130 c 0,94,95
+ 186 120 186 120 155 89.5 c 128,-1,96
+ 124 59 124 59 120 55 c 0,97,98
+ 116 50 116 50 109 50 c 0,99,100
+ 99 50 99 50 95 58 c 256,101,102
+ 90 66 90 66 90 67 c 0,103,104
+ 76 92 76 92 76 120 c 2,105,-1
+ 76 354 l 2,106,107
+ 76 365 76 365 84 371 c 0,108,109
+ 86 374 86 374 89 376 c 0,81,82
EndSplineSet
Validated: 1
EndChar
StartChar: asciitilde
Encoding: 126 126 34
-Width: 600
+Width: 640
Flags: W
HStem: -193 159<515.48 820.143> 222 155<524.811 829.993>
VStem: 372 162<-42.5625 234.938> 816 162<-74.7422 231.322 368.678 404 615 674.742>
@@ -2203,8 +2868,10 @@ EndChar
StartChar: space
Encoding: 32 32 35
-Width: 800
+Width: 640
Flags: W
+HStem: -193 159<515.48 820.143> 222 155<524.811 829.993>
+VStem: 372 162<-42.5625 234.938> 816 162<-74.7422 231.322 368.678 404 615 674.742>
LayerCount: 2
Fore
Validated: 1
@@ -2212,168 +2879,637 @@ EndChar
StartChar: asterisk
Encoding: 42 42 36
-Width: 800
+Width: 640
+Flags: W
+LayerCount: 2
+Fore
+SplineSet
+359 479 m 4,0,1
+ 355 473 355 473 350 473 c 6,2,-1
+ 281 473 l 6,3,4
+ 275 473 275 473 272 479 c 4,5,6
+ 267 488 267 488 256 506 c 4,7,8
+ 251 514 251 514 252 522 c 4,9,10
+ 253 532 253 532 256 538 c 4,11,12
+ 282 591 282 591 305 619 c 4,13,14
+ 309 624 309 624 316 624 c 132,-1,15
+ 323 624 323 624 326 619 c 4,16,17
+ 332 610 332 610 350 579 c 132,-1,18
+ 368 548 368 548 375 538 c 4,19,20
+ 380 531 380 531 380 522 c 4,21,22
+ 380 515 380 515 375 506 c 4,23,24
+ 369 496 369 496 359 479 c 4,0,1
+209 449 m 4,25,26
+ 224 458 224 458 241 458 c 6,27,-1
+ 417 458 l 6,28,29
+ 425 458 425 458 428 454 c 4,30,31
+ 440 440 440 440 465 413 c 4,32,33
+ 471 406 471 406 472 395 c 132,-1,34
+ 473 384 473 384 464 375 c 4,35,36
+ 446 358 446 358 429 340 c 4,37,38
+ 423 334 423 334 414 334 c 6,39,-1
+ 239 334 l 6,40,41
+ 225 334 225 334 211 341 c 4,42,43
+ 195 349 195 349 150 376 c 4,44,45
+ 141 381 141 381 140 395 c 4,46,47
+ 139 406 139 406 150 413 c 4,48,49
+ 156 416 156 416 177.5 429.5 c 132,-1,50
+ 199 443 199 443 209 449 c 4,25,26
+359 313 m 4,51,52
+ 364 303 364 303 375 286 c 4,53,54
+ 380 278 380 278 380 269 c 132,-1,55
+ 380 260 380 260 375 254 c 4,56,57
+ 340 195 340 195 326 173 c 4,58,59
+ 323 167 323 167 315.5 167 c 132,-1,60
+ 308 167 308 167 305 173 c 4,61,62
+ 299 183 299 183 281 213 c 132,-1,63
+ 263 243 263 243 256 254 c 4,64,65
+ 252 261 252 261 252 270 c 132,-1,66
+ 252 279 252 279 256 286 c 4,67,68
+ 269 308 269 308 272 313 c 132,-1,69
+ 275 318 275 318 281 318 c 6,70,-1
+ 350 318 l 6,71,72
+ 356 318 356 318 359 313 c 4,51,52
+554 411 m 4,73,74
+ 546 402 546 402 531 402 c 4,75,76
+ 530 402 530 402 525 401.5 c 132,-1,77
+ 520 401 520 401 517 401 c 4,78,79
+ 499 401 499 401 487 410 c 4,80,81
+ 472 420 472 420 436 462 c 4,82,83
+ 430 468 430 468 431 477 c 4,84,85
+ 431 500 431 500 431 519 c 4,86,87
+ 431 541 431 541 431 558 c 132,-1,88
+ 431 575 431 575 431 597 c 132,-1,89
+ 431 619 431 619 431 646 c 4,90,91
+ 431 656 431 656 436 666 c 4,92,93
+ 462 724 462 724 480 763 c 4,94,95
+ 485 773 485 773 496 773 c 4,96,97
+ 502 773 502 773 508 770 c 4,98,99
+ 520 761 520 761 532 744 c 4,100,101
+ 546 726 546 726 552 711 c 4,102,103
+ 560 693 560 693 560 673 c 4,104,105
+ 560 671 560 671 560 669 c 6,106,-1
+ 560 433 l 6,107,108
+ 560 427 560 427 560 422 c 4,109,110
+ 558 415 558 415 554 411 c 4,73,74
+89 416 m 4,111,112
+ 86 418 86 418 84 420 c 4,113,114
+ 76 427 76 427 76 438 c 6,115,-1
+ 76 672 l 6,116,117
+ 76 701 76 701 90 725 c 4,118,119
+ 90 726 90 726 95 735 c 4,120,121
+ 100 743 100 743 109 743 c 4,122,123
+ 115 743 115 743 120 738 c 4,124,125
+ 125 734 125 734 155 703.5 c 132,-1,126
+ 185 673 185 673 196 663 c 4,127,128
+ 206 653 206 653 205 640 c 6,129,-1
+ 205 467 l 6,130,131
+ 205 458 205 458 197 454 c 4,132,133
+ 188 448 188 448 161.5 433 c 132,-1,134
+ 135 418 135 418 128 414 c 4,135,136
+ 120 410 120 410 111 410 c 4,137,138
+ 104 410 104 410 97 412 c 4,139,140
+ 91 414 91 414 89 416 c 4,111,112
+120 751 m 4,141,142
+ 118 757 118 757 120 760 c 132,-1,143
+ 122 763 122 763 129 770 c 4,144,145
+ 133 774 133 774 141 779 c 4,146,147
+ 158 791 158 791 179 791 c 6,148,-1
+ 442 791 l 5,149,-1
+ 456 790 l 6,150,151
+ 457 790 457 790 459 789.5 c 132,-1,152
+ 461 789 461 789 463 789 c 4,153,154
+ 469 788 469 788 473 784 c 4,155,156
+ 478 779 478 779 476 773 c 4,157,158
+ 472 765 472 765 432 674 c 4,159,160
+ 427 663 427 663 415 663 c 6,161,-1
+ 216 663 l 6,162,163
+ 206 663 206 663 200 670 c 4,164,165
+ 123 745 123 745 120 751 c 4,141,142
+554 379 m 4,166,167
+ 558 375 558 375 560 368 c 4,168,169
+ 561 362 561 362 560 357 c 6,170,-1
+ 560 120 l 6,171,172
+ 560 98 560 98 552 79 c 4,173,174
+ 544 61 544 61 532 46 c 4,175,176
+ 522 32 522 32 508 20 c 4,177,178
+ 502 16 502 16 496 16 c 4,179,180
+ 484 16 484 16 480 27 c 4,181,182
+ 478 30 478 30 460 70 c 132,-1,183
+ 442 110 442 110 436 124 c 4,184,185
+ 431 134 431 134 431 144 c 4,186,187
+ 431 170 431 170 431 192.5 c 132,-1,188
+ 431 215 431 215 431 232 c 132,-1,189
+ 431 249 431 249 431 271 c 4,190,191
+ 431 289 431 289 431 313 c 4,192,193
+ 431 321 431 321 436 327 c 4,194,195
+ 471 370 471 370 487 380 c 4,196,197
+ 500 389 500 389 517 389 c 4,198,199
+ 520 389 520 389 525 388.5 c 132,-1,200
+ 530 388 530 388 531 388 c 4,201,202
+ 546 388 546 388 554 379 c 4,166,167
+120 42 m 4,203,204
+ 123 48 123 48 200 123 c 4,205,206
+ 206 129 206 129 216 129 c 6,207,-1
+ 415 129 l 6,208,209
+ 427 129 427 129 432 119 c 4,210,211
+ 473 28 473 28 476 19 c 4,212,213
+ 478 13 478 13 473 8 c 4,214,215
+ 469 4 469 4 463 3 c 4,216,217
+ 462 3 462 3 459 3 c 132,-1,218
+ 456 3 456 3 456 3 c 6,219,-1
+ 442 2 l 5,220,-1
+ 179 2 l 6,221,222
+ 158 2 158 2 141 14 c 4,223,224
+ 133 19 133 19 129 23 c 4,225,226
+ 122 30 122 30 120 33 c 132,-1,227
+ 118 36 118 36 120 42 c 4,203,204
+89 376 m 4,228,229
+ 91 378 91 378 97 380 c 132,-1,230
+ 103 382 103 382 111 383 c 4,231,232
+ 120 383 120 383 128 379 c 4,233,234
+ 135 375 135 375 161.5 359.5 c 132,-1,235
+ 188 344 188 344 197 339 c 4,236,237
+ 205 335 205 335 205 326 c 6,238,-1
+ 205 151 l 6,239,240
+ 205 138 205 138 196 130 c 4,241,242
+ 186 120 186 120 155 89.5 c 132,-1,243
+ 124 59 124 59 120 55 c 4,244,245
+ 116 50 116 50 109 50 c 4,246,247
+ 99 50 99 50 95 58 c 260,248,249
+ 90 66 90 66 90 67 c 4,250,251
+ 76 92 76 92 76 120 c 6,252,-1
+ 76 354 l 6,253,254
+ 76 365 76 365 84 371 c 4,255,256
+ 86 374 86 374 89 376 c 4,228,229
+EndSplineSet
+Validated: 2049
+EndChar
+
+StartChar: f
+Encoding: 102 102 37
+Width: 640
+Flags: W
+LayerCount: 2
+Fore
+SplineSet
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+89 416 m 0,26,27
+ 86 418 86 418 84 420 c 0,28,29
+ 76 427 76 427 76 438 c 2,30,-1
+ 76 672 l 2,31,32
+ 76 701 76 701 90 725 c 0,33,34
+ 90 726 90 726 95 735 c 0,35,36
+ 100 743 100 743 109 743 c 0,37,38
+ 115 743 115 743 120 738 c 0,39,40
+ 125 734 125 734 155 703.5 c 128,-1,41
+ 185 673 185 673 196 663 c 0,42,43
+ 206 653 206 653 205 640 c 2,44,-1
+ 205 467 l 2,45,46
+ 205 458 205 458 197 454 c 0,47,48
+ 188 448 188 448 161.5 433 c 128,-1,49
+ 135 418 135 418 128 414 c 0,50,51
+ 120 410 120 410 111 410 c 0,52,53
+ 104 410 104 410 97 412 c 0,54,55
+ 91 414 91 414 89 416 c 0,26,27
+120 751 m 0,56,57
+ 118 757 118 757 120 760 c 128,-1,58
+ 122 763 122 763 129 770 c 0,59,60
+ 133 774 133 774 141 779 c 0,61,62
+ 158 791 158 791 179 791 c 2,63,-1
+ 442 791 l 1,64,-1
+ 456 790 l 2,65,66
+ 457 790 457 790 459 789.5 c 128,-1,67
+ 461 789 461 789 463 789 c 0,68,69
+ 469 788 469 788 473 784 c 0,70,71
+ 478 779 478 779 476 773 c 0,72,73
+ 472 765 472 765 432 674 c 0,74,75
+ 427 663 427 663 415 663 c 2,76,-1
+ 216 663 l 2,77,78
+ 206 663 206 663 200 670 c 0,79,80
+ 123 745 123 745 120 751 c 0,56,57
+89 376 m 0,81,82
+ 91 378 91 378 97 380 c 128,-1,83
+ 103 382 103 382 111 383 c 0,84,85
+ 120 383 120 383 128 379 c 0,86,87
+ 135 375 135 375 161.5 359.5 c 128,-1,88
+ 188 344 188 344 197 339 c 0,89,90
+ 205 335 205 335 205 326 c 2,91,-1
+ 205 151 l 2,92,93
+ 205 138 205 138 196 130 c 0,94,95
+ 186 120 186 120 155 89.5 c 128,-1,96
+ 124 59 124 59 120 55 c 0,97,98
+ 116 50 116 50 109 50 c 0,99,100
+ 99 50 99 50 95 58 c 256,101,102
+ 90 66 90 66 90 67 c 0,103,104
+ 76 92 76 92 76 120 c 2,105,-1
+ 76 354 l 2,106,107
+ 76 365 76 365 84 371 c 0,108,109
+ 86 374 86 374 89 376 c 0,81,82
+EndSplineSet
+Validated: 1
+EndChar
+
+StartChar: e
+Encoding: 101 101 38
+Width: 640
+Flags: W
+LayerCount: 2
+Fore
+SplineSet
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+89 416 m 0,26,27
+ 86 418 86 418 84 420 c 0,28,29
+ 76 427 76 427 76 438 c 2,30,-1
+ 76 672 l 2,31,32
+ 76 701 76 701 90 725 c 0,33,34
+ 90 726 90 726 95 735 c 0,35,36
+ 100 743 100 743 109 743 c 0,37,38
+ 115 743 115 743 120 738 c 0,39,40
+ 125 734 125 734 155 703.5 c 128,-1,41
+ 185 673 185 673 196 663 c 0,42,43
+ 206 653 206 653 205 640 c 2,44,-1
+ 205 467 l 2,45,46
+ 205 458 205 458 197 454 c 0,47,48
+ 188 448 188 448 161.5 433 c 128,-1,49
+ 135 418 135 418 128 414 c 0,50,51
+ 120 410 120 410 111 410 c 0,52,53
+ 104 410 104 410 97 412 c 0,54,55
+ 91 414 91 414 89 416 c 0,26,27
+120 751 m 0,56,57
+ 118 757 118 757 120 760 c 128,-1,58
+ 122 763 122 763 129 770 c 0,59,60
+ 133 774 133 774 141 779 c 0,61,62
+ 158 791 158 791 179 791 c 2,63,-1
+ 442 791 l 1,64,-1
+ 456 790 l 2,65,66
+ 457 790 457 790 459 789.5 c 128,-1,67
+ 461 789 461 789 463 789 c 0,68,69
+ 469 788 469 788 473 784 c 0,70,71
+ 478 779 478 779 476 773 c 0,72,73
+ 472 765 472 765 432 674 c 0,74,75
+ 427 663 427 663 415 663 c 2,76,-1
+ 216 663 l 2,77,78
+ 206 663 206 663 200 670 c 0,79,80
+ 123 745 123 745 120 751 c 0,56,57
+120 42 m 0,81,82
+ 123 48 123 48 200 123 c 0,83,84
+ 206 129 206 129 216 129 c 2,85,-1
+ 415 129 l 2,86,87
+ 427 129 427 129 432 119 c 0,88,89
+ 473 28 473 28 476 19 c 0,90,91
+ 478 13 478 13 473 8 c 0,92,93
+ 469 4 469 4 463 3 c 0,94,95
+ 462 3 462 3 459 3 c 128,-1,96
+ 456 3 456 3 456 3 c 2,97,-1
+ 442 2 l 1,98,-1
+ 179 2 l 2,99,100
+ 158 2 158 2 141 14 c 0,101,102
+ 133 19 133 19 129 23 c 0,103,104
+ 122 30 122 30 120 33 c 128,-1,105
+ 118 36 118 36 120 42 c 0,81,82
+89 376 m 0,106,107
+ 91 378 91 378 97 380 c 128,-1,108
+ 103 382 103 382 111 383 c 0,109,110
+ 120 383 120 383 128 379 c 0,111,112
+ 135 375 135 375 161.5 359.5 c 128,-1,113
+ 188 344 188 344 197 339 c 0,114,115
+ 205 335 205 335 205 326 c 2,116,-1
+ 205 151 l 2,117,118
+ 205 138 205 138 196 130 c 0,119,120
+ 186 120 186 120 155 89.5 c 128,-1,121
+ 124 59 124 59 120 55 c 0,122,123
+ 116 50 116 50 109 50 c 0,124,125
+ 99 50 99 50 95 58 c 256,126,127
+ 90 66 90 66 90 67 c 0,128,129
+ 76 92 76 92 76 120 c 2,130,-1
+ 76 354 l 2,131,132
+ 76 365 76 365 84 371 c 0,133,134
+ 86 374 86 374 89 376 c 0,106,107
+EndSplineSet
+Validated: 1
+EndChar
+
+StartChar: q
+Encoding: 113 113 39
+Width: 640
+Flags: W
+LayerCount: 2
+Fore
+SplineSet
+463 -4 m 0,0,1
+ 483 -4 483 -4 495 -13 c 2,2,-1
+ 588 -82 l 2,3,4
+ 593 -86 593 -86 595 -91 c 0,5,6
+ 599 -109 599 -109 605 -145 c 0,7,8
+ 607 -156 607 -156 602 -165 c 0,9,10
+ 596 -173 596 -173 585 -177 c 0,11,12
+ 576 -180 576 -180 532 -187 c 0,13,14
+ 525 -188 525 -188 515 -181 c 2,15,-1
+ 428 -118 l 2,16,17
+ 412 -106 412 -106 408 -97 c 0,18,19
+ 380 -46 380 -46 374 -35 c 0,20,21
+ 369 -24 369 -24 375.5 -14 c 128,-1,22
+ 382 -4 382 -4 394 -4 c 0,23,24
+ 400 -4 400 -4 425 -4 c 0,25,26
+ 451 -4 451 -4 463 -4 c 0,0,1
+554 411 m 0,27,28
+ 546 402 546 402 531 402 c 0,29,30
+ 530 402 530 402 525 401.5 c 128,-1,31
+ 520 401 520 401 517 401 c 0,32,33
+ 499 401 499 401 487 410 c 0,34,35
+ 472 420 472 420 436 462 c 0,36,37
+ 430 468 430 468 431 477 c 0,38,39
+ 431 500 431 500 431 519 c 0,40,41
+ 431 541 431 541 431 558 c 128,-1,42
+ 431 575 431 575 431 597 c 128,-1,43
+ 431 619 431 619 431 646 c 0,44,45
+ 431 656 431 656 436 666 c 0,46,47
+ 462 724 462 724 480 763 c 0,48,49
+ 485 773 485 773 496 773 c 0,50,51
+ 502 773 502 773 508 770 c 0,52,53
+ 520 761 520 761 532 744 c 0,54,55
+ 546 726 546 726 552 711 c 0,56,57
+ 560 693 560 693 560 673 c 0,58,59
+ 560 671 560 671 560 669 c 2,60,-1
+ 560 433 l 2,61,62
+ 560 427 560 427 560 422 c 0,63,64
+ 558 415 558 415 554 411 c 0,27,28
+89 416 m 0,65,66
+ 86 418 86 418 84 420 c 0,67,68
+ 76 427 76 427 76 438 c 2,69,-1
+ 76 672 l 2,70,71
+ 76 701 76 701 90 725 c 0,72,73
+ 90 726 90 726 95 735 c 0,74,75
+ 100 743 100 743 109 743 c 0,76,77
+ 115 743 115 743 120 738 c 0,78,79
+ 125 734 125 734 155 703.5 c 128,-1,80
+ 185 673 185 673 196 663 c 0,81,82
+ 206 653 206 653 205 640 c 2,83,-1
+ 205 467 l 2,84,85
+ 205 458 205 458 197 454 c 0,86,87
+ 188 448 188 448 161.5 433 c 128,-1,88
+ 135 418 135 418 128 414 c 0,89,90
+ 120 410 120 410 111 410 c 0,91,92
+ 104 410 104 410 97 412 c 0,93,94
+ 91 414 91 414 89 416 c 0,65,66
+120 751 m 0,95,96
+ 118 757 118 757 120 760 c 128,-1,97
+ 122 763 122 763 129 770 c 0,98,99
+ 133 774 133 774 141 779 c 0,100,101
+ 158 791 158 791 179 791 c 2,102,-1
+ 442 791 l 1,103,-1
+ 456 790 l 2,104,105
+ 457 790 457 790 459 789.5 c 128,-1,106
+ 461 789 461 789 463 789 c 0,107,108
+ 469 788 469 788 473 784 c 0,109,110
+ 478 779 478 779 476 773 c 0,111,112
+ 472 765 472 765 432 674 c 0,113,114
+ 427 663 427 663 415 663 c 2,115,-1
+ 216 663 l 2,116,117
+ 206 663 206 663 200 670 c 0,118,119
+ 123 745 123 745 120 751 c 0,95,96
+554 379 m 0,120,121
+ 558 375 558 375 560 368 c 0,122,123
+ 561 362 561 362 560 357 c 2,124,-1
+ 560 120 l 2,125,126
+ 560 98 560 98 552 79 c 0,127,128
+ 544 61 544 61 532 46 c 0,129,130
+ 522 32 522 32 508 20 c 0,131,132
+ 502 16 502 16 496 16 c 0,133,134
+ 484 16 484 16 480 27 c 0,135,136
+ 478 30 478 30 460 70 c 128,-1,137
+ 442 110 442 110 436 124 c 0,138,139
+ 431 134 431 134 431 144 c 0,140,141
+ 431 170 431 170 431 192.5 c 128,-1,142
+ 431 215 431 215 431 232 c 128,-1,143
+ 431 249 431 249 431 271 c 0,144,145
+ 431 289 431 289 431 313 c 0,146,147
+ 431 321 431 321 436 327 c 0,148,149
+ 471 370 471 370 487 380 c 0,150,151
+ 500 389 500 389 517 389 c 0,152,153
+ 520 389 520 389 525 388.5 c 128,-1,154
+ 530 388 530 388 531 388 c 0,155,156
+ 546 388 546 388 554 379 c 0,120,121
+120 42 m 0,157,158
+ 123 48 123 48 200 123 c 0,159,160
+ 206 129 206 129 216 129 c 2,161,-1
+ 415 129 l 2,162,163
+ 427 129 427 129 432 119 c 0,164,165
+ 473 28 473 28 476 19 c 0,166,167
+ 478 13 478 13 473 8 c 0,168,169
+ 469 4 469 4 463 3 c 0,170,171
+ 462 3 462 3 459 3 c 128,-1,172
+ 456 3 456 3 456 3 c 2,173,-1
+ 442 2 l 1,174,-1
+ 179 2 l 2,175,176
+ 158 2 158 2 141 14 c 0,177,178
+ 133 19 133 19 129 23 c 0,179,180
+ 122 30 122 30 120 33 c 128,-1,181
+ 118 36 118 36 120 42 c 0,157,158
+89 376 m 0,182,183
+ 91 378 91 378 97 380 c 128,-1,184
+ 103 382 103 382 111 383 c 0,185,186
+ 120 383 120 383 128 379 c 0,187,188
+ 135 375 135 375 161.5 359.5 c 128,-1,189
+ 188 344 188 344 197 339 c 0,190,191
+ 205 335 205 335 205 326 c 2,192,-1
+ 205 151 l 2,193,194
+ 205 138 205 138 196 130 c 0,195,196
+ 186 120 186 120 155 89.5 c 128,-1,197
+ 124 59 124 59 120 55 c 0,198,199
+ 116 50 116 50 109 50 c 0,200,201
+ 99 50 99 50 95 58 c 256,202,203
+ 90 66 90 66 90 67 c 0,204,205
+ 76 92 76 92 76 120 c 2,206,-1
+ 76 354 l 2,207,208
+ 76 365 76 365 84 371 c 0,209,210
+ 86 374 86 374 89 376 c 0,182,183
+EndSplineSet
+Validated: 1
+EndChar
+
+StartChar: p
+Encoding: 112 112 40
+Width: 640
Flags: W
LayerCount: 2
Fore
SplineSet
-451 403 m 4,0,1
- 447 396 447 396 440 396 c 6,2,-1
- 354 396 l 6,3,4
- 347 396 347 396 343 403 c 4,5,6
- 332 421 332 421 323 437 c 4,7,8
- 318 446 318 446 318 457 c 132,-1,9
- 318 468 318 468 323 477 c 4,10,11
- 371 557 371 557 384 578 c 4,12,13
- 388 585 388 585 397 585 c 132,-1,14
- 406 585 406 585 410 578 c 4,15,16
- 417 567 417 567 440 528.5 c 132,-1,17
- 463 490 463 490 471 477 c 4,18,19
- 477 468 477 468 477 457.5 c 132,-1,20
- 477 447 477 447 471 437 c 4,21,22
- 458 415 458 415 451 403 c 4,0,1
-264 366 m 4,23,24
- 282 377 282 377 304 377 c 6,25,-1
- 524 377 l 6,26,27
- 531 377 531 377 537 372 c 4,28,29
- 552 355 552 355 584 321 c 4,30,31
- 593 311 593 311 593 298 c 4,32,33
- 593 284 593 284 583 274 c 4,34,35
- 558 248 558 248 539 230 c 4,36,37
- 532 222 532 222 520 222 c 6,38,-1
- 301 222 l 6,39,40
- 282 222 282 222 266 231 c 4,41,42
- 261 234 261 234 190 275 c 4,43,44
- 177 282 177 282 177 298 c 4,45,46
- 177 313 177 313 190 321 c 4,47,48
- 197 325 197 325 224 341.5 c 132,-1,49
- 251 358 251 358 264 366 c 4,23,24
-451 196 m 4,50,51
- 458 184 458 184 471 162 c 4,52,53
- 477 152 477 152 477 141.5 c 132,-1,54
- 477 131 477 131 471 122 c 4,55,56
- 427 48 427 48 410 21 c 4,57,58
- 406 14 406 14 397 14 c 132,-1,59
- 388 14 388 14 384 21 c 4,60,61
- 377 33 377 33 354 71 c 132,-1,62
- 331 109 331 109 323 122 c 4,63,64
- 318 131 318 131 318 142 c 132,-1,65
- 318 153 318 153 323 162 c 4,66,67
- 339 189 339 189 343 196 c 4,68,69
- 347 202 347 202 354 202 c 6,70,-1
- 440 202 l 6,71,72
- 447 202 447 202 451 196 c 4,50,51
-695 319 m 0,73,74
- 685 308 685 308 666 307 c 0,75,76
- 665 307 665 307 659 306.5 c 128,-1,77
- 653 306 653 306 649 306 c 0,78,79
- 627 306 627 306 611 317 c 0,80,81
- 592 329 592 329 548 382 c 0,82,83
- 541 390 541 390 541 401 c 0,84,85
- 541 430 541 430 541 453 c 0,86,87
- 541 481 541 481 541 502.5 c 128,-1,88
- 541 524 541 524 541 551.5 c 128,-1,89
- 541 579 541 579 541 612 c 0,90,91
- 541 625 541 625 547 637 c 0,92,93
- 580 710 580 710 602 758 c 0,94,95
- 608 771 608 771 623 771 c 0,96,97
- 631 771 631 771 638 767 c 0,98,99
- 655 753 655 753 668 735 c 0,100,101
- 682 716 682 716 692 694 c 0,102,103
- 703 669 703 669 703 641 c 2,104,-1
- 703 346 l 2,105,106
- 703 339 703 339 702 332 c 0,107,108
- 700 324 700 324 695 319 c 0,73,74
-114 325 m 0,109,110
- 110 327 110 327 107 330 c 0,111,112
- 97 339 97 339 97 352 c 2,113,-1
- 97 645 l 2,114,115
- 97 681 97 681 115 711 c 0,116,117
- 115 712 115 712 121 723 c 0,118,119
- 127 733 127 733 139 733 c 0,120,121
- 147 733 147 733 152 727 c 0,122,123
- 158 722 158 722 196 684 c 128,-1,124
- 234 646 234 646 247 633 c 0,125,126
- 259 621 259 621 259 605 c 2,127,-1
- 259 388 l 2,128,129
- 259 377 259 377 249 372 c 0,130,131
- 238 365 238 365 204.5 346 c 128,-1,132
- 171 327 171 327 162 322 c 0,133,134
- 152 317 152 317 141 317 c 0,135,136
- 132 317 132 317 124 320 c 0,137,138
- 117 323 117 323 114 325 c 0,109,110
-153 743 m 0,139,140
- 151 751 151 751 153 754.5 c 128,-1,141
- 155 758 155 758 164 767 c 0,142,143
- 169 772 169 772 179 778 c 0,144,145
- 200 793 200 793 226 793 c 2,146,-1
- 555 793 l 1,147,-1
- 572 792 l 2,148,149
- 573 792 573 792 576 791.5 c 128,-1,150
- 579 791 579 791 581 791 c 0,151,152
- 589 790 589 790 594 785 c 0,153,154
- 600 779 600 779 598 771 c 0,155,156
- 593 761 593 761 542 647 c 0,157,158
- 536 633 536 633 521 633 c 2,159,-1
- 272 633 l 2,160,161
- 260 633 260 633 252 642 c 0,162,163
- 157 735 157 735 153 743 c 0,139,140
-695 278 m 0,164,165
- 700 273 700 273 702 265 c 0,166,167
- 703 258 703 258 703 251 c 2,168,-1
- 703 -45 l 2,169,170
- 703 -72 703 -72 692 -97 c 0,171,172
- 682 -119 682 -119 668 -138 c 0,173,174
- 655 -156 655 -156 638 -170 c 0,175,176
- 631 -175 631 -175 623 -175 c 0,177,178
- 608 -175 608 -175 602 -161 c 0,179,180
- 600 -157 600 -157 577.5 -107.5 c 128,-1,181
- 555 -58 555 -58 547 -40 c 0,182,183
- 541 -28 541 -28 541 -15 c 0,184,185
- 541 18 541 18 541 45.5 c 128,-1,186
- 541 73 541 73 541 94.5 c 128,-1,187
- 541 116 541 116 541 144 c 0,188,189
- 541 167 541 167 541 196 c 0,190,191
- 541 206 541 206 548 214 c 0,192,193
- 592 268 592 268 611 280 c 0,194,195
- 627 291 627 291 649 291 c 0,196,197
- 653 291 653 291 659 290.5 c 128,-1,198
- 665 290 665 290 666 290 c 0,199,200
- 685 289 685 289 695 278 c 0,164,165
-153 -143 m 0,201,202
- 157 -135 157 -135 252 -42 c 0,203,204
- 260 -34 260 -34 272 -34 c 2,205,-1
- 521 -34 l 2,206,207
- 536 -34 536 -34 542 -47 c 0,208,209
- 593 -161 593 -161 598 -172 c 0,210,211
- 600 -179 600 -179 594 -185 c 0,212,213
- 589 -190 589 -190 581 -191 c 0,214,215
- 580 -191 580 -191 576.5 -191.5 c 128,-1,216
- 573 -192 573 -192 572 -192 c 2,217,-1
- 555 -193 l 1,218,-1
- 226 -193 l 2,219,220
- 200 -193 200 -193 179 -178 c 0,221,222
- 169 -172 169 -172 164 -167 c 0,223,224
- 155 -158 155 -158 153 -154.5 c 128,-1,225
- 151 -151 151 -151 153 -143 c 0,201,202
-114 275 m 0,226,227
- 117 277 117 277 124 280 c 0,228,229
- 132 283 132 283 141 283 c 0,230,231
- 152 283 152 283 162 278 c 0,232,233
- 171 273 171 273 204.5 254 c 128,-1,234
- 238 235 238 235 249 228 c 0,235,236
- 259 223 259 223 259 212 c 2,237,-1
- 259 -6 l 2,238,239
- 259 -22 259 -22 247 -33 c 0,240,241
- 234 -46 234 -46 196 -84 c 128,-1,242
- 158 -122 158 -122 152 -127 c 0,243,244
- 147 -133 147 -133 139 -133 c 0,245,246
- 127 -133 127 -133 121 -123 c 256,247,248
- 115 -113 115 -113 115 -112 c 0,249,250
- 97 -81 97 -81 97 -45 c 2,251,-1
- 97 247 l 2,252,253
- 97 261 97 261 107 269 c 0,254,255
- 110 272 110 272 114 275 c 0,226,227
+209 449 m 0,0,1
+ 224 458 224 458 241 458 c 2,2,-1
+ 417 458 l 2,3,4
+ 425 458 425 458 428 454 c 0,5,6
+ 440 440 440 440 465 413 c 0,7,8
+ 471 406 471 406 472 395 c 128,-1,9
+ 473 384 473 384 464 375 c 0,10,11
+ 446 358 446 358 429 340 c 0,12,13
+ 423 334 423 334 414 334 c 2,14,-1
+ 239 334 l 2,15,16
+ 225 334 225 334 211 341 c 0,17,18
+ 195 349 195 349 150 376 c 0,19,20
+ 141 381 141 381 140 395 c 0,21,22
+ 139 406 139 406 150 413 c 0,23,24
+ 156 416 156 416 177.5 429.5 c 128,-1,25
+ 199 443 199 443 209 449 c 0,0,1
+463 -4 m 0,26,27
+ 483 -4 483 -4 495 -13 c 2,28,-1
+ 588 -82 l 2,29,30
+ 593 -86 593 -86 595 -91 c 0,31,32
+ 599 -109 599 -109 605 -145 c 0,33,34
+ 607 -156 607 -156 602 -165 c 0,35,36
+ 596 -173 596 -173 585 -177 c 0,37,38
+ 576 -180 576 -180 532 -187 c 0,39,40
+ 525 -188 525 -188 515 -181 c 2,41,-1
+ 428 -118 l 2,42,43
+ 412 -106 412 -106 408 -97 c 0,44,45
+ 380 -46 380 -46 374 -35 c 0,46,47
+ 369 -24 369 -24 375.5 -14 c 128,-1,48
+ 382 -4 382 -4 394 -4 c 0,49,50
+ 400 -4 400 -4 425 -4 c 0,51,52
+ 451 -4 451 -4 463 -4 c 0,26,27
+554 411 m 0,53,54
+ 546 402 546 402 531 402 c 0,55,56
+ 530 402 530 402 525 401.5 c 128,-1,57
+ 520 401 520 401 517 401 c 0,58,59
+ 499 401 499 401 487 410 c 0,60,61
+ 472 420 472 420 436 462 c 0,62,63
+ 430 468 430 468 431 477 c 0,64,65
+ 431 500 431 500 431 519 c 0,66,67
+ 431 541 431 541 431 558 c 128,-1,68
+ 431 575 431 575 431 597 c 128,-1,69
+ 431 619 431 619 431 646 c 0,70,71
+ 431 656 431 656 436 666 c 0,72,73
+ 462 724 462 724 480 763 c 0,74,75
+ 485 773 485 773 496 773 c 0,76,77
+ 502 773 502 773 508 770 c 0,78,79
+ 520 761 520 761 532 744 c 0,80,81
+ 546 726 546 726 552 711 c 0,82,83
+ 560 693 560 693 560 673 c 0,84,85
+ 560 671 560 671 560 669 c 2,86,-1
+ 560 433 l 2,87,88
+ 560 427 560 427 560 422 c 0,89,90
+ 558 415 558 415 554 411 c 0,53,54
+89 416 m 0,91,92
+ 86 418 86 418 84 420 c 0,93,94
+ 76 427 76 427 76 438 c 2,95,-1
+ 76 672 l 2,96,97
+ 76 701 76 701 90 725 c 0,98,99
+ 90 726 90 726 95 735 c 0,100,101
+ 100 743 100 743 109 743 c 0,102,103
+ 115 743 115 743 120 738 c 0,104,105
+ 125 734 125 734 155 703.5 c 128,-1,106
+ 185 673 185 673 196 663 c 0,107,108
+ 206 653 206 653 205 640 c 2,109,-1
+ 205 467 l 2,110,111
+ 205 458 205 458 197 454 c 0,112,113
+ 188 448 188 448 161.5 433 c 128,-1,114
+ 135 418 135 418 128 414 c 0,115,116
+ 120 410 120 410 111 410 c 0,117,118
+ 104 410 104 410 97 412 c 0,119,120
+ 91 414 91 414 89 416 c 0,91,92
+120 751 m 0,121,122
+ 118 757 118 757 120 760 c 128,-1,123
+ 122 763 122 763 129 770 c 0,124,125
+ 133 774 133 774 141 779 c 0,126,127
+ 158 791 158 791 179 791 c 2,128,-1
+ 442 791 l 1,129,-1
+ 456 790 l 2,130,131
+ 457 790 457 790 459 789.5 c 128,-1,132
+ 461 789 461 789 463 789 c 0,133,134
+ 469 788 469 788 473 784 c 0,135,136
+ 478 779 478 779 476 773 c 0,137,138
+ 472 765 472 765 432 674 c 0,139,140
+ 427 663 427 663 415 663 c 2,141,-1
+ 216 663 l 2,142,143
+ 206 663 206 663 200 670 c 0,144,145
+ 123 745 123 745 120 751 c 0,121,122
+554 379 m 0,146,147
+ 558 375 558 375 560 368 c 0,148,149
+ 561 362 561 362 560 357 c 2,150,-1
+ 560 120 l 2,151,152
+ 560 98 560 98 552 79 c 0,153,154
+ 544 61 544 61 532 46 c 0,155,156
+ 522 32 522 32 508 20 c 0,157,158
+ 502 16 502 16 496 16 c 0,159,160
+ 484 16 484 16 480 27 c 0,161,162
+ 478 30 478 30 460 70 c 128,-1,163
+ 442 110 442 110 436 124 c 0,164,165
+ 431 134 431 134 431 144 c 0,166,167
+ 431 170 431 170 431 192.5 c 128,-1,168
+ 431 215 431 215 431 232 c 128,-1,169
+ 431 249 431 249 431 271 c 0,170,171
+ 431 289 431 289 431 313 c 0,172,173
+ 431 321 431 321 436 327 c 0,174,175
+ 471 370 471 370 487 380 c 0,176,177
+ 500 389 500 389 517 389 c 0,178,179
+ 520 389 520 389 525 388.5 c 128,-1,180
+ 530 388 530 388 531 388 c 0,181,182
+ 546 388 546 388 554 379 c 0,146,147
+120 42 m 0,183,184
+ 123 48 123 48 200 123 c 0,185,186
+ 206 129 206 129 216 129 c 2,187,-1
+ 415 129 l 2,188,189
+ 427 129 427 129 432 119 c 0,190,191
+ 473 28 473 28 476 19 c 0,192,193
+ 478 13 478 13 473 8 c 0,194,195
+ 469 4 469 4 463 3 c 0,196,197
+ 462 3 462 3 459 3 c 128,-1,198
+ 456 3 456 3 456 3 c 2,199,-1
+ 442 2 l 1,200,-1
+ 179 2 l 2,201,202
+ 158 2 158 2 141 14 c 0,203,204
+ 133 19 133 19 129 23 c 0,205,206
+ 122 30 122 30 120 33 c 128,-1,207
+ 118 36 118 36 120 42 c 0,183,184
+89 376 m 0,208,209
+ 91 378 91 378 97 380 c 128,-1,210
+ 103 382 103 382 111 383 c 0,211,212
+ 120 383 120 383 128 379 c 0,213,214
+ 135 375 135 375 161.5 359.5 c 128,-1,215
+ 188 344 188 344 197 339 c 0,216,217
+ 205 335 205 335 205 326 c 2,218,-1
+ 205 151 l 2,219,220
+ 205 138 205 138 196 130 c 0,221,222
+ 186 120 186 120 155 89.5 c 128,-1,223
+ 124 59 124 59 120 55 c 0,224,225
+ 116 50 116 50 109 50 c 0,226,227
+ 99 50 99 50 95 58 c 256,228,229
+ 90 66 90 66 90 67 c 0,230,231
+ 76 92 76 92 76 120 c 2,232,-1
+ 76 354 l 2,233,234
+ 76 365 76 365 84 371 c 0,235,236
+ 86 374 86 374 89 376 c 0,208,209
EndSplineSet
Validated: 2049
EndChar
diff --git a/fbw-a380x/src/systems/instruments/src/FCU/Components/Altitude.tsx b/fbw-a380x/src/systems/instruments/src/FCU/Components/Altitude.tsx
index 35829716f51..dc0371d74f4 100644
--- a/fbw-a380x/src/systems/instruments/src/FCU/Components/Altitude.tsx
+++ b/fbw-a380x/src/systems/instruments/src/FCU/Components/Altitude.tsx
@@ -35,7 +35,7 @@ export class Altitude extends DisplayComponent {
ALT
-
+
{this.altText}
diff --git a/fbw-a380x/src/systems/instruments/src/FCU/Components/Baro.tsx b/fbw-a380x/src/systems/instruments/src/FCU/Components/Baro.tsx
index 363526576cd..787aa02fc86 100644
--- a/fbw-a380x/src/systems/instruments/src/FCU/Components/Baro.tsx
+++ b/fbw-a380x/src/systems/instruments/src/FCU/Components/Baro.tsx
@@ -66,9 +66,11 @@ export class Baro extends DisplayComponent {
);
private readonly preSelBaroText = MappedSubject.create(
- ([correction, isVisible, isLightTest]) => {
+ ([correction, isVisible, isLightTest, mode]) => {
if (isLightTest) {
- return '8.8.8.8';
+ return '8p88'; // p is used as a standin character for the Q test character
+ } else if (mode === 'QFE') {
+ return 'qfe';
} else if (isVisible) {
return correction < 100 ? correction.toFixed(2) : correction.toFixed(0).padStart(4, '0');
} else {
@@ -78,6 +80,7 @@ export class Baro extends DisplayComponent {
this.correction,
this.isPreSelVisible,
this.isLightTestActive,
+ this.mode,
);
onAfterRender(_node: VNode): void {
@@ -95,8 +98,8 @@ export class Baro extends DisplayComponent {
{
>
QNH
- {/* Removed QFE label as QFE systems are INOP */}
- {/*
- QFE
- */}
-
+
{this.preSelBaroText}
-
+
{this.baroText}
diff --git a/fbw-a380x/src/systems/instruments/src/FCU/Components/Heading.tsx b/fbw-a380x/src/systems/instruments/src/FCU/Components/Heading.tsx
index 68476f1c811..955d1172902 100644
--- a/fbw-a380x/src/systems/instruments/src/FCU/Components/Heading.tsx
+++ b/fbw-a380x/src/systems/instruments/src/FCU/Components/Heading.tsx
@@ -19,10 +19,10 @@ export class Heading extends DisplayComponent {
TRK
-
+
---
-
+
°
diff --git a/fbw-a380x/src/systems/instruments/src/FCU/Components/Speed.tsx b/fbw-a380x/src/systems/instruments/src/FCU/Components/Speed.tsx
index dcc76a8afe5..6f1872b087e 100644
--- a/fbw-a380x/src/systems/instruments/src/FCU/Components/Speed.tsx
+++ b/fbw-a380x/src/systems/instruments/src/FCU/Components/Speed.tsx
@@ -16,7 +16,7 @@ export class Speed extends DisplayComponent {
SPD
-
+
---
diff --git a/fbw-a380x/src/systems/instruments/src/FCU/Components/VerticalSpeed.tsx b/fbw-a380x/src/systems/instruments/src/FCU/Components/VerticalSpeed.tsx
index 402d2e5e74f..8b2e4ae9667 100644
--- a/fbw-a380x/src/systems/instruments/src/FCU/Components/VerticalSpeed.tsx
+++ b/fbw-a380x/src/systems/instruments/src/FCU/Components/VerticalSpeed.tsx
@@ -16,7 +16,7 @@ export class VerticalSpeed extends DisplayComponent {
V/S
-
+
-----
diff --git a/fbw-a380x/src/systems/instruments/src/FCU/style.scss b/fbw-a380x/src/systems/instruments/src/FCU/style.scss
index e3b7acb317d..7c2d2e43061 100644
--- a/fbw-a380x/src/systems/instruments/src/FCU/style.scss
+++ b/fbw-a380x/src/systems/instruments/src/FCU/style.scss
@@ -83,20 +83,21 @@ text.Label.Visible {
:root text.Value {
font-family: Digital;
- font-size:440px;
+ font-size:550px;
text-anchor: start;
fill: $display-colour;
letter-spacing: 0px;
}
:root .Baro text.Value {
- font-size: 400px;
+ font-size: 512px;
}
:root #PreSelBaroValue {
font-family: Digital;
text-anchor: end;
letter-spacing: 0px;
+ font-size: 275px;
}
:root line {
diff --git a/fbw-a380x/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx b/fbw-a380x/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx
index 6d001810ac1..47527dc1641 100644
--- a/fbw-a380x/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx
+++ b/fbw-a380x/src/systems/instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher.tsx
@@ -5,201 +5,18 @@
import { EventBus, SimVarDefinition, SimVarValueType, SimVarPublisher } from '@microsoft/msfs-sdk';
export type PseudoFwcSimvars = {
- acEssBus: boolean;
- ewdPotentiometer: number;
- autoThrustCommand1: number;
- autoThrustCommand2: number;
- autoThrustLimit: number;
- autoThrustLimitToga: number;
- thrustLimitType: number;
- autoThrustMode: number;
- autoThrustStatus: number;
- autoThrustTLA1: number;
- autoThrustTLA2: number;
- autoThrustWarningToga: boolean;
- packs1Supplying: boolean;
- packs2Supplying: boolean;
- engine1AntiIce: boolean;
- engine1EGT: number;
- engine1Fadec: boolean;
- engine1FF: number;
engine1Master: number;
- engine1N1: number;
- engine1N2: number;
- engine1ReverserTransit: boolean;
- engine1ReverserDeployed: boolean;
- engine1State: number;
- engine2AntiIce: boolean;
- engine2EGT: number;
- engine2Fadec: boolean;
- engine2FF: number;
engine2Master: number;
- engine2N1: number;
- engine2N2: number;
- engine2ReverserTransit: boolean;
- engine2ReverserDeployed: boolean;
- engine2State: number;
engine3Master: number;
engine4Master: number;
- wingAntiIce: boolean;
- apuBleedPressure: number;
- left1LandingGear: boolean;
- right1LandingGear: boolean;
- throttle1Position: number;
- throttle2Position: number;
- fwcFlightPhase: number;
- idleN1: number;
- flexTemp: number;
- satRaw: number;
- totalFuel: number;
- slatsFlapsStatusRaw: number;
- slatsPositionRaw: number;
- flapsPositionRaw: number;
- ewdLowerLeft1: number;
- ewdLowerLeft2: number;
- ewdLowerLeft3: number;
- ewdLowerLeft4: number;
- ewdLowerLeft5: number;
- ewdLowerLeft6: number;
- ewdLowerLeft7: number;
- ewdLowerRight1: number;
- ewdLowerRight2: number;
- ewdLowerRight3: number;
- ewdLowerRight4: number;
- ewdLowerRight5: number;
- ewdLowerRight6: number;
- ewdLowerRight7: number;
};
-export enum PseudoFwcVars {
- acEssBus = 'L:A32NX_ELEC_AC_ESS_BUS_IS_POWERED',
- ewdPotentiometer = 'LIGHT POTENTIOMETER:92',
- autoThrustCommand1 = 'L:A32NX_AUTOTHRUST_N1_COMMANDED:1',
- autoThrustCommand2 = 'L:A32NX_AUTOTHRUST_N1_COMMANDED:2',
- autoThrustLimit = 'L:A32NX_AUTOTHRUST_THRUST_LIMIT',
- autoThrustLimitToga = 'L:A32NX_AUTOTHRUST_THRUST_LIMIT_TOGA',
- thrustLimitType = 'L:A32NX_AUTOTHRUST_THRUST_LIMIT_TYPE',
- autoThrustMode = 'L:A32NX_AUTOTHRUST_MODE',
- autoThrustStatus = 'L:A32NX_AUTOTHRUST_STATUS',
- autoThrustTLA1 = 'L:A32NX_AUTOTHRUST_TLA_N1:1',
- autoThrustTLA2 = 'L:A32NX_AUTOTHRUST_TLA_N1:2',
- autoThrustWarningToga = 'L:A32NX_AUTOTHRUST_THRUST_LEVER_WARNING_TOGA',
- packs1Supplying = 'L:A32NX_COND_PACK_FLOW_VALVE_1_IS_OPEN',
- packs2Supplying = 'L:A32NX_COND_PACK_FLOW_VALVE_2_IS_OPEN',
- engine1AntiIce = 'L:XMLVAR_Momentary_PUSH_OVHD_ANTIICE_ENG1_Pressed',
- engine1EGT = 'L:A32NX_ENGINE_EGT:1',
- engine1Fadec = 'L:A32NX_FADEC_POWERED_ENG1',
- engine1FF = 'L:A32NX_ENGINE_FF:1',
- engine1N1 = 'L:A32NX_ENGINE_N1:1',
- engine1N2 = 'L:A32NX_ENGINE_N2:1',
- engine1ReverserTransit = 'L:A32NX_REVERSER_1_DEPLOYING',
- engine1ReverserDeployed = 'L:A32NX_REVERSER_1_DEPLOYED',
- engine1State = 'L:A32NX_ENGINE_STATE:1',
- engine2AntiIce = 'L:XMLVAR_Momentary_PUSH_OVHD_ANTIICE_ENG2_Pressed',
- engine2EGT = 'L:A32NX_ENGINE_EGT:2',
- engine2Fadec = 'L:A32NX_FADEC_POWERED_ENG2',
- engine2FF = 'L:A32NX_ENGINE_FF:2',
- engine2N1 = 'L:A32NX_ENGINE_N1:2',
- engine2N2 = 'L:A32NX_ENGINE_N2:2',
- engine2ReverserTransit = 'L:A32NX_REVERSER_2_DEPLOYING',
- engine2ReverserDeployed = 'L:A32NX_REVERSER_2_DEPLOYED',
- engine2State = 'L:A32NX_ENGINE_STATE:2',
- wingAntiIce = 'L:A32NX_PNEU_WING_ANTI_ICE_SYSTEM_SELECTED',
- apuBleedPressure = 'L:APU_BLEED_PRESSURE',
- left1LandingGear = 'L:A32NX_LGCIU_1_LEFT_GEAR_COMPRESSED',
- right1LandingGear = 'L:A32NX_LGCIU_1_RIGHT_GEAR_COMPRESSED',
- throttle1Position = 'L:XMLVAR_Throttle1Position',
- throttle2Position = 'L:XMLVAR_Throttle2Position',
- fwcFlightPhase = 'L:A32NX_FWC_FLIGHT_PHASE',
- idleN1 = 'L:A32NX_ENGINE_IDLE_N1',
- flexTemp = 'L:AIRLINER_TO_FLEX_TEMP',
- satRaw = 'L:A32NX_ADIRS_ADR_1_STATIC_AIR_TEMPERATURE',
- totalFuel = 'FUEL TOTAL QUANTITY WEIGHT',
- slatsFlapsStatusRaw = 'L:A32NX_SFCC_SLAT_FLAP_SYSTEM_STATUS_WORD',
- slatsPositionRaw = 'L:A32NX_SFCC_SLAT_ACTUAL_POSITION_WORD',
- flapsPositionRaw = 'L:A32NX_SFCC_FLAP_ACTUAL_POSITION_WORD',
- ewdLowerLeft1 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_1',
- ewdLowerLeft2 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_2',
- ewdLowerLeft3 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_3',
- ewdLowerLeft4 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_4',
- ewdLowerLeft5 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_5',
- ewdLowerLeft6 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_6',
- ewdLowerLeft7 = 'L:A32NX_Ewd_LOWER_LEFT_LINE_7',
- ewdLowerRight1 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_1',
- ewdLowerRight2 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_2',
- ewdLowerRight3 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_3',
- ewdLowerRight4 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_4',
- ewdLowerRight5 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_5',
- ewdLowerRight6 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_6',
- ewdLowerRight7 = 'L:A32NX_Ewd_LOWER_RIGHT_LINE_7',
-}
-
export class PseudoFwcSimvarPublisher extends SimVarPublisher {
private static simvars = new Map([
- ['acEssBus', { name: PseudoFwcVars.acEssBus, type: SimVarValueType.Bool }],
- ['ewdPotentiometer', { name: PseudoFwcVars.ewdPotentiometer, type: SimVarValueType.Number }],
- ['autoThrustCommand1', { name: PseudoFwcVars.autoThrustCommand1, type: SimVarValueType.Number }],
- ['autoThrustCommand2', { name: PseudoFwcVars.autoThrustCommand2, type: SimVarValueType.Number }],
- ['autoThrustLimit', { name: PseudoFwcVars.autoThrustLimit, type: SimVarValueType.Number }],
- ['autoThrustLimitToga', { name: PseudoFwcVars.autoThrustLimitToga, type: SimVarValueType.Number }],
- ['thrustLimitType', { name: PseudoFwcVars.thrustLimitType, type: SimVarValueType.Enum }],
- ['autoThrustMode', { name: PseudoFwcVars.autoThrustMode, type: SimVarValueType.Enum }],
- ['autoThrustStatus', { name: PseudoFwcVars.autoThrustStatus, type: SimVarValueType.Enum }],
- ['autoThrustTLA1', { name: PseudoFwcVars.autoThrustTLA1, type: SimVarValueType.Number }],
- ['autoThrustTLA2', { name: PseudoFwcVars.autoThrustTLA2, type: SimVarValueType.Number }],
- ['autoThrustWarningToga', { name: PseudoFwcVars.autoThrustWarningToga, type: SimVarValueType.Bool }],
- ['packs1Supplying', { name: PseudoFwcVars.packs1Supplying, type: SimVarValueType.Bool }],
- ['packs2Supplying', { name: PseudoFwcVars.packs2Supplying, type: SimVarValueType.Bool }],
- ['engine1AntiIce', { name: PseudoFwcVars.engine1AntiIce, type: SimVarValueType.Bool }],
- ['engine1EGT', { name: PseudoFwcVars.engine1EGT, type: SimVarValueType.Number }],
- ['engine1Fadec', { name: PseudoFwcVars.engine1Fadec, type: SimVarValueType.Bool }],
['engine1Master', { name: 'A:FUELSYSTEM VALVE SWITCH:1', type: SimVarValueType.Bool }],
- ['engine1FF', { name: PseudoFwcVars.engine1FF, type: SimVarValueType.Number }],
- ['engine1N1', { name: PseudoFwcVars.engine1N1, type: SimVarValueType.Number }],
- ['engine1N2', { name: PseudoFwcVars.engine1N2, type: SimVarValueType.Number }],
- ['engine1ReverserTransit', { name: PseudoFwcVars.engine1ReverserTransit, type: SimVarValueType.Bool }],
- ['engine1ReverserDeployed', { name: PseudoFwcVars.engine1ReverserDeployed, type: SimVarValueType.Bool }],
- ['engine1State', { name: PseudoFwcVars.engine1State, type: SimVarValueType.Enum }],
- ['engine2AntiIce', { name: PseudoFwcVars.engine2AntiIce, type: SimVarValueType.Bool }],
- ['engine2EGT', { name: PseudoFwcVars.engine2EGT, type: SimVarValueType.Number }],
- ['engine2Fadec', { name: PseudoFwcVars.engine2Fadec, type: SimVarValueType.Bool }],
- ['engine2FF', { name: PseudoFwcVars.engine2FF, type: SimVarValueType.Number }],
['engine2Master', { name: 'A:FUELSYSTEM VALVE SWITCH:2', type: SimVarValueType.Bool }],
- ['engine2N1', { name: PseudoFwcVars.engine2N1, type: SimVarValueType.Number }],
- ['engine2N2', { name: PseudoFwcVars.engine2N2, type: SimVarValueType.Number }],
- ['engine2ReverserTransit', { name: PseudoFwcVars.engine2ReverserTransit, type: SimVarValueType.Bool }],
- ['engine2ReverserDeployed', { name: PseudoFwcVars.engine2ReverserDeployed, type: SimVarValueType.Bool }],
- ['engine2State', { name: PseudoFwcVars.engine2State, type: SimVarValueType.Enum }],
['engine3Master', { name: 'A:FUELSYSTEM VALVE SWITCH:3', type: SimVarValueType.Bool }],
['engine4Master', { name: 'A:FUELSYSTEM VALVE SWITCH:4', type: SimVarValueType.Bool }],
- ['wingAntiIce', { name: PseudoFwcVars.wingAntiIce, type: SimVarValueType.Bool }],
- ['apuBleedPressure', { name: PseudoFwcVars.apuBleedPressure, type: SimVarValueType.PSI }],
- ['left1LandingGear', { name: PseudoFwcVars.left1LandingGear, type: SimVarValueType.Bool }],
- ['right1LandingGear', { name: PseudoFwcVars.right1LandingGear, type: SimVarValueType.Bool }],
- ['throttle1Position', { name: PseudoFwcVars.throttle1Position, type: SimVarValueType.Number }],
- ['throttle2Position', { name: PseudoFwcVars.throttle2Position, type: SimVarValueType.Number }],
- ['fwcFlightPhase', { name: PseudoFwcVars.fwcFlightPhase, type: SimVarValueType.Enum }],
- ['idleN1', { name: PseudoFwcVars.idleN1, type: SimVarValueType.Number }],
- ['flexTemp', { name: PseudoFwcVars.flexTemp, type: SimVarValueType.Number }],
- ['satRaw', { name: PseudoFwcVars.satRaw, type: SimVarValueType.Number }],
- ['totalFuel', { name: PseudoFwcVars.totalFuel, type: SimVarValueType.Number }],
- ['slatsFlapsStatusRaw', { name: PseudoFwcVars.slatsFlapsStatusRaw, type: SimVarValueType.Number }],
- ['slatsPositionRaw', { name: PseudoFwcVars.slatsPositionRaw, type: SimVarValueType.Number }],
- ['flapsPositionRaw', { name: PseudoFwcVars.flapsPositionRaw, type: SimVarValueType.Number }],
- ['ewdLowerLeft1', { name: PseudoFwcVars.ewdLowerLeft1, type: SimVarValueType.Number }],
- ['ewdLowerLeft2', { name: PseudoFwcVars.ewdLowerLeft2, type: SimVarValueType.Number }],
- ['ewdLowerLeft3', { name: PseudoFwcVars.ewdLowerLeft3, type: SimVarValueType.Number }],
- ['ewdLowerLeft4', { name: PseudoFwcVars.ewdLowerLeft4, type: SimVarValueType.Number }],
- ['ewdLowerLeft5', { name: PseudoFwcVars.ewdLowerLeft5, type: SimVarValueType.Number }],
- ['ewdLowerLeft6', { name: PseudoFwcVars.ewdLowerLeft6, type: SimVarValueType.Number }],
- ['ewdLowerLeft7', { name: PseudoFwcVars.ewdLowerLeft7, type: SimVarValueType.Number }],
- ['ewdLowerRight1', { name: PseudoFwcVars.ewdLowerRight1, type: SimVarValueType.Number }],
- ['ewdLowerRight2', { name: PseudoFwcVars.ewdLowerRight2, type: SimVarValueType.Number }],
- ['ewdLowerRight3', { name: PseudoFwcVars.ewdLowerRight3, type: SimVarValueType.Number }],
- ['ewdLowerRight4', { name: PseudoFwcVars.ewdLowerRight4, type: SimVarValueType.Number }],
- ['ewdLowerRight5', { name: PseudoFwcVars.ewdLowerRight5, type: SimVarValueType.Number }],
- ['ewdLowerRight6', { name: PseudoFwcVars.ewdLowerRight6, type: SimVarValueType.Number }],
- ['ewdLowerRight7', { name: PseudoFwcVars.ewdLowerRight7, type: SimVarValueType.Number }],
]);
public constructor(bus: EventBus) {
diff --git a/fbw-a380x/src/systems/instruments/src/ND/instrument.tsx b/fbw-a380x/src/systems/instruments/src/ND/instrument.tsx
index 286a01720a1..e3534d83a36 100644
--- a/fbw-a380x/src/systems/instruments/src/ND/instrument.tsx
+++ b/fbw-a380x/src/systems/instruments/src/ND/instrument.tsx
@@ -244,7 +244,7 @@ class NDInstrument implements FsInstrument {
diff --git a/fbw-a380x/src/systems/instruments/src/PFD/PFD.tsx b/fbw-a380x/src/systems/instruments/src/PFD/PFD.tsx
index 945922d2174..385b8be4864 100644
--- a/fbw-a380x/src/systems/instruments/src/PFD/PFD.tsx
+++ b/fbw-a380x/src/systems/instruments/src/PFD/PFD.tsx
@@ -175,7 +175,7 @@ export class PFDComponent extends DisplayComponent {
return (
diff --git a/fbw-a380x/src/systems/instruments/src/PFD/shared/PFDSimvarPublisher.tsx b/fbw-a380x/src/systems/instruments/src/PFD/shared/PFDSimvarPublisher.tsx
index b289f68de72..de69cc28db8 100644
--- a/fbw-a380x/src/systems/instruments/src/PFD/shared/PFDSimvarPublisher.tsx
+++ b/fbw-a380x/src/systems/instruments/src/PFD/shared/PFDSimvarPublisher.tsx
@@ -194,7 +194,7 @@ export enum PFDVars {
fmaSpeedProtection = 'L:A32NX_FMA_SPEED_PROTECTION_MODE',
AThrMode = 'L:A32NX_AUTOTHRUST_MODE',
apVsSelected = 'L:A32NX_AUTOPILOT_VS_SELECTED',
- approachCapability = 'L:A32NX_ApproachCapability',
+ approachCapability = 'L:A32NX_APPROACH_CAPABILITY',
ap1Active = 'L:A32NX_AUTOPILOT_1_ACTIVE',
ap2Active = 'L:A32NX_AUTOPILOT_2_ACTIVE',
fmaVerticalArmed = 'L:A32NX_FMA_VERTICAL_ARMED',
diff --git a/fbw-a380x/src/systems/systems-host/index.ts b/fbw-a380x/src/systems/systems-host/index.ts
index 1d93a2a0f3d..b8ebac5a4de 100644
--- a/fbw-a380x/src/systems/systems-host/index.ts
+++ b/fbw-a380x/src/systems/systems-host/index.ts
@@ -11,9 +11,9 @@ import {
MappedSubject,
SubscribableMapFunctions,
WeightBalanceSimvarPublisher,
+ StallWarningPublisher,
} from '@microsoft/msfs-sdk';
import { LegacyGpws } from 'systems-host/systems/LegacyGpws';
-import { LegacyFwc } from 'systems-host/systems/LegacyFwc';
import { LegacyFuel } from 'systems-host/systems/LegacyFuel';
import { LegacySoundManager } from 'systems-host/systems/LegacySoundManager';
import { LegacyTcasComputer } from 'systems-host/systems/tcas/components/LegacyTcasComputer';
@@ -34,6 +34,7 @@ import { AtsuSystem } from 'systems-host/systems/atsu';
import { FwsCore } from 'systems-host/systems/FlightWarningSystem/FwsCore';
import { FuelSystemPublisher } from 'systems-host/systems/FuelSystemPublisher';
import { BrakeToVacateDistanceUpdater } from 'systems-host/systems/BrakeToVacateDistanceUpdater';
+import { PseudoFwcSimvarPublisher } from 'instruments/src/MsfsAvionicsCommon/providers/PseudoFwcPublisher';
class SystemsHost extends BaseInstrument {
private readonly bus = new ArincEventBus();
@@ -49,9 +50,6 @@ class SystemsHost extends BaseInstrument {
private readonly failuresConsumer = new FailuresConsumer('A32NX');
// TODO: Migrate PowerSupplyBusses, if needed
-
- private fwc: LegacyFwc;
-
private gpws: LegacyGpws;
private soundManager: LegacySoundManager;
@@ -97,6 +95,10 @@ class SystemsHost extends BaseInstrument {
private readonly fuelSystemPublisher = new FuelSystemPublisher(this.bus);
+ private readonly stallWarningPublisher = new StallWarningPublisher(this.bus, 0.9);
+
+ private readonly pseudoFwcPublisher = new PseudoFwcSimvarPublisher(this.bus);
+
private readonly fwsCore = new FwsCore(1, this.bus);
//FIXME add some deltatime functionality to backplane instruments so we dont have to pass SystemHost
@@ -129,12 +131,13 @@ class SystemsHost extends BaseInstrument {
this.backplane.addPublisher('BtvPublisher', this.btvPublisher);
this.backplane.addPublisher('Weightpublisher', this.weightAndBalancePublisher);
this.backplane.addPublisher('FuelPublisher', this.fuelSystemPublisher);
+ this.backplane.addPublisher('StallWarning', this.stallWarningPublisher);
+ this.backplane.addPublisher('PseudoFwc', this.pseudoFwcPublisher);
this.backplane.addInstrument('LegacyFuel', this.legacyFuel);
this.hEventPublisher = new HEventPublisher(this.bus);
- this.fwc = new LegacyFwc();
this.soundManager = new LegacySoundManager();
- this.gpws = new LegacyGpws(this.soundManager);
+ this.gpws = new LegacyGpws(this.bus, this.soundManager);
this.gpws.init();
this.fwsCore.init();
@@ -149,7 +152,6 @@ class SystemsHost extends BaseInstrument {
const dt = lastUpdateTime === undefined ? 0 : now - lastUpdateTime;
lastUpdateTime = now;
- this.fwc.update(dt);
this.soundManager.update(dt);
this.gpws.update(dt);
this.fwsCore.update(dt);
diff --git a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsAbnormalSensed.ts b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsAbnormalSensed.ts
index a049becf163..1cdd302a427 100644
--- a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsAbnormalSensed.ts
+++ b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsAbnormalSensed.ts
@@ -1434,7 +1434,7 @@ export class FwsAbnormalSensed {
flightPhaseInhib: [3, 4, 5, 10],
simVarIsActive: this.fws.autoThrustOffInvoluntary,
notActiveWhenFaults: [],
- whichItemsToShow: () => [true],
+ whichItemsToShow: () => [false],
whichItemsChecked: () => [SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_MODE_MESSAGE', 'number') !== 1],
failure: 2,
sysPage: -1,
diff --git a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsCore.ts b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsCore.ts
index 5e502ee1300..55330129573 100644
--- a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsCore.ts
+++ b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsCore.ts
@@ -56,6 +56,8 @@ import {
import { FwsAbnormalNonSensed } from 'systems-host/systems/FlightWarningSystem/FwsAbnormalNonSensed';
import { MfdSurvEvents } from 'instruments/src/MsfsAvionicsCommon/providers/MfdSurvPublisher';
import { Mle, Mmo, VfeF1, VfeF1F, VfeF2, VfeF3, VfeFF, Vle, Vmo } from '@shared/PerformanceConstants';
+import { FwsAuralVolume, FwsSoundManager } from 'systems-host/systems/FlightWarningSystem/FwsSoundManager';
+import { FwcFlightPhase, FwsFlightPhases } from 'systems-host/systems/FlightWarningSystem/FwsFlightPhases';
export function xor(a: boolean, b: boolean): boolean {
return !!((a ? 1 : 0) ^ (b ? 1 : 0));
@@ -77,30 +79,29 @@ export enum FwcAuralWarning {
CavalryCharge,
}
-export enum FwcAuralVolume {
- Full, // 0 dB
- Attenuated, // -6dB
- Silent, // -200 dB
-}
-
export class FwsCore {
public readonly sub = this.bus.getSubscriber<
PseudoFwcSimvars & StallWarningEvents & MfdSurvEvents & FuelSystemEvents & KeyEvents
>();
public readonly vhfSub = this.bus.getSubscriber();
- private fwsUpdateThrottler = new UpdateThrottler(125); // has to be > 100 due to pulse nodes
+ private readonly fwsUpdateThrottler = new UpdateThrottler(125); // has to be > 100 due to pulse nodes
private keyEventManager: KeyEventManager;
+ private readonly startupTimer = new DebounceTimer();
+
+ private readonly startupCompleted = Subject.create(false);
+
+ public readonly soundManager = new FwsSoundManager(this.bus, this.startupCompleted);
+
+ private readonly flightPhases = new FwsFlightPhases(this);
+
/** Time to inhibit master warnings and cautions during startup in ms */
private static readonly FWC_STARTUP_TIME = 5000;
/** Time to inhibit SCs after one is trigger in ms */
- private static readonly AURAL_SC_INHIBIT_TIME = 5000;
-
- /** The time to play the single chime sound in ms */
- private static readonly AURAL_SC_PLAY_TIME = 500;
+ private static readonly AURAL_SC_INHIBIT_TIME = 2000;
private static readonly EWD_MESSAGE_LINES = 10;
@@ -215,9 +216,6 @@ export class FwsCore {
public readonly apDiscInputBuffer = new NXLogicMemoryNode(false);
/* PSEUDO FWC VARIABLES */
- private readonly startupTimer = new DebounceTimer();
-
- private readonly startupCompleted = Subject.create(false);
/** Keys/IDs of all failures currently active, irrespective they are already cleared or not */
public readonly allCurrentFailures: string[] = [];
@@ -263,8 +261,6 @@ export class FwsCore {
public readonly auralSingleChimePlayingTimer = new DebounceTimer();
- public readonly auralCavalryChargeActive = Subject.create(false);
-
public readonly masterWarning = Subject.create(false);
public readonly masterCaution = Subject.create(false);
@@ -286,21 +282,6 @@ export class FwsCore {
this.startupCompleted,
);
- public readonly auralCrcOutput = MappedSubject.create(
- ([auralCrc, startup]) => auralCrc && startup,
- this.auralCrcActive,
- this.startupCompleted,
- );
-
- public readonly auralCavalryChargeOutput = MappedSubject.create(
- ([auralCavCharge, auralCrc, startup]) => auralCavCharge && !auralCrc && startup,
- this.auralCavalryChargeActive,
- this.auralCrcOutput,
- this.startupCompleted,
- );
-
- public readonly fwsAuralVolume = Subject.create(FwcAuralVolume.Full);
-
public readonly ecamStsNormal = Subject.create(true);
public readonly ecamEwdShowStsIndication = Subject.create(false);
@@ -512,14 +493,17 @@ export class FwsCore {
/** 1.8s according to references, but was raised to 1.9s to allow for triple click to finish */
public readonly autoPilotInstinctiveDiscPressedTwiceInLast1p9Sec = new NXLogicTriggeredMonostableNode(1.9, true);
+ /** Prohibits that CRC can be cancelled before even hearing it */
+ public readonly autoPilotFirstCavalryStillWithinFirst0p3s = new NXLogicTriggeredMonostableNode(0.3, true);
+
public readonly autoPilotInstinctiveDiscPressedPulse = new NXLogicPulseNode(true);
/** Stay in first warning stage for 1.8s. Raised to 1.9s to allow for triple click to finish */
public readonly autoPilotOffVoluntaryEndAfter1p9s = new NXLogicTriggeredMonostableNode(1.9, true);
- public readonly autoPilotOffVoluntaryFirstCavalryChargeActive = new NXLogicTriggeredMonostableNode(0.8, true);
+ public readonly autoPilotOffVoluntaryFirstCavalryChargeActive = new NXLogicTriggeredMonostableNode(0.9, true);
- public readonly autoPilotOffSendTripleClickAfterFirstCavalryCharge = new NXLogicPulseNode(false);
+ public readonly autoPilotOffVoluntaryFirstCavalryChargeActivePulse = new NXLogicPulseNode(false);
public readonly autoPilotOffVoluntaryDiscPulse = new NXLogicPulseNode(true);
@@ -533,6 +517,14 @@ export class FwsCore {
public readonly autoPilotOffShowMemo = Subject.create(false);
+ public readonly approachCapability = Subject.create(0);
+
+ public readonly approachCapabilityDowngradeDebounce = new NXLogicTriggeredMonostableNode(1, true);
+
+ public readonly approachCapabilityDowngradeSuppress = new NXLogicTriggeredMonostableNode(3, true);
+
+ public readonly approachCapabilityDowngradeDebouncePulse = new NXLogicPulseNode(false);
+
public readonly autoThrustDisengagedInstantPulse = new NXLogicPulseNode(false);
public readonly autoThrustInstinctiveDiscPressed = new NXLogicTriggeredMonostableNode(1.5, true); // Save event for 1.5 sec
@@ -1063,7 +1055,7 @@ export class FwsCore {
/* 31 - FWS */
- public readonly fwcFlightPhase = Subject.create(-1);
+ public readonly flightPhase = Subject.create(null);
public readonly flightPhase128 = Subject.create(false);
@@ -1123,8 +1115,6 @@ export class FwsCore {
/** If one of the ADR's CAS is above V1 - 4kts, confirm for 0.3s */
public readonly v1SpeedConfirmNode = new NXLogicConfirmNode(0.3);
- public readonly v1CalloutOutput = Subject.create(false);
-
/* LANDING GEAR AND LIGHTS */
public readonly aircraftOnGround = Subject.create(false);
@@ -1205,6 +1195,8 @@ export class FwsCore {
public readonly autoBrakeOff = Subject.create(false);
+ public autoBrakeOffAuralTriggered = false;
+
public autoBrakeOffMemoInhibited = false;
/* NAVIGATION */
@@ -1253,6 +1245,8 @@ export class FwsCore {
this.fwsNumber === 2 ? this.airDataFoOn3 : this.airDataCaptOn3,
);
+ public readonly adrPressureAltitude = Subject.create(0);
+
public readonly ir1MaintWord = Arinc429Register.empty();
public readonly ir2MaintWord = Arinc429Register.empty();
public readonly ir3MaintWord = Arinc429Register.empty();
@@ -1624,22 +1618,14 @@ export class FwsCore {
});
this.toConfigNormal.sub((normal) => SimVar.SetSimVarValue('L:A32NX_TO_CONFIG_NORMAL', 'bool', normal));
- this.fwcFlightPhase.sub(() => this.flightPhaseEndedPulseNode.write(true, 0));
+ this.flightPhase.sub((fp) => {
+ SimVar.SetSimVarValue('L:A32NX_FWC_FLIGHT_PHASE', 'Enum', fp || 0);
+ if (fp !== null) {
+ this.flightPhaseEndedPulseNode.write(true, 0);
+ }
+ });
- this.auralCrcOutput.sub(
- (crc) => SimVar.SetSimVarValue('L:A32NX_FWC_CRC', 'bool', this.startupCompleted.get() ? crc : false),
- true,
- );
-
- this.auralCavalryChargeOutput.sub(
- (cc) =>
- SimVar.SetSimVarValue(
- 'L:A32NX_FWC_CAVALRY_CHARGE',
- SimVarValueType.Bool,
- this.startupCompleted.get() ? cc : false,
- ),
- true,
- );
+ this.auralCrcActive.sub((crc) => this.soundManager.handleSoundCondition('continuousRepetitiveChime', crc), true);
this.masterCautionOutput.sub((caution) => {
// Inhibit master warning/cautions until FWC startup has been completed
@@ -1651,13 +1637,6 @@ export class FwsCore {
SimVar.SetSimVarValue('L:A32NX_MASTER_WARNING', 'bool', warning);
}, true);
- this.fwsAuralVolume.sub((volume) => {
- // Inhibit master warning/cautions until FWC startup has been completed
- SimVar.SetSimVarValue('L:A32NX_FWS_AUDIO_VOLUME', SimVarValueType.Enum, volume);
- }, true);
-
- this.v1CalloutOutput.sub((c) => SimVar.SetSimVarValue('L:A32NX_AUDIO_V1_CALLOUT', SimVarValueType.Bool, c), true);
-
// L/G lever red arrow sinking outputs
this.lgLeverRedArrow.sub((on) => {
// TODO FWCs need to be powered...
@@ -1668,7 +1647,7 @@ export class FwsCore {
this.stallWarning.sub((v) => {
this.fwcOut126.setBitValue(17, v);
// set the sound on/off
- SimVar.SetSimVarValue('L:A32NX_AUDIO_STALL_WARNING', 'bool', v);
+ this.soundManager.handleSoundCondition('stall', v);
}, true);
this.aircraftOnGround.sub((v) => this.fwcOut126.setBitValue(28, v));
@@ -1881,6 +1860,12 @@ export class FwsCore {
// A380X hack: Inject healthy messages for some systems which are not yet implemented
this.healthInjector();
+ // Update flight phases
+ this.flightPhases.update(deltaTime);
+
+ // Play sounds
+ this.soundManager.onUpdate(deltaTime);
+
// Write pulse nodes for buffered inputs
this.toConfigPulseNode.write(this.toConfigInputBuffer.read(), deltaTime);
this.clrPulseNode.write(this.clearButtonInputBuffer.read(), deltaTime);
@@ -1895,24 +1880,24 @@ export class FwsCore {
// Inputs update
this.flightPhaseEndedPulseNode.write(false, deltaTime);
- this.fwcFlightPhase.set(SimVar.GetSimVarValue('L:A32NX_FWC_FLIGHT_PHASE', 'Enum'));
- const phase3 = this.fwcFlightPhase.get() === 3;
- const phase6 = this.fwcFlightPhase.get() === 6;
+ const phase3 = this.flightPhase.get() === 3;
+ const phase6 = this.flightPhase.get() === 6;
this.flightPhase3PulseNode.write(phase3, deltaTime);
// flight phase convenience vars
- this.flightPhase128.set([1, 2, 8].includes(this.fwcFlightPhase.get()));
- this.flightPhase23.set([2, 3].includes(this.fwcFlightPhase.get()));
- this.flightPhase345.set([3, 4, 5].includes(this.fwcFlightPhase.get()));
+ this.flightPhase128.set([1, 2, 8].includes(this.flightPhase.get()));
+ this.flightPhase23.set([2, 3].includes(this.flightPhase.get()));
+ this.flightPhase345.set([3, 4, 5].includes(this.flightPhase.get()));
this.flightPhase34567.set(
- this.flightPhase345.get() || this.fwcFlightPhase.get() === 6 || this.fwcFlightPhase.get() === 7,
+ this.flightPhase345.get() || this.flightPhase.get() === 6 || this.flightPhase.get() === 7,
);
- this.flightPhase1211.set([1, 2, 11].includes(this.fwcFlightPhase.get()));
- this.flightPhase89.set([8, 9].includes(this.fwcFlightPhase.get()));
- this.flightPhase910.set([9, 10].includes(this.fwcFlightPhase.get()));
- const flightPhase6789 = [6, 7, 8, 9].includes(this.fwcFlightPhase.get());
- const flightPhase112 = [1, 12].includes(this.fwcFlightPhase.get());
+ this.flightPhase1211.set([1, 2, 11].includes(this.flightPhase.get()));
+ this.flightPhase89.set([8, 9].includes(this.flightPhase.get()));
+ this.flightPhase910.set([9, 10].includes(this.flightPhase.get()));
+ const flightPhase6789 = [6, 7, 8, 9].includes(this.flightPhase.get());
+ const flightPhase112 = [1, 12].includes(this.flightPhase.get());
+ const flightPhase189 = [1, 8, 9].includes(this.flightPhase.get());
- this.phase815MinConfNode.write(this.fwcFlightPhase.get() === 8, deltaTime);
+ this.phase815MinConfNode.write(this.flightPhase.get() === 8, deltaTime);
this.phase112.set(flightPhase112);
// TO CONFIG button
@@ -2061,12 +2046,12 @@ export class FwsCore {
const yLoPressure = !yellowSysPressurised;
this.eng1Or2RunningAndPhaseConfirmationNode.write(
- this.engine1Running.get() || this.engine2Running.get() || ![1, 2, 11, 12].includes(this.fwcFlightPhase.get()),
+ this.engine1Running.get() || this.engine2Running.get() || ![1, 2, 11, 12].includes(this.flightPhase.get()),
deltaTime,
);
this.eng3Or4RunningAndPhaseConfirmationNode.write(
- this.engine3Running.get() || this.engine4Running.get() || ![1, 2, 11, 12].includes(this.fwcFlightPhase.get()),
+ this.engine3Running.get() || this.engine4Running.get() || ![1, 2, 11, 12].includes(this.flightPhase.get()),
deltaTime,
);
@@ -2147,7 +2132,7 @@ export class FwsCore {
!this.greenRsvLoAirPressure.get() &&
!this.greenRsvOverheat.get() &&
!this.greenAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng1APumpAuto.get(),
deltaTime,
);
@@ -2164,7 +2149,7 @@ export class FwsCore {
!this.greenRsvLoAirPressure.get() &&
!this.greenRsvOverheat.get() &&
!this.greenAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng1BPumpAuto.get(),
deltaTime,
);
@@ -2185,7 +2170,7 @@ export class FwsCore {
!this.greenRsvLoAirPressure.get() &&
!this.greenRsvOverheat.get() &&
!this.greenAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng2APumpAuto.get(),
deltaTime,
);
@@ -2203,7 +2188,7 @@ export class FwsCore {
!this.greenRsvLoAirPressure.get() &&
!this.greenRsvOverheat.get() &&
!this.greenAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng2BPumpAuto.get(),
deltaTime,
);
@@ -2223,7 +2208,7 @@ export class FwsCore {
!this.yellowRsvLoAirPressure.get() &&
!this.yellowRsvOverheat.get() &&
!this.yellowAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng3APumpAuto.get(),
deltaTime,
);
@@ -2244,7 +2229,7 @@ export class FwsCore {
!this.yellowRsvLoAirPressure.get() &&
!this.yellowRsvOverheat.get() &&
!this.yellowAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng3BPumpAuto.get(),
deltaTime,
);
@@ -2266,7 +2251,7 @@ export class FwsCore {
!this.yellowRsvLoAirPressure.get() &&
!this.yellowRsvOverheat.get() &&
!this.yellowAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng4APumpAuto,
deltaTime,
);
@@ -2285,7 +2270,7 @@ export class FwsCore {
!this.yellowRsvLoAirPressure.get() &&
!this.yellowRsvOverheat.get() &&
!this.yellowAbnormLoPressure.get() &&
- this.fwcFlightPhase.get() === 2 &&
+ this.flightPhase.get() === 2 &&
!this.eng4BPumpAuto.get(),
deltaTime,
);
@@ -2334,8 +2319,9 @@ export class FwsCore {
this.adirsRemainingAlignTime.set(SimVar.GetSimVarValue('L:A32NX_ADIRS_REMAINING_IR_ALIGNMENT_TIME', 'Seconds'));
// TODO use GPS alt if ADRs not available
- const pressureAltitude =
- adr1PressureAltitude.valueOr(null) ?? adr2PressureAltitude.valueOr(null) ?? adr3PressureAltitude.valueOr(null);
+ this.adrPressureAltitude.set(
+ adr1PressureAltitude.valueOr(null) ?? adr2PressureAltitude.valueOr(null) ?? adr3PressureAltitude.valueOr(null),
+ );
this.ir1Align.set(
this.ir1MaintWord.bitValueOr(16, false) ||
this.ir1MaintWord.bitValueOr(17, false) ||
@@ -2369,6 +2355,7 @@ export class FwsCore {
/* V1 callout */
const v1 = SimVar.GetSimVarValue('L:AIRLINER_V1_SPEED', SimVarValueType.Knots);
const v1Threshold = v1 - 4;
+ const v1ConfirmNodeStatus = this.v1SpeedConfirmNode.read();
this.v1SpeedConfirmNode.write(
v1 &&
(this.adr1Cas.get().valueOr(0) > v1Threshold ||
@@ -2376,7 +2363,14 @@ export class FwsCore {
this.adr3Cas.get().valueOr(0) > v1Threshold),
deltaTime,
);
- this.v1CalloutOutput.set(this.fwcFlightPhase.get() === 4 && this.v1SpeedConfirmNode.read());
+ if (
+ this.flightPhase.get() === 4 &&
+ this.v1SpeedConfirmNode.read() &&
+ !v1ConfirmNodeStatus &&
+ this.v1SpeedConfirmNode.read()
+ ) {
+ this.soundManager.enqueueSound('v1');
+ }
/* LANDING GEAR AND LIGHTS acquisition */
@@ -2497,14 +2491,14 @@ export class FwsCore {
this.autoPilotOffVoluntaryDiscPulse.write(voluntaryApDisc, deltaTime);
this.autoPilotOffVoluntaryFirstCavalryChargeActive.write(this.autoPilotOffVoluntaryDiscPulse.read(), deltaTime);
- this.autoPilotOffSendTripleClickAfterFirstCavalryCharge.write(
+ this.autoPilotOffVoluntaryFirstCavalryChargeActivePulse.write(
this.autoPilotOffVoluntaryFirstCavalryChargeActive.read(),
deltaTime,
);
- SimVar.SetSimVarValue(
- 'L:A32NX_FMA_TRIPLE_CLICK',
- 'Bool',
- this.autoPilotOffSendTripleClickAfterFirstCavalryCharge.read(),
+
+ this.autoPilotFirstCavalryStillWithinFirst0p3s.write(
+ this.autoPilotOffVoluntaryFirstCavalryChargeActive.read(),
+ deltaTime,
);
this.autoPilotInstinctiveDiscPressedTwiceInLast1p9Sec.write(
@@ -2516,13 +2510,14 @@ export class FwsCore {
this.autoPilotOffVoluntaryMemory.write(
this.autoPilotOffVoluntaryDiscPulse.read(),
apEngaged ||
- this.autoPilotInstinctiveDiscPressedTwiceInLast1p9Sec.read() ||
+ (this.autoPilotInstinctiveDiscPressedTwiceInLast1p9Sec.read() &&
+ !this.autoPilotFirstCavalryStillWithinFirst0p3s.read()) ||
!this.autoPilotOffVoluntaryEndAfter1p9s.read(),
);
const discPbPressedAfterDisconnection =
!this.autoPilotDisengagedInstantPulse.read() &&
- (this.autoPilotInstinctiveDiscPressedPulse.read() || masterWarningButtonLeft || masterCautionButtonRight);
+ (this.autoPilotInstinctiveDiscPressedPulse.read() || masterWarningButtonLeft || masterWarningButtonRight);
this.autoPilotOffUnacknowledged.write(
this.autoPilotDisengagedInstantPulse.read(),
@@ -2539,21 +2534,37 @@ export class FwsCore {
if (this.autoPilotDisengagedInstantPulse.read()) {
// Request quiet CRC one time
this.requestMasterWarningFromApOff = true;
- this.auralCavalryChargeActive.set(true);
- this.fwsAuralVolume.set(FwcAuralVolume.Attenuated);
+ this.soundManager.setVolume(FwsAuralVolume.Attenuated);
+ this.soundManager.enqueueSound('cavalryChargeCont'); // On the A380, first cav charge can be cancelled early
}
- if (!this.autoPilotOffVoluntaryFirstCavalryChargeActive.read()) {
- this.auralCavalryChargeActive.set(false);
- this.fwsAuralVolume.set(FwcAuralVolume.Full);
+ if (this.autoPilotOffVoluntaryFirstCavalryChargeActivePulse.read()) {
+ this.soundManager.dequeueSound('cavalryChargeCont');
+ this.soundManager.setVolume(FwsAuralVolume.Full);
}
if (!this.autoPilotOffVoluntaryMemory.read() && !this.autoPilotOffInvoluntaryMemory.read()) {
this.requestMasterWarningFromApOff = false;
- this.auralCavalryChargeActive.set(false);
- this.fwsAuralVolume.set(FwcAuralVolume.Full);
+ this.soundManager.dequeueSound('cavalryChargeCont');
+ this.soundManager.setVolume(FwsAuralVolume.Full);
}
this.autoPilotInstinctiveDiscPressedPulse.write(false, deltaTime);
+ // approach capability downgrade. Debounce first, then suppress for a certain amount of time
+ // (to avoid multiple triple clicks, and a delay which is too long)
+ const newCapability = SimVar.GetSimVarValue('L:A32NX_APPROACH_CAPABILITY', SimVarValueType.Number);
+ const capabilityDowngrade = newCapability < this.approachCapability.get() && newCapability > 0;
+ this.approachCapabilityDowngradeDebounce.write(
+ capabilityDowngrade && flightPhase189 && !this.approachCapabilityDowngradeSuppress.read(),
+ deltaTime,
+ );
+ this.approachCapabilityDowngradeDebouncePulse.write(this.approachCapabilityDowngradeDebounce.read(), deltaTime);
+ this.approachCapabilityDowngradeSuppress.write(this.approachCapabilityDowngradeDebouncePulse.read(), deltaTime);
+ // Capability downgrade after debounce --> triple click
+ if (this.approachCapabilityDowngradeDebouncePulse.read()) {
+ this.soundManager.enqueueSound('tripleClick');
+ }
+ this.approachCapability.set(newCapability);
+
// A/THR OFF
const aThrEngaged = this.autoThrustStatus.get() === 2 || this.autoThrustMode.get() !== 0;
this.autoThrustDisengagedInstantPulse.write(aThrEngaged, deltaTime);
@@ -2613,6 +2624,7 @@ export class FwsCore {
if (!this.autoBrakeDeactivatedNode.read()) {
this.autoBrakeOffMemoInhibited = false;
this.requestMasterCautionFromABrkOff = false;
+ this.autoBrakeOffAuralTriggered = false;
}
this.autoBrakeOffAuralConfirmNode.write(
@@ -2633,11 +2645,10 @@ export class FwsCore {
// FIXME double callout if ABRK fails
this.autoBrakeOff.set(autoBrakeOffShouldTrigger);
- SimVar.SetSimVarValue(
- 'L:A32NX_AUDIO_AUTOBRAKE_OFF',
- SimVarValueType.Bool,
- autoBrakeOffShouldTrigger && this.autoBrakeOffAuralConfirmNode.read(),
- );
+ if (autoBrakeOffShouldTrigger && this.autoBrakeOffAuralConfirmNode.read() && !this.autoBrakeOffAuralTriggered) {
+ this.soundManager.enqueueSound('autoBrakeOff');
+ this.autoBrakeOffAuralTriggered = true;
+ }
// Engine Logic
this.thrustLeverNotSet.set(this.autothrustLeverWarningFlex.get() || this.autothrustLeverWarningToga.get());
@@ -2767,11 +2778,11 @@ export class FwsCore {
/* 21 - AIR CONDITIONING AND PRESSURIZATION */
- this.flightLevel.set(Math.round(pressureAltitude / 100));
+ this.flightLevel.set(Math.round(this.adrPressureAltitude.get() / 100));
- this.phase8ConfirmationNode60.write(this.fwcFlightPhase.get() === 8, deltaTime);
+ this.phase8ConfirmationNode60.write(this.flightPhase.get() === 8, deltaTime);
- this.phase8ConfirmationNode180.write(this.fwcFlightPhase.get() === 8, deltaTime);
+ this.phase8ConfirmationNode180.write(this.flightPhase.get() === 8, deltaTime);
this.fdac1Channel1Failure.set(SimVar.GetSimVarValue('L:A32NX_COND_FDAC_1_CHANNEL_1_FAILURE', 'bool'));
this.fdac1Channel2Failure.set(SimVar.GetSimVarValue('L:A32NX_COND_FDAC_1_CHANNEL_2_FAILURE', 'bool'));
@@ -3277,7 +3288,7 @@ export class FwsCore {
const flapsNotInToPos = this.flapsSuperiorTo26Deg.get() || this.flapsInferiorTo8Deg.get();
this.flapConfigSr.write(
this.flightPhase345.get() && flapsNotInToPos,
- !flapsNotInToPos || phase6 || this.fwcFlightPhase.get() === 7,
+ !flapsNotInToPos || phase6 || this.flightPhase.get() === 7,
);
this.flapsNotTo.set(this.flightPhase1211.get() && flapsNotInToPos);
this.flapsNotToMemo.set(this.flapConfigSr.read() || this.flapsNotTo.get());
@@ -3292,7 +3303,7 @@ export class FwsCore {
const slatsNotInToPos = this.slatsInferiorTo20Deg.get();
this.slatConfigSr.write(
this.flightPhase345.get() && slatsNotInToPos,
- !slatsNotInToPos || phase6 || this.fwcFlightPhase.get() === 7,
+ !slatsNotInToPos || phase6 || this.flightPhase.get() === 7,
);
this.slatsNotTo.set(this.flightPhase1211.get() && slatsNotInToPos);
this.slatConfigAural.set(
@@ -3306,7 +3317,7 @@ export class FwsCore {
const speedbrakesNotInToPos = fcdc1DiscreteWord4.bitValueOr(28, false) || fcdc2DiscreteWord4.bitValueOr(28, false);
this.speedbrakesConfigSr.write(
this.flightPhase345.get() && speedbrakesNotInToPos,
- !speedbrakesNotInToPos || phase6 || this.fwcFlightPhase.get() === 7,
+ !speedbrakesNotInToPos || phase6 || this.flightPhase.get() === 7,
);
this.speedbrakesNotTo.set(this.flightPhase1211.get() && speedbrakesNotInToPos);
this.speedbrakesConfigAural.set(
@@ -3335,7 +3346,7 @@ export class FwsCore {
);
// taxi in flap 0 one minute check
- this.taxiInFlap0Check.write(this.slatFlapSelectionS0F0 && this.fwcFlightPhase.get() == 11, deltaTime);
+ this.taxiInFlap0Check.write(this.slatFlapSelectionS0F0 && this.flightPhase.get() == 11, deltaTime);
this.flapsMcduDisagree.set(
(flapsMcduPos1Disagree || flapsMcduPos2Disagree || flapsMcduPos3Disagree) &&
@@ -3355,7 +3366,7 @@ export class FwsCore {
const pitchConfigInPhase3or4or5 = this.flightPhase345.get() && pitchConfig;
this.pitchConfigInPhase3or4or5Sr.write(
pitchConfigInPhase3or4or5,
- phase6 || this.fwcFlightPhase.get() === 7 || !pitchConfig,
+ phase6 || this.flightPhase.get() === 7 || !pitchConfig,
);
this.pitchTrimNotToAudio.set(pitchConfigTestInPhase1211 || pitchConfigInPhase3or4or5);
this.pitchTrimNotToWarning.set(pitchConfigTestInPhase1211 || this.pitchConfigInPhase3or4or5Sr.read());
@@ -3403,7 +3414,7 @@ export class FwsCore {
(adr1PressureAltitude.valueOr(0) >= 22000 ||
adr2PressureAltitude.valueOr(0) >= 22000 ||
adr3PressureAltitude.valueOr(0) >= 22000) &&
- this.fwcFlightPhase.get() === 8 &&
+ this.flightPhase.get() === 8 &&
!this.slatFlapSelectionS0F0,
);
@@ -3415,13 +3426,13 @@ export class FwsCore {
deltaTime,
);
this.speedBrakeCaution1Confirm.write(
- this.fwcFlightPhase.get() === 8 &&
+ this.flightPhase.get() === 8 &&
this.speedBrakeCommand50sConfirm.read() &&
!this.engAboveIdleWithSpeedBrakeConfirm.read(),
deltaTime,
);
const speedBrakeCaution1 = this.speedBrakeCaution1Confirm.read();
- const speedBrakeCaution2 = this.fwcFlightPhase.get() === 9 && this.speedBrakeCommand5sConfirm.read();
+ const speedBrakeCaution2 = this.flightPhase.get() === 9 && this.speedBrakeCommand5sConfirm.read();
// FIXME FCU does not provide the bit, so we synthesize it
const apVerticalMode = SimVar.GetSimVarValue('L:A32NX_FMA_VERTICAL_MODE', 'number');
const apTcasRaNoseUp =
@@ -3431,7 +3442,7 @@ export class FwsCore {
this.apTcasRaNoseUpConfirm.write(apTcasRaNoseUp, deltaTime);
this.speedBrakeCaution3Confirm.write(
this.speedBrakeCommand.get() &&
- this.fwcFlightPhase.get() === 8 &&
+ this.flightPhase.get() === 8 &&
oneEngineAboveMinPower &&
this.apTcasRaNoseUpConfirm.read(),
deltaTime,
@@ -3464,7 +3475,7 @@ export class FwsCore {
const lgDown =
this.lgciu1DiscreteWord1.bitValueOr(29, false) ||
(this.lgciu2DiscreteWord1.bitValueOr(29, false) && mainGearDownlocked);
- this.phase104s5Trigger.write(this.fwcFlightPhase.get() === 10, deltaTime);
+ this.phase104s5Trigger.write(this.flightPhase.get() === 10, deltaTime);
this.groundSpoiler5sDelayed.write(
fcdc1DiscreteWord4.bitValueOr(27, false) || fcdc2DiscreteWord4.bitValueOr(27, false),
deltaTime,
@@ -3487,7 +3498,7 @@ export class FwsCore {
);
// l/g gear not down
- const fwcFlightPhase = this.fwcFlightPhase.get();
+ const fwcFlightPhase = this.flightPhase.get();
const flightPhase4567 =
fwcFlightPhase === 4 || fwcFlightPhase === 5 || fwcFlightPhase === 6 || fwcFlightPhase === 7;
const flightPhase8 = fwcFlightPhase === 8;
@@ -3498,7 +3509,7 @@ export class FwsCore {
this.radioHeight3.valueOr(Infinity),
) < 750;
const altInhibit =
- (pressureAltitude ?? 0) > 18500 &&
+ (this.adrPressureAltitude.get() ?? 0) > 18500 &&
!this.radioHeight1.isNoComputedData() &&
!this.radioHeight1.isNormalOperation() &&
!this.radioHeight2.isNoComputedData() &&
@@ -3812,7 +3823,7 @@ export class FwsCore {
(this.engine1State.get() === 0 && this.engine2State.get() === 0)),
);
- const flightPhase = this.fwcFlightPhase.get();
+ const flightPhase = this.flightPhase.get();
let tempMemoArrayLeft: string[] = [];
let tempMemoArrayRight: string[] = [];
const allFailureKeys: string[] = [];
@@ -4083,7 +4094,7 @@ export class FwsCore {
}
if (value.auralWarning?.get() === FwcAuralWarning.CavalryCharge) {
- this.auralCavalryChargeActive.set(true);
+ this.soundManager.enqueueSound('cavalryChargeCont');
}
}
@@ -4258,26 +4269,17 @@ export class FwsCore {
const sdStsShown = SimVar.GetSimVarValue('L:A32NX_ECAM_SD_CURRENT_PAGE_INDEX', SimVarValueType.Number) === 14;
this.ecamEwdShowStsIndication.set(!this.ecamStsNormal.get() && !sdStsShown);
- // This does not consider interrupting c-chord, priority of synthetic voice etc.
- const chimeRequested = this.auralSingleChimePending || this.requestSingleChimeFromAThrOff;
- if (
- chimeRequested &&
- !this.auralCrcActive.get() &&
- !this.auralCavalryChargeActive.get() &&
- !this.auralSingleChimeInhibitTimer.isPending()
- ) {
+ const chimeRequested =
+ (this.auralSingleChimePending || this.requestSingleChimeFromAThrOff) && !this.auralCrcActive.get();
+ if (chimeRequested && !this.auralSingleChimeInhibitTimer.isPending()) {
this.auralSingleChimePending = false;
this.requestSingleChimeFromAThrOff = false;
- SimVar.SetSimVarValue('L:A32NX_FWC_SC', 'bool', true);
+ this.soundManager.enqueueSound('singleChime');
// there can only be one SC per 2 seconds, non-cumulative, so clear any pending ones at the end of that inhibit period
this.auralSingleChimeInhibitTimer.schedule(
() => (this.auralSingleChimePending = false),
FwsCore.AURAL_SC_INHIBIT_TIME,
);
- this.auralSingleChimePlayingTimer.schedule(
- () => SimVar.SetSimVarValue('L:A32NX_FWC_SC', 'bool', false),
- FwsCore.AURAL_SC_PLAY_TIME,
- );
}
this.normalChecklists.update();
@@ -4343,7 +4345,7 @@ export class FwsCore {
const w = Arinc429Word.fromSimVarValue('L:A32NX_ROW_ROP_WORD_1');
// ROW
- SimVar.SetSimVarValue('L:A32NX_AUDIO_ROW_RWY_TOO_SHORT', 'bool', w.bitValueOr(15, false));
+ this.soundManager.handleSoundCondition('runwayTooShort', w.bitValueOr(15, false));
// ROP
// MAX BRAKING, only for manual braking, if maximum pedal braking is not applied
@@ -4351,20 +4353,19 @@ export class FwsCore {
SimVar.GetSimVarValue('L:A32NX_LEFT_BRAKE_PEDAL_INPUT', 'number') > 90 ||
SimVar.GetSimVarValue('L:A32NX_RIGHT_BRAKE_PEDAL_INPUT', 'number') > 90;
const maxBraking = w.bitValueOr(13, false) && !maxBrakingSet;
- SimVar.SetSimVarValue('L:A32NX_AUDIO_ROP_MAX_BRAKING', 'bool', maxBraking);
+ this.soundManager.handleSoundCondition('brakeMaxBraking', maxBraking);
// SET MAX REVERSE, if not already max. reverse set and !MAX_BRAKING
const maxReverseSet =
SimVar.GetSimVarValue('L:XMLVAR_Throttle1Position', 'number') < 0.1 &&
SimVar.GetSimVarValue('L:XMLVAR_Throttle2Position', 'number') < 0.1;
const maxReverse = (w.bitValueOr(12, false) || w.bitValueOr(13, false)) && !maxReverseSet;
- SimVar.SetSimVarValue('L:A32NX_AUDIO_ROW_SET_MAX_REVERSE', 'bool', !maxBraking && maxReverse);
+ this.soundManager.handleSoundCondition('setMaxReverse', !maxBraking && maxReverse);
// At 80kt, KEEP MAX REVERSE once, if max. reversers deployed
const ias = SimVar.GetSimVarValue('AIRSPEED INDICATED', 'knots');
- SimVar.SetSimVarValue(
- 'L:A32NX_AUDIO_ROP_KEEP_MAX_REVERSE',
- 'bool',
+ this.soundManager.handleSoundCondition(
+ 'keepMaxReverse',
ias <= 80 && ias > 4 && (w.bitValueOr(12, false) || w.bitValueOr(13, false)),
);
}
diff --git a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsFlightPhases.ts b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsFlightPhases.ts
new file mode 100644
index 00000000000..ef8066cbcd8
--- /dev/null
+++ b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsFlightPhases.ts
@@ -0,0 +1,534 @@
+/* eslint-disable no-underscore-dangle */
+/* eslint-disable camelcase */
+import {
+ Arinc429Register,
+ NXLogicConfirmNode,
+ NXLogicMemoryNode,
+ NXLogicTriggeredMonostableNode,
+} from '@flybywiresim/fbw-sdk';
+import { FwsCore } from 'systems-host/systems/FlightWarningSystem/FwsCore';
+
+export enum FwcFlightPhase {
+ ElecPwr = 1,
+ FirstEngineStarted = 2,
+ SecondEngineTakeOffPower = 3,
+ AtOrAboveEightyKnots = 4,
+ AtOrAboveV1 = 5,
+ LiftOff = 6,
+ AtOrAbove400Feet = 7,
+ AtOrAbove1500FeetTo800Feet = 8,
+ AtOrBelow800Feet = 9,
+ TouchDown = 10,
+ AtOrBelowEightyKnots = 11,
+ EnginesShutdown = 12,
+}
+
+// FIXME use subjects from FwsCore
+/**
+ * This nearly a 1:1 port from the A32NX's FWC serves as temporary replacement, until a more sophisticated system simulation is in place.
+ */
+export class FwsFlightPhases {
+ toConfigTest: boolean;
+
+ ldgMemo: boolean;
+
+ toMemo: boolean;
+
+ gndMemo: NXLogicConfirmNode;
+
+ oneEngineRunningConf: NXLogicConfirmNode;
+
+ speedAbove80KtsMemo: NXLogicMemoryNode;
+
+ speedAboveV1Memo: NXLogicMemoryNode;
+
+ mctMemo: NXLogicConfirmNode;
+
+ firePBOutConf: NXLogicConfirmNode;
+
+ firePBOutMemo: NXLogicTriggeredMonostableNode;
+
+ firePBClear12: NXLogicMemoryNode;
+
+ phase112Memo: NXLogicTriggeredMonostableNode;
+
+ phase10GroundMemo: NXLogicTriggeredMonostableNode;
+
+ ac80KtsMemo: NXLogicTriggeredMonostableNode;
+
+ prevPhase11InvertMemo: NXLogicTriggeredMonostableNode;
+
+ twoEnginesTOPowerInvertMemo: NXLogicTriggeredMonostableNode;
+
+ phase9Nvm: NXLogicMemoryNode;
+
+ prevPhase11: boolean;
+
+ groundImmediateMemo: NXLogicTriggeredMonostableNode;
+
+ phase6Memo: NXLogicTriggeredMonostableNode;
+
+ phase7Memo: NXLogicTriggeredMonostableNode;
+
+ phase89Memo: NXLogicTriggeredMonostableNode;
+
+ memoTo_conf01: NXLogicConfirmNode;
+
+ memoTo_memo: NXLogicMemoryNode;
+
+ memoLdgMemo_conf01: NXLogicConfirmNode;
+
+ memoLdgMemo_inhibit: NXLogicMemoryNode;
+
+ memoLdgMemo_conf02: NXLogicConfirmNode;
+
+ memoLdgMemo_below2000ft: NXLogicMemoryNode;
+
+ memoToInhibit_conf01: NXLogicConfirmNode;
+
+ memoLdgInhibit_conf01: NXLogicConfirmNode;
+
+ previousTargetAltitude: number;
+
+ _wasBelowThreshold: boolean;
+
+ _wasAboveThreshold: boolean;
+
+ _wasInRange: boolean;
+
+ _wasReach200ft: boolean;
+
+ _cChordShortWasTriggered: boolean;
+
+ aircraft: Aircraft;
+
+ private readonly adrAltitude = Arinc429Register.empty();
+
+ constructor(private fws: FwsCore) {
+ // momentary
+ this.toConfigTest = null;
+
+ // persistent
+ this.ldgMemo = null;
+ this.toMemo = null;
+
+ this.gndMemo = new NXLogicConfirmNode(1);
+
+ this.oneEngineRunningConf = new NXLogicConfirmNode(30);
+
+ this.speedAbove80KtsMemo = new NXLogicMemoryNode(true);
+
+ this.speedAboveV1Memo = new NXLogicMemoryNode();
+
+ this.mctMemo = new NXLogicConfirmNode(60, false);
+
+ this.firePBOutConf = new NXLogicConfirmNode(0.2);
+ this.firePBOutMemo = new NXLogicTriggeredMonostableNode(2);
+ this.firePBClear12 = new NXLogicMemoryNode(false);
+ this.phase112Memo = new NXLogicTriggeredMonostableNode(300);
+ this.phase10GroundMemo = new NXLogicTriggeredMonostableNode(2);
+ this.ac80KtsMemo = new NXLogicTriggeredMonostableNode(2);
+ this.prevPhase11InvertMemo = new NXLogicTriggeredMonostableNode(3, false);
+ this.twoEnginesTOPowerInvertMemo = new NXLogicTriggeredMonostableNode(1, false);
+ this.phase9Nvm = new NXLogicMemoryNode(true, true);
+ this.prevPhase11 = false;
+
+ this.groundImmediateMemo = new NXLogicTriggeredMonostableNode(2);
+ this.phase6Memo = new NXLogicTriggeredMonostableNode(15);
+ this.phase7Memo = new NXLogicTriggeredMonostableNode(120);
+ this.phase89Memo = new NXLogicTriggeredMonostableNode(180);
+
+ this.memoTo_conf01 = new NXLogicConfirmNode(120, true);
+ this.memoTo_memo = new NXLogicMemoryNode(false);
+
+ this.memoLdgMemo_conf01 = new NXLogicConfirmNode(1, true);
+ this.memoLdgMemo_inhibit = new NXLogicMemoryNode(false);
+ this.memoLdgMemo_conf02 = new NXLogicConfirmNode(10, true);
+ this.memoLdgMemo_below2000ft = new NXLogicMemoryNode(true);
+
+ this.memoToInhibit_conf01 = new NXLogicConfirmNode(3, true);
+
+ this.memoLdgInhibit_conf01 = new NXLogicConfirmNode(3, true);
+
+ // altitude warning
+ this.previousTargetAltitude = NaN;
+ this._wasBelowThreshold = false;
+ this._wasAboveThreshold = false;
+ this._wasInRange = false;
+ this._wasReach200ft = false;
+ }
+
+ update(deltaTime: number) {
+ this._updateFlightPhase(deltaTime);
+ this._updateTakeoffMemo(deltaTime);
+ this._updateLandingMemo(deltaTime);
+ this._updateAltitudeWarning();
+ }
+
+ _updateFlightPhase(_deltaTime: number) {
+ const raHeight1Invalid = this.fws.radioHeight1.isFailureWarning() || this.fws.radioHeight1.isNoComputedData();
+ const raHeight2Invalid = this.fws.radioHeight2.isFailureWarning() || this.fws.radioHeight2.isNoComputedData();
+ let radioHeight;
+ if (raHeight1Invalid) {
+ if (raHeight2Invalid) {
+ radioHeight = this.fws.radioHeight3;
+ } else {
+ radioHeight = this.fws.radioHeight2;
+ }
+ } else {
+ radioHeight = this.fws.radioHeight1;
+ }
+ // TODO find a better source for the following value ("core speed at or above idle")
+ // Note that N1 starts below idle on spawn on the runway, so this should be below 16 to not jump back to phase 1
+ const oneEngRunning =
+ this.fws.N1Eng1.get() > 15 ||
+ this.fws.N1Eng2.get() > 15 ||
+ this.fws.N1Eng3.get() > 15 ||
+ this.fws.N1Eng4.get() > 15;
+ const oneEngineRunning = this.oneEngineRunningConf.write(oneEngRunning, _deltaTime);
+ const noEngineRunning = !oneEngineRunning;
+ const hFail =
+ this.fws.radioHeight1.isFailureWarning() &&
+ this.fws.radioHeight2.isFailureWarning() &&
+ this.fws.radioHeight3.isFailureWarning();
+ const adcTestInhib = false;
+
+ const groundImmediate = Simplane.getIsGrounded();
+ const ground = this.gndMemo.write(groundImmediate, _deltaTime);
+
+ const ias = this.fws.computedAirSpeedToNearest2.get();
+ const acSpeedAbove80kts = this.speedAbove80KtsMemo.write(ias > 83, ias < 77);
+
+ const v1 = SimVar.GetSimVarValue('L:AIRLINER_V1_SPEED', 'knots');
+ let acAboveV1: boolean;
+ if (v1) {
+ acAboveV1 = this.speedAboveV1Memo.write(ias > v1 + 3, ias < v1 - 3);
+ } else {
+ acAboveV1 = false;
+ }
+
+ const hAbv1500 = radioHeight.isNoComputedData() || radioHeight.value > 1500;
+ const hAbv800 = radioHeight.isNoComputedData() || radioHeight.value > 800;
+ const hAbv400 = radioHeight.isNoComputedData() || radioHeight.value > 400;
+
+ const eng1TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:1', 'number');
+ const eng1TLAFTO = SimVar.GetSimVarValue('L:A32NX_AIRLINER_TO_FLEX_TEMP', 'number') !== 0; // is a flex temp is set?
+ const eng1MCT = eng1TLA > 33.3 && eng1TLA < 36.7;
+ const eng1TLAFullPwr = eng1TLA > 43.3;
+ const eng1MCL = eng1TLA > 22.9;
+ const eng1SupMCT = !(eng1TLA < 36.7);
+
+ const eng2TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:2', 'number');
+ const eng2TLAFTO = eng1TLAFTO; // until we have proper FADECs
+ const eng2MCT = eng2TLA > 33.3 && eng2TLA < 36.7;
+ const eng2TLAFullPwr = eng2TLA > 43.3;
+ const eng2MCL = eng2TLA > 22.9;
+ const eng2SupMCT = !(eng2TLA < 36.7);
+
+ const eng3TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:3', 'number');
+ const eng3TLAFTO = eng1TLAFTO; // until we have proper FADECs
+ const eng3MCT = eng3TLA > 33.3 && eng3TLA < 36.7;
+ const eng3TLAFullPwr = eng3TLA > 43.3;
+ const eng3MCL = eng3TLA > 22.9;
+ const eng3SupMCT = !(eng3TLA < 36.7);
+
+ const eng4TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:4', 'number');
+ const eng4TLAFTO = eng1TLAFTO; // until we have proper FADECs
+ const eng4MCT = eng4TLA > 33.3 && eng4TLA < 36.7;
+ const eng4TLAFullPwr = eng3TLA > 43.3;
+ const eng4MCL = eng4TLA > 22.9;
+ const eng4SupMCT = !(eng4TLA < 36.7);
+
+ const twoEnginesMcl = [eng1MCL, eng2MCL, eng3MCL, eng4MCL].filter(Boolean).length >= 2;
+ const eng1TOPowerSignal = (eng1TLAFTO && eng1MCT) || eng1TLAFullPwr || eng1SupMCT;
+ const eng2TOPowerSignal = (eng2TLAFTO && eng2MCT) || eng2TLAFullPwr || eng2SupMCT;
+ const eng3TOPowerSignal = (eng3TLAFTO && eng3MCT) || eng3TLAFullPwr || eng3SupMCT;
+ const eng4TOPowerSignal = (eng4TLAFTO && eng4MCT) || eng4TLAFullPwr || eng4SupMCT;
+
+ const twoEnginesTOPowerSignal =
+ [eng1TOPowerSignal, eng2TOPowerSignal, eng3TOPowerSignal, eng4TOPowerSignal].filter(Boolean).length >= 2;
+
+ const twoEnginesTOPower =
+ twoEnginesTOPowerSignal ||
+ (this.mctMemo.write(twoEnginesTOPowerSignal, _deltaTime) && !hAbv1500 && twoEnginesMcl);
+
+ const eng1FirePbMemo = this.firePBOutMemo.write(
+ this.firePBOutConf.write(this.fws.fireButtonEng1.get(), _deltaTime),
+ _deltaTime,
+ );
+ const resetFirePbClear12 = eng1FirePbMemo && ground;
+
+ const phase10 =
+ (this.phase10GroundMemo.write(groundImmediate, _deltaTime) || groundImmediate) &&
+ !twoEnginesTOPower &&
+ acSpeedAbove80kts;
+
+ const phase345Cond = ground && twoEnginesTOPower;
+ const phase3 = !acSpeedAbove80kts && oneEngRunning && phase345Cond;
+ const phase4 = acSpeedAbove80kts && phase345Cond && !acAboveV1;
+ const phase5 = acSpeedAbove80kts && phase345Cond && acAboveV1;
+
+ const setPhase11Nvm = phase3 || phase10;
+ const resetPhase11Nvm =
+ (!this.ac80KtsMemo.write(!acSpeedAbove80kts, _deltaTime) &&
+ ((ground && this.prevPhase11InvertMemo.write(this.prevPhase11, _deltaTime)) ||
+ resetFirePbClear12 ||
+ (ground && this.twoEnginesTOPowerInvertMemo.write(twoEnginesTOPower, _deltaTime))) &&
+ !this.prevPhase11) ||
+ adcTestInhib;
+ const phase11Nvm = this.phase9Nvm.write(setPhase11Nvm, resetPhase11Nvm); // S* / R (NVM)
+ const phase211Cond = ground && !twoEnginesTOPower && !acSpeedAbove80kts;
+ const phase11 = oneEngRunning && phase11Nvm && phase211Cond;
+ const phase2 = phase211Cond && !phase11Nvm && oneEngRunning;
+
+ const phase112MemoA = this.firePBClear12.write(phase11, resetFirePbClear12); // S / R*
+ const phase112Cond = !phase11 && noEngineRunning && groundImmediate;
+ const phase112Memo = this.phase112Memo.write(phase112MemoA && phase112Cond, _deltaTime);
+ const phase1 = phase112Cond && !phase112Memo;
+ const phase12 = phase112Cond && phase112Memo;
+
+ this.prevPhase11 = phase11;
+
+ const ground2sMemorized = this.groundImmediateMemo.write(groundImmediate, _deltaTime) || groundImmediate;
+
+ const phase6Cond = !hAbv400 && twoEnginesTOPower && !hFail && !ground2sMemorized;
+ const phase6 = this.phase6Memo.write(phase6Cond, _deltaTime) && phase6Cond;
+
+ const phase7Cond = !phase6 && !hAbv1500 && twoEnginesTOPower && !hFail && !ground2sMemorized;
+ const phase7 = this.phase7Memo.write(phase7Cond, _deltaTime) && phase7Cond;
+
+ const phase89Cond = !ground2sMemorized && !hFail && !twoEnginesTOPower && !hAbv1500 && !hAbv800;
+ const phase89Memo = this.phase89Memo.write(phase89Cond, _deltaTime) && phase89Cond;
+
+ const phase8 = !phase7 && !ground2sMemorized && !phase89Memo;
+ const phase9 = phase89Memo && !phase10;
+
+ // consolidate into single variable (just to be safe)
+ const phases = [phase1, phase2, phase3, phase4, phase5, phase6, phase7, phase8, phase9, phase10, phase11, phase12];
+
+ if (this.fws.flightPhase.get() === null && phases.indexOf(true) !== -1) {
+ // if we aren't initialized, just grab the first one that is valid
+ this.fws.flightPhase.set(phases.indexOf(true) + 1);
+ console.log(`FWC flight phase: ${this.fws.flightPhase.get()}`);
+ return;
+ }
+
+ const activePhases = phases
+ .map((x, i) => [x ? 1 : 0, i + 1])
+ .filter((y) => y[0] === 1)
+ .map((z) => z[1]);
+
+ // the usual and easy case: only one flight phase is valid
+ if (activePhases.length === 1) {
+ if (activePhases[0] !== this.fws.flightPhase.get()) {
+ console.log(`FWC flight phase: ${this.fws.flightPhase.get()} => ${activePhases[0]}`);
+ this.fws.flightPhase.set(activePhases[0]);
+ }
+ return;
+ }
+
+ // the mixed case => warn
+ if (activePhases.length > 1) {
+ if (activePhases.indexOf(this.fws.flightPhase.get()) !== -1) {
+ // if the currently active one is present, keep it
+ return;
+ }
+ // pick the earliest one
+ this.fws.flightPhase.set(activePhases[0]);
+ return;
+ }
+
+ // otherwise, no flight phase is valid => warn
+ if (this.fws.flightPhase.get() === null) {
+ this.fws.flightPhase.set(null);
+ }
+ }
+
+ _updateTakeoffMemo(_deltaTime: number) {
+ const setFlightPhaseMemo = this.fws.flightPhase.get() === FwcFlightPhase.FirstEngineStarted && this.toConfigTest;
+ const resetFlightPhaseMemo =
+ this.fws.flightPhase.get() === FwcFlightPhase.EnginesShutdown ||
+ this.fws.flightPhase.get() === FwcFlightPhase.SecondEngineTakeOffPower ||
+ this.fws.flightPhase.get() === FwcFlightPhase.ElecPwr ||
+ this.fws.flightPhase.get() === FwcFlightPhase.AtOrAbove1500FeetTo800Feet;
+ const flightPhaseMemo = this.memoTo_memo.write(setFlightPhaseMemo, resetFlightPhaseMemo);
+
+ this.fws.engine1Running.get();
+ const toTimerElapsed = this.memoTo_conf01.write(
+ this.fws.engine1Running.get() &&
+ this.fws.engine2Running.get() &&
+ this.fws.engine3Running.get() &&
+ this.fws.engine4Running.get(),
+ _deltaTime,
+ );
+
+ this.toMemo =
+ flightPhaseMemo || (this.fws.flightPhase.get() === FwcFlightPhase.FirstEngineStarted && toTimerElapsed);
+ SimVar.SetSimVarValue('L:A32NX_FWC_TOMEMO', 'Bool', this.toMemo);
+ }
+
+ _updateLandingMemo(_deltaTime: number) {
+ const radioHeight1Invalid = this.fws.radioHeight1.isFailureWarning() || this.fws.radioHeight1.isNoComputedData();
+ const radioHeight2Invalid = this.fws.radioHeight2.isFailureWarning() || this.fws.radioHeight2.isNoComputedData();
+ const radioHeight3Invalid = this.fws.radioHeight3.isFailureWarning() || this.fws.radioHeight3.isNoComputedData();
+ const gearDownlocked = SimVar.GetSimVarValue('GEAR TOTAL PCT EXTENDED', 'percent') > 0.95;
+
+ const setBelow2000ft =
+ (this.fws.radioHeight1.value < 2000 && !radioHeight1Invalid) ||
+ (this.fws.radioHeight2.value < 2000 && !radioHeight2Invalid) ||
+ (this.fws.radioHeight3.value < 2000 && !radioHeight3Invalid);
+ const resetBelow2000ft =
+ (this.fws.radioHeight1.value > 2200 || radioHeight1Invalid) &&
+ (this.fws.radioHeight2.value > 2200 || radioHeight2Invalid) &&
+ (this.fws.radioHeight3.value > 2200 || radioHeight3Invalid);
+ const memo2 = this.memoLdgMemo_below2000ft.write(setBelow2000ft, resetBelow2000ft);
+
+ const setInhibitMemo = this.memoLdgMemo_conf01.write(
+ resetBelow2000ft && !radioHeight1Invalid && !radioHeight2Invalid && !radioHeight3Invalid,
+ _deltaTime,
+ );
+ const resetInhibitMemo = !(
+ this.fws.flightPhase.get() === FwcFlightPhase.AtOrBelow800Feet ||
+ this.fws.flightPhase.get() === FwcFlightPhase.TouchDown ||
+ this.fws.flightPhase.get() === FwcFlightPhase.AtOrAbove1500FeetTo800Feet
+ );
+ const memo1 = this.memoLdgMemo_inhibit.write(setInhibitMemo, resetInhibitMemo);
+
+ const showInApproach = memo1 && memo2 && this.fws.flightPhase.get() === FwcFlightPhase.AtOrAbove1500FeetTo800Feet;
+
+ const invalidRadioMemo = this.memoLdgMemo_conf02.write(
+ radioHeight1Invalid &&
+ radioHeight2Invalid &&
+ radioHeight3Invalid &&
+ gearDownlocked &&
+ this.fws.flightPhase.get() === FwcFlightPhase.AtOrAbove1500FeetTo800Feet,
+ _deltaTime,
+ );
+
+ this.ldgMemo =
+ showInApproach ||
+ invalidRadioMemo ||
+ this.fws.flightPhase.get() === FwcFlightPhase.TouchDown ||
+ this.fws.flightPhase.get() === FwcFlightPhase.AtOrBelow800Feet;
+ SimVar.SetSimVarValue('L:A32NX_FWC_LDGMEMO', 'Bool', this.ldgMemo);
+ }
+
+ _updateAltitudeWarning() {
+ const warningPressed =
+ !!SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_L', 'Bool') ||
+ !!SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_R', 'Bool');
+ if (warningPressed === true) {
+ this._wasBelowThreshold = false;
+ this._wasAboveThreshold = false;
+ this._wasInRange = false;
+ this._cChordShortWasTriggered = false;
+ this.fws.soundManager.dequeueSound('cChordOnce');
+ this.fws.soundManager.dequeueSound('cChordCont');
+ return;
+ }
+
+ if (Simplane.getIsGrounded()) {
+ this.fws.soundManager.dequeueSound('cChordCont');
+ }
+
+ // Use FCU displayed value
+ const currentAltitudeConstraint = SimVar.GetSimVarValue('L:A32NX_FG_ALTITUDE_CONSTRAINT', 'feet');
+ const currentFCUAltitude = SimVar.GetSimVarValue('AUTOPILOT ALTITUDE LOCK VAR:3', 'feet');
+ const targetAltitude =
+ currentAltitudeConstraint && !this.hasAltitudeConstraint() ? currentAltitudeConstraint : currentFCUAltitude;
+
+ // Exit when selected altitude is being changed
+ if (this.previousTargetAltitude !== targetAltitude) {
+ this.previousTargetAltitude = targetAltitude;
+ this._wasBelowThreshold = false;
+ this._wasAboveThreshold = false;
+ this._wasInRange = false;
+ this._wasReach200ft = false;
+ this._cChordShortWasTriggered = false;
+ this.fws.soundManager.dequeueSound('cChordOnce');
+ this.fws.soundManager.dequeueSound('cChordCont');
+ return;
+ }
+
+ // Exit when:
+ // - Landing gear down & slats extended
+ // - Glide slope captured
+ // - Landing locked down
+
+ const landingGearIsDown =
+ SimVar.GetSimVarValue('L:A32NX_FLAPS_HANDLE_INDEX', 'Enum') >= 1 &&
+ SimVar.GetSimVarValue('L:A32NX_GEAR_HANDLE_POSITION', 'Percent over 100') > 0.5;
+ const verticalMode = SimVar.GetSimVarValue('L:A32NX_FMA_VERTICAL_MODE', 'Number');
+ const glideSlopeCaptured = verticalMode >= 30 && verticalMode <= 34;
+ const landingGearIsLockedDown = SimVar.GetSimVarValue('GEAR POSITION:0', 'Enum') > 0.9;
+ const isTcasResolutionAdvisoryActive = SimVar.GetSimVarValue('L:A32NX_TCAS_STATE', 'Enum') > 1;
+ if (landingGearIsDown || glideSlopeCaptured || landingGearIsLockedDown || isTcasResolutionAdvisoryActive) {
+ this._wasBelowThreshold = false;
+ this._wasAboveThreshold = false;
+ this._wasInRange = false;
+ this._wasReach200ft = false;
+ this._cChordShortWasTriggered = false;
+ this.fws.soundManager.dequeueSound('cChordOnce');
+ this.fws.soundManager.dequeueSound('cChordCont');
+ return;
+ }
+
+ // FIXME better altitude selection
+ this.adrAltitude.setFromSimVar(`L:A32NX_ADIRS_ADR_1_BARO_CORRECTED_ALTITUDE_${this.fws.fwsNumber}`);
+ if (!this.adrAltitude.isNormalOperation()) {
+ return;
+ }
+ const delta = Math.abs(this.adrAltitude.value - targetAltitude);
+
+ if (delta < 200) {
+ this._wasBelowThreshold = true;
+ this._wasAboveThreshold = false;
+ this._wasReach200ft = true;
+ }
+ if (delta > 750) {
+ this._wasAboveThreshold = true;
+ this._wasBelowThreshold = false;
+ this._cChordShortWasTriggered = false;
+ }
+ if (delta >= 200 && delta <= 750) {
+ this._wasInRange = true;
+ }
+
+ const apEngaged =
+ SimVar.GetSimVarValue('L:A32NX_AUTOPILOT_1_ACTIVE', 'Bool') ||
+ SimVar.GetSimVarValue('L:A32NX_AUTOPILOT_2_ACTIVE', 'Bool');
+ if (this._wasBelowThreshold && this._wasReach200ft) {
+ if (delta >= 200) {
+ this.fws.soundManager.enqueueSound('cChordCont');
+ } else {
+ this.fws.soundManager.dequeueSound('cChordCont');
+ }
+ } else if (
+ this._wasAboveThreshold &&
+ delta <= 750 &&
+ !this._wasReach200ft &&
+ !this._cChordShortWasTriggered &&
+ !apEngaged
+ ) {
+ this._cChordShortWasTriggered = true;
+ this.fws.soundManager.dequeueSound('cChordCont');
+ this.fws.soundManager.enqueueSound('cChordOnce');
+ } else if (delta > 750 && this._wasInRange && !this._wasReach200ft) {
+ if (delta > 750) {
+ this.fws.soundManager.enqueueSound('cChordCont');
+ } else {
+ this.fws.soundManager.dequeueSound('cChordCont');
+ }
+ }
+ }
+
+ hasAltitudeConstraint() {
+ if (
+ Simplane.getAutoPilotAltitudeManaged() &&
+ SimVar.GetSimVarValue('L:AP_CURRENT_TARGET_ALTITUDE_IS_CONSTRAINT', 'number') !== 0
+ ) {
+ return false;
+ }
+ return true;
+ }
+}
diff --git a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsMemos.ts b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsMemos.ts
index c4e104543f1..815d4d2bd8e 100644
--- a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsMemos.ts
+++ b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsMemos.ts
@@ -55,7 +55,7 @@ export class FwsMemos {
simVarIsActive: MappedSubject.create(
([speedBrakeCommand, fwcFlightPhase]) => speedBrakeCommand && ![1, 8, 9, 10].includes(fwcFlightPhase),
this.fws.speedBrakeCommand,
- this.fws.fwcFlightPhase,
+ this.fws.flightPhase,
),
whichCodeToReturn: () => [this.fws.amberSpeedBrake.get() ? 1 : 0],
codesToReturn: ['000006001', '000006002'],
@@ -353,7 +353,7 @@ export class FwsMemos {
// RAT OUT
flightPhaseInhib: [],
simVarIsActive: this.fws.ratDeployed.map((v) => v > 0),
- whichCodeToReturn: () => [[1, 2].includes(this.fws.fwcFlightPhase.get()) ? 0 : 1],
+ whichCodeToReturn: () => [[1, 2].includes(this.fws.flightPhase.get()) ? 0 : 1],
codesToReturn: ['242000001', '242000002'],
memoInhibit: () => false,
failure: 0,
diff --git a/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsSoundManager.ts b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsSoundManager.ts
new file mode 100644
index 00000000000..36696baec36
--- /dev/null
+++ b/fbw-a380x/src/systems/systems-host/systems/FlightWarningSystem/FwsSoundManager.ts
@@ -0,0 +1,453 @@
+// Copyright (c) 2021-2024 FlyByWire Simulations
+//
+// SPDX-License-Identifier: GPL-3.0
+
+import { EventBus, SimVarValueType, Subscribable } from '@microsoft/msfs-sdk';
+
+export interface FwsSoundManagerControlEvents {
+ enqueueSound: string;
+ dequeueSound: string;
+}
+
+// Synthetic voice has priority over everything, SC is least important
+enum FwsAuralWarningType {
+ SingleChime,
+ AuralWarning,
+ SyntheticVoice,
+}
+
+export enum FwsAuralVolume {
+ Full, // 0 dB
+ Attenuated, // -6dB
+ Silent, // -200 dB
+}
+
+interface FwsAural {
+ /** The LocalVar which triggers the playback. Not prefixed by L: here. Either localVarName or wwiseEventName has to be defined. */
+ localVarName?: string;
+ /** The Wwise event which triggers the playback. Either localVarName or wwiseEventName has to be defined. */
+ wwiseEventName?: string;
+ /** Sounds are queued based on type and priority (highest priority = gets queued first within same type) */
+ priority: number;
+ type: FwsAuralWarningType;
+ /** Length of audio in seconds, if non-repetitive */
+ length?: number;
+ /** If this is set, this sound is repeated periodically with the specified pause in seconds */
+ periodicWithPause?: number;
+ continuous?: boolean;
+}
+
+export const FwsAuralsList: Record = {
+ continuousRepetitiveChime: {
+ localVarName: 'A32NX_FWC_CRC',
+ priority: 5,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: true,
+ },
+ singleChime: {
+ localVarName: 'A32NX_FWC_SC',
+ length: 0.54,
+ priority: 0,
+ type: FwsAuralWarningType.SingleChime,
+ continuous: false,
+ },
+ cavalryChargeOnce: {
+ localVarName: 'A32NX_FWC_CAVALRY_CHARGE',
+ length: 0.9,
+ priority: 4,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ cavalryChargeCont: {
+ localVarName: 'A32NX_FWC_CAVALRY_CHARGE',
+ priority: 4,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: true,
+ },
+ tripleClick: {
+ localVarName: 'A32NX_FMA_TRIPLE_CLICK',
+ length: 0.62,
+ priority: 3,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ v1: {
+ localVarName: 'A32NX_AUDIO_V1_CALLOUT',
+ length: 1.3,
+ priority: 1,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ autoBrakeOff: {
+ localVarName: 'A32NX_AUDIO_AUTOBRAKE_OFF',
+ length: 1.5,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ runwayTooShort: {
+ localVarName: 'A32NX_AUDIO_ROW_RWY_TOO_SHORT',
+ length: 1.6,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: true,
+ },
+ keepMaxReverse: {
+ localVarName: 'A32NX_AUDIO_ROP_KEEP_MAX_REVERSE',
+ length: 1.4,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ setMaxReverse: {
+ localVarName: 'A32NX_AUDIO_ROW_SET_MAX_REVERSE',
+ length: 1.62,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: false,
+ },
+ brakeMaxBraking: {
+ localVarName: 'A32NX_AUDIO_ROP_MAX_BRAKING',
+ length: 3.1,
+ priority: 4,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: true,
+ },
+ stall: {
+ localVarName: 'A32NX_AUDIO_ROP_MAX_BRAKING',
+ length: 3.0,
+ priority: 5,
+ type: FwsAuralWarningType.SyntheticVoice,
+ continuous: true,
+ },
+ cChordOnce: {
+ localVarName: 'A32NX_ALT_DEVIATION',
+ length: 1.0,
+ priority: 3,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: false,
+ },
+ cChordCont: {
+ localVarName: 'A32NX_ALT_DEVIATION',
+ priority: 3,
+ type: FwsAuralWarningType.AuralWarning,
+ continuous: true,
+ },
+ // Altitude callouts
+ minimums: {
+ wwiseEventName: 'aural_minimumnew',
+ length: 0.67,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ hundred_above: {
+ wwiseEventName: 'aural_100above',
+ length: 0.72,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ retard: {
+ wwiseEventName: 'new_retard',
+ length: 0.9,
+ periodicWithPause: 0.2,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_2500: {
+ wwiseEventName: 'new_2500',
+ length: 1.1,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_2500b: {
+ wwiseEventName: 'new_2_500',
+ length: 1.047,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_2000: {
+ wwiseEventName: 'new_2000',
+ length: 0.72,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_1000: {
+ wwiseEventName: 'new_1000',
+ length: 0.9,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_500: {
+ wwiseEventName: 'new_500',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_400: {
+ wwiseEventName: 'new_400',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_300: {
+ wwiseEventName: 'new_300',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_200: {
+ wwiseEventName: 'new_200',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_100: {
+ wwiseEventName: 'new_100',
+ length: 0.6,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_90: {
+ wwiseEventName: '90_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_80: {
+ wwiseEventName: '80_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_70: {
+ wwiseEventName: '70_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_60: {
+ wwiseEventName: '60_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_50: {
+ wwiseEventName: '50_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_40: {
+ wwiseEventName: '40_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_30: {
+ wwiseEventName: '30_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_20: {
+ wwiseEventName: '20_380',
+ length: 0.4,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_10: {
+ wwiseEventName: '10_380',
+ length: 0.3,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+ alt_5: {
+ wwiseEventName: '5_380',
+ length: 0.3,
+ priority: 2,
+ type: FwsAuralWarningType.SyntheticVoice,
+ },
+};
+
+// FIXME Not all sounds are added to this yet (e.g. CIDS chimes), consider adding them in the future
+// Also, single chimes are not filtered (in RL only once every two seconds)
+export class FwsSoundManager {
+ private readonly soundQueue = new Set();
+
+ private singleChimesPending = 0;
+
+ private currentSoundPlaying: keyof typeof FwsAuralsList | null = null;
+
+ /** in seconds */
+ private currentSoundPlayTimeRemaining = 0;
+
+ constructor(
+ private bus: EventBus,
+ private startupCompleted: Subscribable,
+ ) {
+ // Stop all sounds
+ Object.values(FwsAuralsList).forEach((a) => {
+ if (a.localVarName) {
+ SimVar.SetSimVarValue(`L:${a.localVarName}`, SimVarValueType.Bool, false);
+ }
+ });
+
+ const sub = this.bus.getSubscriber();
+ sub.on('enqueueSound').handle((s) => this.enqueueSound(s));
+ sub.on('dequeueSound').handle((s) => this.dequeueSound(s));
+ }
+
+ /** Add sound to queue. Don't add if already playing */
+ enqueueSound(soundKey: keyof typeof FwsAuralsList) {
+ const sound = FwsAuralsList[soundKey];
+ if (!sound || this.currentSoundPlaying === soundKey) {
+ return;
+ }
+
+ if (sound.type === FwsAuralWarningType.SyntheticVoice || sound.type === FwsAuralWarningType.AuralWarning) {
+ this.soundQueue.add(soundKey);
+ } else if (sound.type === FwsAuralWarningType.SingleChime) {
+ this.singleChimesPending++;
+ }
+ }
+
+ /** Remove sound from queue, e.g. when condition doesn't apply anymore. If sound is currently playing, stops sound immediately */
+ dequeueSound(soundKey: keyof typeof FwsAuralsList) {
+ // Check if this sound is currently playing
+ if (this.currentSoundPlaying === soundKey && FwsAuralsList[this.currentSoundPlaying]?.continuous) {
+ this.stopCurrentSound();
+ }
+ this.soundQueue.delete(soundKey);
+ }
+
+ private stopCurrentSound() {
+ // Only LVar sounds which are continuous can be stopped
+ if (
+ this.currentSoundPlaying &&
+ FwsAuralsList[this.currentSoundPlaying].localVarName &&
+ FwsAuralsList[this.currentSoundPlaying]?.continuous
+ ) {
+ SimVar.SetSimVarValue(`L:${FwsAuralsList[this.currentSoundPlaying].localVarName}`, SimVarValueType.Bool, false);
+ this.currentSoundPlaying = null;
+ this.currentSoundPlayTimeRemaining = 0;
+ }
+ }
+
+ /**
+ * Convenience function for FWS: If condition true and sound not already playing, add to queue. If not, dequeue sound
+ * */
+ handleSoundCondition(soundKey: keyof typeof FwsAuralsList, condition: boolean) {
+ if (condition && this.currentSoundPlaying !== soundKey) {
+ this.enqueueSound(soundKey);
+ } else if (!condition) {
+ this.dequeueSound(soundKey);
+ }
+ }
+
+ /** This only has an effect on sounds defining WwiseRTPC behavior/var for volume */
+ setVolume(volume: FwsAuralVolume) {
+ SimVar.SetSimVarValue('L:A32NX_FWS_AUDIO_VOLUME', SimVarValueType.Enum, volume);
+ }
+
+ /** Play now, not to be called from the outside */
+ private playSound(soundKey: keyof typeof FwsAuralsList) {
+ const sound = FwsAuralsList[soundKey];
+ if (!sound) {
+ return;
+ }
+
+ if (sound.localVarName) {
+ SimVar.SetSimVarValue(`L:${sound.localVarName}`, SimVarValueType.Bool, true);
+ } else if (sound.wwiseEventName) {
+ Coherent.call('PLAY_INSTRUMENT_SOUND', sound.wwiseEventName);
+ }
+ this.currentSoundPlaying = soundKey;
+ this.currentSoundPlayTimeRemaining = sound.continuous ? Infinity : sound.length;
+ this.soundQueue.delete(soundKey);
+ }
+
+ /** Find most important sound from soundQueue and play */
+ private selectAndPlayMostImportantSound(): keyof typeof FwsAuralsList | null {
+ if (!this.startupCompleted.get()) {
+ return;
+ }
+
+ // Logic for scheduling new sounds: Take sound from soundQueue of most important type
+ // (SyntheticVoice > AuralWarning > SingleChime) with highest priority, and play it
+ let selectedSoundKey: keyof typeof FwsAuralsList | null = null;
+ this.soundQueue.forEach((sk) => {
+ const s = FwsAuralsList[sk];
+ if (
+ selectedSoundKey === null ||
+ s.type > FwsAuralsList[selectedSoundKey].type ||
+ (s.type === FwsAuralsList[selectedSoundKey].type && s.priority > FwsAuralsList[selectedSoundKey].priority)
+ ) {
+ selectedSoundKey = sk;
+ }
+ });
+
+ if (selectedSoundKey) {
+ this.playSound(selectedSoundKey);
+ return selectedSoundKey;
+ }
+
+ // See if single chimes are left
+ if (this.singleChimesPending) {
+ this.playSound('singleChime');
+ this.singleChimesPending--;
+ return 'singleChime';
+ }
+
+ // Ok, nothing to play
+ return null;
+ }
+
+ onUpdate(deltaTime: number) {
+ // Either wait for the current sound to finish, or schedule the next sound
+ if (this.currentSoundPlaying && this.currentSoundPlayTimeRemaining > 0) {
+ if (this.currentSoundPlayTimeRemaining - deltaTime / 1_000 > 0) {
+ // Wait for sound to be finished
+ this.currentSoundPlayTimeRemaining -= deltaTime / 1_000;
+ } else {
+ // Sound finishes in this cycle
+ if (FwsAuralsList[this.currentSoundPlaying].localVarName) {
+ SimVar.SetSimVarValue(
+ `L:${FwsAuralsList[this.currentSoundPlaying].localVarName}`,
+ SimVarValueType.Bool,
+ false,
+ );
+ }
+ this.currentSoundPlaying = null;
+ this.currentSoundPlayTimeRemaining = 0;
+ }
+
+ // Interrupt if sound with higher category is present in queue and current sound is continuous
+ let shouldInterrupt = false;
+ let rescheduleSound: keyof typeof FwsAuralsList | null = null;
+ this.soundQueue.forEach((sk) => {
+ const s = FwsAuralsList[sk];
+ if (
+ s &&
+ this.currentSoundPlaying &&
+ FwsAuralsList[this.currentSoundPlaying]?.continuous &&
+ s.type > FwsAuralsList[this.currentSoundPlaying].type
+ ) {
+ shouldInterrupt = true;
+ }
+ });
+
+ if (shouldInterrupt) {
+ if (this.currentSoundPlaying && FwsAuralsList[this.currentSoundPlaying]?.continuous) {
+ rescheduleSound = this.currentSoundPlaying;
+ this.stopCurrentSound();
+ if (rescheduleSound) {
+ this.enqueueSound(rescheduleSound);
+ }
+ }
+ }
+ } else {
+ // Play next sound
+ this.selectAndPlayMostImportantSound();
+ }
+ }
+}
diff --git a/fbw-a380x/src/systems/systems-host/systems/LegacyFwc.ts b/fbw-a380x/src/systems/systems-host/systems/LegacyFwc.ts
deleted file mode 100644
index 9ee2596a8f5..00000000000
--- a/fbw-a380x/src/systems/systems-host/systems/LegacyFwc.ts
+++ /dev/null
@@ -1,727 +0,0 @@
-/* eslint-disable no-underscore-dangle */
-/* eslint-disable camelcase */
-// TODO remove this once Rust implementation is up and running
-import { Arinc429Word, UpdateThrottler } from '@flybywiresim/fbw-sdk';
-
-enum FwcFlightPhase {
- ElecPwr = 1,
- FirstEngineStarted = 2,
- SecondEngineTakeOffPower = 3,
- AtOrAboveEightyKnots = 4,
- AtOrAboveV1 = 5,
- LiftOff = 6,
- AtOrAbove400Feet = 7,
- AtOrAbove1500FeetTo800Feet = 8,
- AtOrBelow800Feet = 9,
- TouchDown = 10,
- AtOrBelowEightyKnots = 11,
- EnginesShutdown = 12,
-}
-
-/**
- * This 1:1 port from the A32NX's FWC serves as temporary replacement, until a more sophisticated system simulation is in place.
- * After merge of PR #4872 (https://github.com/flybywiresim/aircraft/pull/4872) (intended for A32NX), the FWS architecture has to
- * be ported to the A380X, then this class can be removed.
- */
-export class LegacyFwc {
- private updateThrottler = new UpdateThrottler(125); // has to be > 100 due to pulse nodes
-
- toConfigTest: boolean;
-
- flightPhase: FwcFlightPhase;
-
- ldgMemo: boolean;
-
- toMemo: boolean;
-
- gndMemo: NXLogic_ConfirmNode;
-
- oneEngineRunningConf: NXLogic_ConfirmNode;
-
- speedAbove80KtsMemo: NXLogic_MemoryNode;
-
- speedAboveV1Memo: NXLogic_MemoryNode;
-
- mctMemo: NXLogic_ConfirmNode;
-
- firePBOutConf: NXLogic_ConfirmNode;
-
- firePBOutMemo: NXLogic_TriggeredMonostableNode;
-
- firePBClear12: NXLogic_MemoryNode;
-
- phase112Memo: NXLogic_TriggeredMonostableNode;
-
- phase10GroundMemo: NXLogic_TriggeredMonostableNode;
-
- ac80KtsMemo: NXLogic_TriggeredMonostableNode;
-
- prevPhase11InvertMemo: NXLogic_TriggeredMonostableNode;
-
- twoEnginesTOPowerInvertMemo: NXLogic_TriggeredMonostableNode;
-
- phase9Nvm: NXLogic_MemoryNode;
-
- prevPhase11: boolean;
-
- groundImmediateMemo: NXLogic_TriggeredMonostableNode;
-
- phase6Memo: NXLogic_TriggeredMonostableNode;
-
- phase7Memo: NXLogic_TriggeredMonostableNode;
-
- phase89Memo: NXLogic_TriggeredMonostableNode;
-
- memoTo_conf01: NXLogic_ConfirmNode;
-
- memoTo_memo: NXLogic_MemoryNode;
-
- memoLdgMemo_conf01: NXLogic_ConfirmNode;
-
- memoLdgMemo_inhibit: NXLogic_MemoryNode;
-
- memoLdgMemo_conf02: NXLogic_ConfirmNode;
-
- memoLdgMemo_below2000ft: NXLogic_MemoryNode;
-
- memoToInhibit_conf01: NXLogic_ConfirmNode;
-
- memoLdgInhibit_conf01: NXLogic_ConfirmNode;
-
- previousTargetAltitude: number;
-
- _wasBellowThreshold: boolean;
-
- _wasAboveThreshold: boolean;
-
- _wasInRange: boolean;
-
- _wasReach200ft: boolean;
-
- aircraft: Aircraft;
-
- constructor() {
- // momentary
- this.toConfigTest = null; // WTOCT
-
- // persistent
- this.flightPhase = null;
- this.ldgMemo = null;
- this.toMemo = null;
-
- // ESDL 1. 0. 60
- this.gndMemo = new NXLogic_ConfirmNode(1); // outptuts ZGND
-
- // ESDL 1. 0. 60
- this.oneEngineRunningConf = new NXLogic_ConfirmNode(30);
-
- // ESDL 1. 0. 73
- this.speedAbove80KtsMemo = new NXLogic_MemoryNode(true);
-
- this.speedAboveV1Memo = new NXLogic_MemoryNode();
-
- // ESDL 1. 0. 79 / ESDL 1. 0. 80
- this.mctMemo = new NXLogic_ConfirmNode(60, false);
-
- // ESDL 1. 0.100
- this.firePBOutConf = new NXLogic_ConfirmNode(0.2); // CONF01
- this.firePBOutMemo = new NXLogic_TriggeredMonostableNode(2); // MTRIG 05
- this.firePBClear12 = new NXLogic_MemoryNode(false);
- this.phase112Memo = new NXLogic_TriggeredMonostableNode(300); // MTRIG 03
- this.phase10GroundMemo = new NXLogic_TriggeredMonostableNode(2); // MTRIG 06
- this.ac80KtsMemo = new NXLogic_TriggeredMonostableNode(2); // MTRIG 04
- this.prevPhase11InvertMemo = new NXLogic_TriggeredMonostableNode(3, false); // MTRIG 02
- this.twoEnginesTOPowerInvertMemo = new NXLogic_TriggeredMonostableNode(1, false); // MTRIG 01
- this.phase9Nvm = new NXLogic_MemoryNode(true, true);
- this.prevPhase11 = false;
-
- // ESDL 1. 0.110
- this.groundImmediateMemo = new NXLogic_TriggeredMonostableNode(2); // MTRIG 03
- this.phase6Memo = new NXLogic_TriggeredMonostableNode(15);
- this.phase7Memo = new NXLogic_TriggeredMonostableNode(120);
- this.phase89Memo = new NXLogic_TriggeredMonostableNode(180); // MTRIG 02
-
- // ESDL 1. 0.180
- this.memoTo_conf01 = new NXLogic_ConfirmNode(120, true); // CONF 01
- this.memoTo_memo = new NXLogic_MemoryNode(false);
-
- // ESDL 1. 0.190
- this.memoLdgMemo_conf01 = new NXLogic_ConfirmNode(1, true); // CONF 01
- this.memoLdgMemo_inhibit = new NXLogic_MemoryNode(false);
- this.memoLdgMemo_conf02 = new NXLogic_ConfirmNode(10, true); // CONF 01
- this.memoLdgMemo_below2000ft = new NXLogic_MemoryNode(true);
-
- // ESDL 1. 0.310
- this.memoToInhibit_conf01 = new NXLogic_ConfirmNode(3, true); // CONF 01
-
- // ESDL 1. 0.320
- this.memoLdgInhibit_conf01 = new NXLogic_ConfirmNode(3, true); // CONF 01
-
- // altitude warning
- this.previousTargetAltitude = NaN;
- this._wasBellowThreshold = false;
- this._wasAboveThreshold = false;
- this._wasInRange = false;
- this._wasReach200ft = false;
- }
-
- update(_deltaTime: number) {
- const throttledT = this.updateThrottler.canUpdate(_deltaTime);
-
- if (throttledT > 0) {
- this._updateFlightPhase(throttledT);
- this._updateTakeoffMemo(throttledT);
- this._updateLandingMemo(throttledT);
- this._updateAltitudeWarning();
- }
- }
-
- _updateFlightPhase(_deltaTime: number) {
- const radioHeight1 = Arinc429Word.fromSimVarValue('L:A32NX_RA_1_RADIO_ALTITUDE');
- const radioHeight2 = Arinc429Word.fromSimVarValue('L:A32NX_RA_2_RADIO_ALTITUDE');
- const radioHeight3 = Arinc429Word.fromSimVarValue('L:A32NX_RA_3_RADIO_ALTITUDE');
-
- const raHeight1InValid = radioHeight1.isFailureWarning() || radioHeight1.isNoComputedData();
- const raHeight2InValid = radioHeight2.isFailureWarning() || radioHeight2.isNoComputedData();
- let radioHeight;
- if (raHeight1InValid) {
- if (raHeight2InValid) {
- radioHeight = radioHeight3;
- } else {
- radioHeight = radioHeight2;
- }
- } else {
- radioHeight = radioHeight1;
- }
- const eng1N1 = SimVar.GetSimVarValue('ENG N1 RPM:1', 'Percent');
- const eng2N1 = SimVar.GetSimVarValue('ENG N1 RPM:2', 'Percent');
- const eng3N1 = SimVar.GetSimVarValue('ENG N1 RPM:3', 'Percent');
- const eng4N1 = SimVar.GetSimVarValue('ENG N1 RPM:4', 'Percent');
- // TODO find a better source for the following value ("core speed at or above idle")
- // Note that N1 starts below idle on spawn on the runway, so this should be below 16 to not jump back to phase 1
- const oneEngRunning = eng1N1 > 15 || eng2N1 > 15 || eng3N1 > 15 || eng4N1 > 15;
- const oneEngineRunning = this.oneEngineRunningConf.write(oneEngRunning, _deltaTime);
- const noEngineRunning = !oneEngineRunning;
- const hFail = radioHeight1.isFailureWarning() && radioHeight2.isFailureWarning() && radioHeight3.isFailureWarning();
- const adcTestInhib = false;
-
- // ESLD 1.0.60
- const groundImmediate = Simplane.getIsGrounded();
- const ground = this.gndMemo.write(groundImmediate, _deltaTime);
-
- // ESLD 1.0.73
- const ias = SimVar.GetSimVarValue('AIRSPEED INDICATED', 'knots');
- const acSpeedAbove80kts = this.speedAbove80KtsMemo.write(ias > 83, ias < 77);
-
- const v1 = SimVar.GetSimVarValue('L:AIRLINER_V1_SPEED', 'knots');
- let acAboveV1;
- if (v1) {
- acAboveV1 = this.speedAboveV1Memo.write(ias > v1 + 3, ias < v1 - 3);
- } else {
- acAboveV1 = false;
- }
-
- // ESLD 1.0.90
- const hAbv1500 = radioHeight.isNoComputedData() || radioHeight.value > 1500;
- const hAbv800 = radioHeight.isNoComputedData() || radioHeight.value > 800;
- const hAbv400 = radioHeight.isNoComputedData() || radioHeight.value > 400;
-
- // ESLD 1.0.79 + 1.0.80
- const eng1TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:1', 'number');
- const eng1TLAFTO = SimVar.GetSimVarValue('L:A32NX_AIRLINER_TO_FLEX_TEMP', 'number') !== 0; // is a flex temp is set?
- const eng1MCT = eng1TLA > 33.3 && eng1TLA < 36.7;
- const eng1TLAFullPwr = eng1TLA > 43.3;
- const eng1MCL = eng1TLA > 22.9;
- const eng1SupMCT = !(eng1TLA < 36.7);
-
- const eng2TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:2', 'number');
- const eng2TLAFTO = eng1TLAFTO; // until we have proper FADECs
- const eng2MCT = eng2TLA > 33.3 && eng2TLA < 36.7;
- const eng2TLAFullPwr = eng2TLA > 43.3;
- const eng2MCL = eng2TLA > 22.9;
- const eng2SupMCT = !(eng2TLA < 36.7);
-
- const eng3TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:3', 'number');
- const eng3TLAFTO = eng1TLAFTO; // until we have proper FADECs
- const eng3MCT = eng3TLA > 33.3 && eng3TLA < 36.7;
- const eng3TLAFullPwr = eng3TLA > 43.3;
- const eng3MCL = eng3TLA > 22.9;
- const eng3SupMCT = !(eng3TLA < 36.7);
-
- const eng4TLA = SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:4', 'number');
- const eng4TLAFTO = eng1TLAFTO; // until we have proper FADECs
- const eng4MCT = eng3TLA > 33.3 && eng3TLA < 36.7;
- const eng4TLAFullPwr = eng3TLA > 43.3;
- const eng4MCL = eng3TLA > 22.9;
- const eng4SupMCT = !(eng4TLA < 36.7);
-
- const twoEnginesMcl = [eng1MCL, eng2MCL, eng3MCL, eng4MCL].filter(Boolean).length >= 2;
- const eng1TOPowerSignal = (eng1TLAFTO && eng1MCT) || eng1TLAFullPwr || eng1SupMCT;
- const eng2TOPowerSignal = (eng2TLAFTO && eng2MCT) || eng2TLAFullPwr || eng2SupMCT;
- const eng3TOPowerSignal = (eng3TLAFTO && eng3MCT) || eng3TLAFullPwr || eng3SupMCT;
- const eng4TOPowerSignal = (eng4TLAFTO && eng4MCT) || eng4TLAFullPwr || eng4SupMCT;
-
- const twoEnginesTOPowerSignal =
- [eng1TOPowerSignal, eng2TOPowerSignal, eng3TOPowerSignal, eng4TOPowerSignal].filter(Boolean).length >= 2;
-
- const twoEnginesTOPower =
- twoEnginesTOPowerSignal ||
- (this.mctMemo.write(twoEnginesTOPowerSignal, _deltaTime) && !hAbv1500 && twoEnginesMcl);
-
- // ESLD 1.0.100
- const eng1FirePbOut = SimVar.GetSimVarValue('L:A32NX_FIRE_BUTTON_ENG1', 'Bool');
- const eng1FirePbMemo = this.firePBOutMemo.write(this.firePBOutConf.write(eng1FirePbOut, _deltaTime), _deltaTime);
- const resetFirePbClear12 = eng1FirePbMemo && ground;
-
- const phase10 =
- (this.phase10GroundMemo.write(groundImmediate, _deltaTime) || groundImmediate) &&
- !twoEnginesTOPower &&
- acSpeedAbove80kts;
-
- const phase345Cond = ground && twoEnginesTOPower;
- const phase3 = !acSpeedAbove80kts && oneEngRunning && phase345Cond;
- const phase4 = acSpeedAbove80kts && phase345Cond && !acAboveV1;
- const phase5 = acSpeedAbove80kts && phase345Cond && acAboveV1;
-
- const setPhase11Nvm = phase3 || phase10;
- const resetPhase11Nvm =
- (!this.ac80KtsMemo.write(!acSpeedAbove80kts, _deltaTime) &&
- ((ground && this.prevPhase11InvertMemo.write(this.prevPhase11, _deltaTime)) ||
- resetFirePbClear12 ||
- (ground && this.twoEnginesTOPowerInvertMemo.write(twoEnginesTOPower, _deltaTime))) &&
- !this.prevPhase11) ||
- adcTestInhib;
- const phase11Nvm = this.phase9Nvm.write(setPhase11Nvm, resetPhase11Nvm); // S* / R (NVM)
- const phase211Cond = ground && !twoEnginesTOPower && !acSpeedAbove80kts;
- const phase11 = oneEngRunning && phase11Nvm && phase211Cond;
- const phase2 = phase211Cond && !phase11Nvm && oneEngRunning;
-
- const phase112MemoA = this.firePBClear12.write(phase11, resetFirePbClear12); // S / R*
- const phase112Cond = !phase11 && noEngineRunning && groundImmediate;
- const phase112Memo = this.phase112Memo.write(phase112MemoA && phase112Cond, _deltaTime); // MTRIG 03
- const phase1 = phase112Cond && !phase112Memo;
- const phase12 = phase112Cond && phase112Memo;
-
- this.prevPhase11 = phase11;
-
- // ESLD 1.0.110
- const ground2sMemorized = this.groundImmediateMemo.write(groundImmediate, _deltaTime) || groundImmediate;
-
- const phase6Cond = !hAbv400 && twoEnginesTOPower && !hFail && !ground2sMemorized;
- const phase6 = this.phase6Memo.write(phase6Cond, _deltaTime) && phase6Cond;
-
- const phase7Cond = !phase6 && !hAbv1500 && twoEnginesTOPower && !hFail && !ground2sMemorized;
- const phase7 = this.phase7Memo.write(phase7Cond, _deltaTime) && phase7Cond;
-
- const phase89Cond = !ground2sMemorized && !hFail && !twoEnginesTOPower && !hAbv1500 && !hAbv800;
- const phase89Memo = this.phase89Memo.write(phase89Cond, _deltaTime) && phase89Cond;
-
- const phase8 = !phase7 && !ground2sMemorized && !phase89Memo;
- const phase9 = phase89Memo && !phase10;
-
- /** * End of ESLD logic ** */
-
- // consolidate into single variable (just to be safe)
- const phases = [phase1, phase2, phase3, phase4, phase5, phase6, phase7, phase8, phase9, phase10, phase11, phase12];
-
- if (this.flightPhase === null && phases.indexOf(true) !== -1) {
- // if we aren't initialized, just grab the first one that is valid
- this._setFlightPhase(phases.indexOf(true) + 1);
- console.log(`FWC flight phase: ${this.flightPhase}`);
- return;
- }
-
- const activePhases = phases
- .map((x, i) => [x ? 1 : 0, i + 1])
- .filter((y) => y[0] === 1)
- .map((z) => z[1]);
-
- // the usual and easy case: only one flight phase is valid
- if (activePhases.length === 1) {
- if (activePhases[0] !== this.flightPhase) {
- console.log(`FWC flight phase: ${this.flightPhase} => ${activePhases[0]}`);
- this._setFlightPhase(activePhases[0]);
- }
- return;
- }
-
- // the mixed case => warn
- if (activePhases.length > 1) {
- if (activePhases.indexOf(this.flightPhase) !== -1) {
- // if the currently active one is present, keep it
- return;
- }
- // pick the earliest one
- this._setFlightPhase(activePhases[0]);
- return;
- }
-
- // otherwise, no flight phase is valid => warn
- if (this.flightPhase === null) {
- this._setFlightPhase(null);
- }
- }
-
- _setFlightPhase(flightPhase: FwcFlightPhase) {
- if (flightPhase === this.flightPhase) {
- return;
- }
-
- // update flight phase
- this.flightPhase = flightPhase;
- SimVar.SetSimVarValue('L:A32NX_FWC_FLIGHT_PHASE', 'Enum', this.flightPhase || 0);
- }
-
- _updateTakeoffMemo(_deltaTime: number) {
- /// FWC ESLD 1.0.180
- const setFlightPhaseMemo = this.flightPhase === FwcFlightPhase.FirstEngineStarted && this.toConfigTest;
- const resetFlightPhaseMemo =
- this.flightPhase === FwcFlightPhase.EnginesShutdown ||
- this.flightPhase === FwcFlightPhase.SecondEngineTakeOffPower ||
- this.flightPhase === FwcFlightPhase.ElecPwr ||
- this.flightPhase === FwcFlightPhase.AtOrAbove1500FeetTo800Feet;
- const flightPhaseMemo = this.memoTo_memo.write(setFlightPhaseMemo, resetFlightPhaseMemo);
-
- const eng1NotRunning = SimVar.GetSimVarValue('ENG N1 RPM:1', 'Percent') < 15;
- const eng2NotRunning = SimVar.GetSimVarValue('ENG N1 RPM:2', 'Percent') < 15;
- const eng3NotRunning = SimVar.GetSimVarValue('ENG N1 RPM:3', 'Percent') < 15;
- const eng4NotRunning = SimVar.GetSimVarValue('ENG N1 RPM:4', 'Percent') < 15;
- const toTimerElapsed = this.memoTo_conf01.write(
- !eng1NotRunning && !eng2NotRunning && !eng3NotRunning && !eng4NotRunning,
- _deltaTime,
- );
-
- this.toMemo = flightPhaseMemo || (this.flightPhase === FwcFlightPhase.FirstEngineStarted && toTimerElapsed);
- SimVar.SetSimVarValue('L:A32NX_FWC_TOMEMO', 'Bool', this.toMemo);
- }
-
- _updateLandingMemo(_deltaTime: number) {
- const radioHeight1 = Arinc429Word.fromSimVarValue('L:A32NX_RA_1_RADIO_ALTITUDE');
- const radioHeight2 = Arinc429Word.fromSimVarValue('L:A32NX_RA_2_RADIO_ALTITUDE');
- const radioHeight3 = Arinc429Word.fromSimVarValue('L:A32NX_RA_3_RADIO_ALTITUDE');
- const radioHeight1Invalid = radioHeight1.isFailureWarning() || radioHeight1.isNoComputedData();
- const radioHeight2Invalid = radioHeight2.isFailureWarning() || radioHeight2.isNoComputedData();
- const radioHeight3Invalid = radioHeight3.isFailureWarning() || radioHeight3.isNoComputedData();
- const gearDownlocked = SimVar.GetSimVarValue('GEAR TOTAL PCT EXTENDED', 'percent') > 0.95;
-
- // FWC ESLD 1.0.190
- const setBelow2000ft =
- (radioHeight1.value < 2000 && !radioHeight1Invalid) ||
- (radioHeight2.value < 2000 && !radioHeight2Invalid) ||
- (radioHeight3.value < 2000 && !radioHeight3Invalid);
- const resetBelow2000ft =
- (radioHeight1.value > 2200 || radioHeight1Invalid) &&
- (radioHeight2.value > 2200 || radioHeight2Invalid) &&
- (radioHeight3.value > 2200 || radioHeight3Invalid);
- const memo2 = this.memoLdgMemo_below2000ft.write(setBelow2000ft, resetBelow2000ft);
-
- const setInhibitMemo = this.memoLdgMemo_conf01.write(
- resetBelow2000ft && !radioHeight1Invalid && !radioHeight2Invalid && !radioHeight3Invalid,
- _deltaTime,
- );
- const resetInhibitMemo = !(
- this.flightPhase === FwcFlightPhase.AtOrBelow800Feet ||
- this.flightPhase === FwcFlightPhase.TouchDown ||
- this.flightPhase === FwcFlightPhase.AtOrAbove1500FeetTo800Feet
- );
- const memo1 = this.memoLdgMemo_inhibit.write(setInhibitMemo, resetInhibitMemo);
-
- const showInApproach = memo1 && memo2 && this.flightPhase === FwcFlightPhase.AtOrAbove1500FeetTo800Feet;
-
- const invalidRadioMemo = this.memoLdgMemo_conf02.write(
- radioHeight1Invalid &&
- radioHeight2Invalid &&
- radioHeight3Invalid &&
- gearDownlocked &&
- this.flightPhase === FwcFlightPhase.AtOrAbove1500FeetTo800Feet,
- _deltaTime,
- );
-
- this.ldgMemo =
- showInApproach ||
- invalidRadioMemo ||
- this.flightPhase === FwcFlightPhase.TouchDown ||
- this.flightPhase === FwcFlightPhase.AtOrBelow800Feet;
- SimVar.SetSimVarValue('L:A32NX_FWC_LDGMEMO', 'Bool', this.ldgMemo);
- }
-
- _updateAltitudeWarning() {
- const indicatedAltitude = Simplane.getAltitude();
- const shortAlert = SimVar.GetSimVarValue('L:A32NX_ALT_DEVIATION_SHORT', 'Bool');
- if (shortAlert === 1) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION_SHORT', 'Bool', false);
- }
-
- const warningPressed =
- !!SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_L', 'Bool') ||
- !!SimVar.GetSimVarValue('L:PUSH_AUTOPILOT_MASTERAWARN_R', 'Bool');
- if (warningPressed === true) {
- this._wasBellowThreshold = false;
- this._wasAboveThreshold = false;
- this._wasInRange = false;
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- return;
- }
-
- if (Simplane.getIsGrounded()) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- }
-
- // Use FCU displayed value
- const currentAltitudeConstraint = SimVar.GetSimVarValue('L:A32NX_FG_ALTITUDE_CONSTRAINT', 'feet');
- const currentFCUAltitude = SimVar.GetSimVarValue('AUTOPILOT ALTITUDE LOCK VAR:3', 'feet');
- const targetAltitude =
- currentAltitudeConstraint && !this.hasAltitudeConstraint() ? currentAltitudeConstraint : currentFCUAltitude;
-
- // Exit when selected altitude is being changed
- if (this.previousTargetAltitude !== targetAltitude) {
- this.previousTargetAltitude = targetAltitude;
- this._wasBellowThreshold = false;
- this._wasAboveThreshold = false;
- this._wasInRange = false;
- this._wasReach200ft = false;
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION_SHORT', 'Bool', false);
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- return;
- }
-
- // Exit when:
- // - Landing gear down & slats extended
- // - Glide slope captured
- // - Landing locked down
-
- const landingGearIsDown =
- SimVar.GetSimVarValue('L:A32NX_FLAPS_HANDLE_INDEX', 'Enum') >= 1 &&
- SimVar.GetSimVarValue('L:A32NX_GEAR_HANDLE_POSITION', 'Percent over 100') > 0.5;
- const verticalMode = SimVar.GetSimVarValue('L:A32NX_FMA_VERTICAL_MODE', 'Number');
- const glideSlopeCaptured = verticalMode >= 30 && verticalMode <= 34;
- const landingGearIsLockedDown = SimVar.GetSimVarValue('GEAR POSITION:0', 'Enum') > 0.9;
- const isTcasResolutionAdvisoryActive = SimVar.GetSimVarValue('L:A32NX_TCAS_STATE', 'Enum') > 1;
- if (landingGearIsDown || glideSlopeCaptured || landingGearIsLockedDown || isTcasResolutionAdvisoryActive) {
- this._wasBellowThreshold = false;
- this._wasAboveThreshold = false;
- this._wasInRange = false;
- this._wasReach200ft = false;
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION_SHORT', 'Bool', false);
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- return;
- }
-
- const delta = Math.abs(indicatedAltitude - targetAltitude);
-
- if (delta < 200) {
- this._wasBellowThreshold = true;
- this._wasAboveThreshold = false;
- this._wasReach200ft = true;
- }
- if (delta > 750) {
- this._wasAboveThreshold = true;
- this._wasBellowThreshold = false;
- }
- if (delta >= 200 && delta <= 750) {
- this._wasInRange = true;
- }
-
- if (this._wasBellowThreshold && this._wasReach200ft) {
- if (delta >= 200) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', true);
- } else if (delta < 200) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- }
- } else if (this._wasAboveThreshold && delta <= 750 && !this._wasReach200ft) {
- if (
- !SimVar.GetSimVarValue('L:A32NX_AUTOPILOT_1_ACTIVE', 'Bool') &&
- !SimVar.GetSimVarValue('L:A32NX_AUTOPILOT_2_ACTIVE', 'Bool')
- ) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION_SHORT', 'Bool', true);
- }
- } else if (delta > 750 && this._wasInRange && !this._wasReach200ft) {
- if (delta > 750) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', true);
- } else if (delta >= 750) {
- SimVar.SetSimVarValue('L:A32NX_ALT_DEVIATION', 'Bool', false);
- }
- }
- }
-
- hasAltitudeConstraint() {
- if (
- Simplane.getAutoPilotAltitudeManaged() &&
- SimVar.GetSimVarValue('L:AP_CURRENT_TARGET_ALTITUDE_IS_CONSTRAINT', 'number') !== 0
- ) {
- return false;
- }
- return true;
- }
-}
-
-/*
- * This file contains various nodes that can be used for logical processing. Systems like the FWC may use them to
- * accurately implement their functionality.
- */
-
-/**
- * The following class represents a monostable circuit. It is inspired by the MTRIG nodes as described in the ESLD and
- * used by the FWC.
- * When it detects either a rising or a falling edge (depending on it's type) it will emit a signal for a certain time t
- * after the detection. It is not retriggerable, so a rising/falling edge within t will not reset the timer.
- */
-class NXLogic_TriggeredMonostableNode {
- t: number;
-
- risingEdge: boolean;
-
- _timer: number;
-
- _previousValue: boolean;
-
- constructor(t: number, risingEdge = true) {
- this.t = t;
- this.risingEdge = risingEdge;
- this._timer = 0;
- this._previousValue = null;
- }
-
- write(value: boolean, _deltaTime: number) {
- if (this._previousValue === null && SimVar.GetSimVarValue('L:A32NX_FWC_SKIP_STARTUP', 'Bool')) {
- this._previousValue = value;
- }
- if (this.risingEdge) {
- if (this._timer > 0) {
- this._timer = Math.max(this._timer - _deltaTime / 1000, 0);
- this._previousValue = value;
- return true;
- }
- if (!this._previousValue && value) {
- this._timer = this.t;
- this._previousValue = value;
- return true;
- }
- } else {
- if (this._timer > 0) {
- this._timer = Math.max(this._timer - _deltaTime / 1000, 0);
- this._previousValue = value;
- return true;
- }
- if (this._previousValue && !value) {
- this._timer = this.t;
- this._previousValue = value;
- return true;
- }
- }
- this._previousValue = value;
- return false;
- }
-}
-
-/**
- * The following class represents a "confirmation" circuit, which only passes a signal once it has been stable for a
- * certain amount of time. It is inspired by the CONF nodes as described in the ESLD and used by the FWC.
- * When it detects either a rising or falling edge (depending on it's type) it will wait for up to time t and emit the
- * incoming signal if it was stable throughout t. If at any point the signal reverts during t the state is fully reset,
- * and the original signal will be emitted again.
- */
-class NXLogic_ConfirmNode {
- t: number;
-
- risingEdge: boolean;
-
- _timer: number;
-
- _previousInput: boolean;
-
- _previousOutput: boolean;
-
- constructor(t: number, risingEdge = true) {
- this.t = t;
- this.risingEdge = risingEdge;
- this._timer = 0;
- this._previousInput = null;
- this._previousOutput = null;
- }
-
- write(value: boolean, _deltaTime: number) {
- if (this._previousInput === null && SimVar.GetSimVarValue('L:A32NX_FWC_SKIP_STARTUP', 'Bool')) {
- this._previousInput = value;
- this._previousOutput = value;
- }
- if (this.risingEdge) {
- if (!value) {
- this._timer = 0;
- } else if (this._timer > 0) {
- this._timer = Math.max(this._timer - _deltaTime / 1000, 0);
- this._previousInput = value;
- this._previousOutput = !value;
- return !value;
- } else if (!this._previousInput && value) {
- this._timer = this.t;
- this._previousInput = value;
- this._previousOutput = !value;
- return !value;
- }
- } else if (value) {
- this._timer = 0;
- } else if (this._timer > 0) {
- this._timer = Math.max(this._timer - _deltaTime / 1000, 0);
- this._previousInput = value;
- this._previousOutput = !value;
- return !value;
- } else if (this._previousInput && !value) {
- this._timer = this.t;
- this._previousInput = value;
- this._previousOutput = !value;
- return !value;
- }
- this._previousInput = value;
- this._previousOutput = value;
- return value;
- }
-
- read() {
- return this._previousOutput;
- }
-}
-
-/**
- * The following class represents a flip-flop or memory circuit that can be used to store a single bit. It is inspired
- * by the S+R nodes as described in the ESLD.
- * It has two inputs: Set and Reset. At first it will always emit a falsy value, until it receives a signal on the set
- * input, at which point it will start emitting a truthy value. This will continue until a signal is received on the
- * reset input, at which point it reverts to the original falsy output. It a signal is sent on both set and reset at the
- * same time, the input with a star will have precedence.
- * The NVM flag is not implemented right now but can be used to indicate non-volatile memory storage, which means the
- * value will persist even when power is lost and subsequently restored.
- */
-class NXLogic_MemoryNode {
- setStar: boolean;
-
- nvm: boolean;
-
- _value: boolean;
-
- /**
- * @param setStar Whether set has precedence over reset if both are applied simultaneously.
- * @param nvm Whether the is non-volatile and will be kept even when power is lost.
- */
- constructor(setStar = true, nvm = false) {
- this.setStar = setStar;
- this.nvm = nvm; // TODO in future, reset non-nvm on power cycle
- this._value = false;
- }
-
- write(set, reset) {
- if (set && reset) {
- this._value = this.setStar;
- } else if (set && !this._value) {
- this._value = true;
- } else if (reset && this._value) {
- this._value = false;
- }
- return this._value;
- }
-
- read() {
- return this._value;
- }
-}
diff --git a/fbw-a380x/src/systems/systems-host/systems/LegacyGpws.ts b/fbw-a380x/src/systems/systems-host/systems/LegacyGpws.ts
index 88b61713dbc..becf5e19fc1 100644
--- a/fbw-a380x/src/systems/systems-host/systems/LegacyGpws.ts
+++ b/fbw-a380x/src/systems/systems-host/systems/LegacyGpws.ts
@@ -2,6 +2,8 @@ import { Arinc429SignStatusMatrix, Arinc429Word, NXDataStore, UpdateThrottler }
import { FmgcFlightPhase } from '@shared/flightphase';
import { LegacySoundManager, soundList } from 'systems-host/systems/LegacySoundManager';
import { A380X_DEFAULT_RADIO_AUTO_CALL_OUTS, A380XRadioAutoCallOutFlags } from '../../shared/src/AutoCallOuts';
+import { EventBus } from '@microsoft/msfs-sdk';
+import { FwsSoundManagerControlEvents } from 'systems-host/systems/FlightWarningSystem/FwsSoundManager';
type ModesType = {
current: number;
@@ -12,12 +14,12 @@ type ModesType = {
/**
* This 1:1 port from the A32NX's GPWS+FWS serves as temporary replacement, until a more sophisticated system simulation is in place.
- * After merge of PR #4872 (https://github.com/flybywiresim/aircraft/pull/4872) (intended for A32NX), the FWS architecture has to
- * be ported to the A380X, then the FWS callout parts of this class can be removed.
*/
export class LegacyGpws {
private updateThrottler = new UpdateThrottler(125); // has to be > 100 due to pulse nodes
+ private pub = this.bus.getPublisher();
+
autoCallOutPins: number;
minimumsState = 0;
@@ -51,7 +53,10 @@ export class LegacyGpws {
egpwsAlertDiscreteWord2 = Arinc429Word.empty();
// eslint-disable-next-line camelcase
- constructor(private soundManager: LegacySoundManager) {
+ constructor(
+ private bus: EventBus,
+ private soundManager: LegacySoundManager,
+ ) {
this.autoCallOutPins = A380X_DEFAULT_RADIO_AUTO_CALL_OUTS;
this.minimumsState = 0;
@@ -331,10 +336,10 @@ export class LegacyGpws {
} else if (this.minimumsState === 1 && over100Above) {
this.minimumsState = 2;
} else if (this.minimumsState === 2 && !over100Above) {
- this.soundManager.tryPlaySound(soundList.hundred_above);
+ this.pub.pub('enqueueSound', 'hundred_above');
this.minimumsState = 1;
} else if (this.minimumsState === 1 && !overMinimums) {
- this.soundManager.tryPlaySound(soundList.minimums);
+ this.pub.pub('enqueueSound', 'minimums');
this.minimumsState = 0;
}
}
@@ -578,7 +583,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 6) {
if (this.RetardState.value !== 'retardPlaying' && this.autoCallOutPins & A380XRadioAutoCallOutFlags.Five) {
- this.soundManager.tryPlaySound(soundList.alt_5);
+ this.pub.pub('enqueueSound', 'alt_5');
}
this.AltCallState.action('down');
}
@@ -588,7 +593,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 12) {
if (this.RetardState.value !== 'retardPlaying' && this.autoCallOutPins & A380XRadioAutoCallOutFlags.Ten) {
- this.soundManager.tryPlaySound(soundList.alt_10);
+ this.pub.pub('enqueueSound', 'alt_10');
}
this.AltCallState.action('down');
}
@@ -598,7 +603,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 22) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Twenty) {
- this.soundManager.tryPlaySound(soundList.alt_20);
+ this.pub.pub('enqueueSound', 'alt_20');
}
this.AltCallState.action('down');
}
@@ -608,7 +613,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 32) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Thirty) {
- this.soundManager.tryPlaySound(soundList.alt_30);
+ this.pub.pub('enqueueSound', 'alt_30');
}
this.AltCallState.action('down');
}
@@ -618,7 +623,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 42) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Forty) {
- this.soundManager.tryPlaySound(soundList.alt_40);
+ this.pub.pub('enqueueSound', 'alt_40');
}
this.AltCallState.action('down');
}
@@ -628,7 +633,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 53) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Fifty) {
- this.soundManager.tryPlaySound(soundList.alt_50);
+ this.pub.pub('enqueueSound', 'alt_50');
}
this.AltCallState.action('down');
}
@@ -638,7 +643,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 63) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Sixty) {
- this.soundManager.tryPlaySound(soundList.alt_60);
+ this.pub.pub('enqueueSound', 'alt_60');
}
this.AltCallState.action('down');
}
@@ -648,7 +653,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 73) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Seventy) {
- this.soundManager.tryPlaySound(soundList.alt_70);
+ this.pub.pub('enqueueSound', 'alt_70');
}
this.AltCallState.action('down');
}
@@ -658,7 +663,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 83) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Eighty) {
- this.soundManager.tryPlaySound(soundList.alt_80);
+ this.pub.pub('enqueueSound', 'alt_80');
}
this.AltCallState.action('down');
}
@@ -668,7 +673,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 93) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.Ninety) {
- this.soundManager.tryPlaySound(soundList.alt_90);
+ this.pub.pub('enqueueSound', 'alt_90');
}
this.AltCallState.action('down');
}
@@ -678,7 +683,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 110) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.OneHundred) {
- this.soundManager.tryPlaySound(soundList.alt_100);
+ this.pub.pub('enqueueSound', 'alt_100');
}
this.AltCallState.action('down');
}
@@ -688,7 +693,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 210) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.TwoHundred) {
- this.soundManager.tryPlaySound(soundList.alt_200);
+ this.pub.pub('enqueueSound', 'alt_200');
}
this.AltCallState.action('down');
}
@@ -698,7 +703,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 310) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.ThreeHundred) {
- this.soundManager.tryPlaySound(soundList.alt_300);
+ this.pub.pub('enqueueSound', 'alt_300');
}
this.AltCallState.action('down');
}
@@ -708,7 +713,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 410) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.FourHundred) {
- this.soundManager.tryPlaySound(soundList.alt_400);
+ this.pub.pub('enqueueSound', 'alt_400');
}
this.AltCallState.action('down');
}
@@ -718,7 +723,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 513) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.FiveHundred) {
- this.soundManager.tryPlaySound(soundList.alt_500);
+ this.pub.pub('enqueueSound', 'alt_500');
}
this.AltCallState.action('down');
}
@@ -728,7 +733,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 1020) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.OneThousand) {
- this.soundManager.tryPlaySound(soundList.alt_1000);
+ this.pub.pub('enqueueSound', 'alt_1000');
}
this.AltCallState.action('down');
}
@@ -738,7 +743,7 @@ export class LegacyGpws {
this.AltCallState.action('up');
} else if (radioAlt <= 2020) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.TwoThousand) {
- this.soundManager.tryPlaySound(soundList.alt_2000);
+ this.pub.pub('enqueueSound', 'alt_2000');
}
this.AltCallState.action('down');
}
@@ -746,9 +751,9 @@ export class LegacyGpws {
case 'over2500':
if (radioAlt <= 2530) {
if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.TwoThousandFiveHundred) {
- this.soundManager.tryPlaySound(soundList.alt_2500);
+ this.pub.pub('enqueueSound', 'alt_2500');
} else if (this.autoCallOutPins & A380XRadioAutoCallOutFlags.TwentyFiveHundred) {
- this.soundManager.tryPlaySound(soundList.alt_2500b);
+ this.pub.pub('enqueueSound', 'alt_2500b');
}
this.AltCallState.action('down');
}
@@ -762,26 +767,28 @@ export class LegacyGpws {
if (radioAlt < 20) {
if (!SimVar.GetSimVarValue('L:A32NX_AUTOPILOT_ACTIVE', 'Bool')) {
this.RetardState.action('play');
- this.soundManager.addPeriodicSound(soundList.retard, 1.1);
+ this.pub.pub('enqueueSound', 'retard');
} else if (radioAlt < 10) {
this.RetardState.action('play');
- this.soundManager.addPeriodicSound(soundList.retard, 1.1);
+ this.pub.pub('enqueueSound', 'retard');
}
}
break;
case 'retardPlaying':
if (
SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:1', 'number') < 2.6 ||
- SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:2', 'number') < 2.6
+ SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:2', 'number') < 2.6 ||
+ SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:3', 'number') < 2.6 ||
+ SimVar.GetSimVarValue('L:A32NX_AUTOTHRUST_TLA:4', 'number') < 2.6
) {
this.RetardState.action('land');
- this.soundManager.removePeriodicSound(soundList.retard);
+ this.pub.pub('dequeueSound', 'retard');
} else if (
SimVar.GetSimVarValue('L:A32NX_FMGC_FLIGHT_PHASE', 'Enum') === FmgcFlightPhase.GoAround ||
radioAlt > 20
) {
this.RetardState.action('go_around');
- this.soundManager.removePeriodicSound(soundList.retard);
+ this.pub.pub('dequeueSound', 'retard');
}
break;
case 'landed':
diff --git a/fbw-a380x/src/systems/systems-host/systems/LegacySoundManager.ts b/fbw-a380x/src/systems/systems-host/systems/LegacySoundManager.ts
index 8512cb125ad..25516bb3c9a 100644
--- a/fbw-a380x/src/systems/systems-host/systems/LegacySoundManager.ts
+++ b/fbw-a380x/src/systems/systems-host/systems/LegacySoundManager.ts
@@ -146,92 +146,4 @@ export const soundList: Record = {
name: 'aural_too_low_terrain',
length: 0.9,
},
- minimums: {
- name: 'aural_minimumnew',
- length: 0.67,
- },
- hundred_above: {
- name: 'aural_100above',
- length: 0.72,
- },
- retard: {
- name: 'new_retard',
- length: 0.9,
- },
- alt_2500: {
- name: 'new_2500',
- length: 1.1,
- },
- alt_2500b: {
- name: 'new_2_500',
- length: 1.047,
- },
- alt_2000: {
- name: 'new_2000',
- length: 0.72,
- },
- alt_1000: {
- name: 'new_1000',
- length: 0.9,
- },
- alt_500: {
- name: 'new_500',
- length: 0.6,
- },
- alt_400: {
- name: 'new_400',
- length: 0.6,
- },
- alt_300: {
- name: 'new_300',
- length: 0.6,
- },
- alt_200: {
- name: 'new_200',
- length: 0.6,
- },
- alt_100: {
- name: 'new_100',
- length: 0.6,
- },
- alt_90: {
- name: '90_380',
- length: 0.4,
- },
- alt_80: {
- name: '80_380',
- length: 0.4,
- },
- alt_70: {
- name: '70_380',
- length: 0.4,
- },
- alt_60: {
- name: '60_380',
- length: 0.4,
- },
- alt_50: {
- name: '50_380',
- length: 0.4,
- },
- alt_40: {
- name: '40_380',
- length: 0.4,
- },
- alt_30: {
- name: '30_380',
- length: 0.4,
- },
- alt_20: {
- name: '20_380',
- length: 0.4,
- },
- alt_10: {
- name: '10_380',
- length: 0.3,
- },
- alt_5: {
- name: '5_380',
- length: 0.3,
- },
};
diff --git a/fbw-a380x/src/wasm/fbw_a380/src/FlyByWireInterface.cpp b/fbw-a380x/src/wasm/fbw_a380/src/FlyByWireInterface.cpp
index 10c137cb3ce..5850fa32186 100644
--- a/fbw-a380x/src/wasm/fbw_a380/src/FlyByWireInterface.cpp
+++ b/fbw-a380x/src/wasm/fbw_a380/src/FlyByWireInterface.cpp
@@ -332,7 +332,7 @@ void FlyByWireInterface::setupLocalVariables() {
idFmaSpeedProtectionActive = std::make_unique("A32NX_FMA_SPEED_PROTECTION_MODE");
idFmaSoftAltModeActive = std::make_unique("A32NX_FMA_SOFT_ALT_MODE");
idFmaCruiseAltModeActive = std::make_unique("A32NX_FMA_CRUISE_ALT_MODE");
- idFmaApproachCapability = std::make_unique("A32NX_ApproachCapability");
+ idFmaApproachCapability = std::make_unique("A32NX_APPROACH_CAPABILITY");
idFmaTripleClick = std::make_unique("A32NX_FMA_TRIPLE_CLICK");
idFmaModeReversion = std::make_unique("A32NX_FMA_MODE_REVERSION");
diff --git a/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.cpp b/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.cpp
index 0ea0c773bcd..18dd71601b0 100644
--- a/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.cpp
+++ b/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.cpp
@@ -622,6 +622,7 @@ bool SimConnectInterface::prepareSimInputSimConnectDataDefinitions() {
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTOPILOT_DISENGAGE_SET, "AUTOPILOT_DISENGAGE_SET", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTOPILOT_DISENGAGE_TOGGLE, "AUTOPILOT_DISENGAGE_TOGGLE", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::TOGGLE_FLIGHT_DIRECTOR, "TOGGLE_FLIGHT_DIRECTOR", false);
+ result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_AUTOPILOT_DISENGAGE, "A32NX.AUTOPILOT_DISENGAGE", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_FCU_AP_1_PUSH, "A32NX.FCU_AP_1_PUSH", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_FCU_AP_2_PUSH, "A32NX.FCU_AP_2_PUSH", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_FCU_AP_DISCONNECT_PUSH, "A32NX.FCU_AP_DISCONNECT_PUSH", false);
@@ -693,6 +694,7 @@ bool SimConnectInterface::prepareSimInputSimConnectDataDefinitions() {
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTO_THROTTLE_ARM, "AUTO_THROTTLE_ARM", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTO_THROTTLE_DISCONNECT, "AUTO_THROTTLE_DISCONNECT", true);
+ result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_AUTO_THROTTLE_DISCONNECT, "A32NX.AUTO_THROTTLE_DISCONNECT", false);
result &= addInputDataDefinition(hSimConnect, 0, Events::AUTO_THROTTLE_TO_GA, "AUTO_THROTTLE_TO_GA", true);
result &= addInputDataDefinition(hSimConnect, 0, Events::A32NX_ATHR_RESET_DISABLE, "A32NX.ATHR_RESET_DISABLE", false);
@@ -2216,7 +2218,7 @@ void SimConnectInterface::processEventWithOneParam(const DWORD eventId, const DW
std::cout << "WASM: event triggered: AUTOPILOT_DISENGAGE_SET" << std::endl;
// Re emitting masked event for autopilot disconnection
- execute_calculator_code("(>K:A32NX.AUTOPILOT_DISENGAGE)", nullptr, nullptr, nullptr);
+ sendEvent(SimConnectInterface::Events::A32NX_AUTOPILOT_DISENGAGE, 0, SIMCONNECT_GROUP_PRIORITY_STANDARD);
}
break;
}
@@ -2678,7 +2680,7 @@ void SimConnectInterface::processEventWithOneParam(const DWORD eventId, const DW
std::cout << "WASM: event triggered: AUTO_THROTTLE_DISCONNECT" << std::endl;
// Re emitting masked event for autobrake disconnection
- execute_calculator_code("(>K:A32NX.AUTO_THROTTLE_DISCONNECT)", nullptr, nullptr, nullptr);
+ sendEvent(Events::A32NX_AUTO_THROTTLE_DISCONNECT, 0, SIMCONNECT_GROUP_PRIORITY_STANDARD);
break;
}
diff --git a/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.h b/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.h
index a97dd8195f0..b5c6093f39f 100644
--- a/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.h
+++ b/fbw-a380x/src/wasm/fbw_a380/src/interface/SimConnectInterface.h
@@ -48,6 +48,7 @@ class SimConnectInterface {
AUTOPILOT_DISENGAGE_SET,
AUTOPILOT_DISENGAGE_TOGGLE,
TOGGLE_FLIGHT_DIRECTOR,
+ A32NX_AUTOPILOT_DISENGAGE,
A32NX_FCU_AP_1_PUSH,
A32NX_FCU_AP_2_PUSH,
A32NX_FCU_AP_DISCONNECT_PUSH,
@@ -116,6 +117,7 @@ class SimConnectInterface {
AP_MACH_HOLD,
AUTO_THROTTLE_ARM,
AUTO_THROTTLE_DISCONNECT,
+ A32NX_AUTO_THROTTLE_DISCONNECT,
AUTO_THROTTLE_TO_GA,
A32NX_ATHR_RESET_DISABLE,
A32NX_THROTTLE_MAPPING_SET_DEFAULTS,
diff --git a/fbw-a380x/src/wasm/systems/a380_systems/Cargo.toml b/fbw-a380x/src/wasm/systems/a380_systems/Cargo.toml
index c46d3dd2567..b60a90b5af0 100644
--- a/fbw-a380x/src/wasm/systems/a380_systems/Cargo.toml
+++ b/fbw-a380x/src/wasm/systems/a380_systems/Cargo.toml
@@ -6,15 +6,15 @@ edition = "2021"
[dependencies]
uom = "0.36.0"
-nalgebra = "0.25.0"
-ntest = "0.7.2"
+nalgebra = "0.33.0"
+ntest = "0.9.3"
fxhash = "0.2.1"
rand = "0.8.0"
-serde = { version = "1.0.210", features = ["derive"] }
-serde_with = { version = "3.9.0", features = ["std"] }
+serde = { version = "1.0.215", features = ["derive"] }
+serde_with = { version = "3.11.0", features = ["std"] }
toml = { version = "0.8.19", features = ["parse"] }
systems = { path = "../../../../../fbw-common/src/wasm/systems/systems" }
[dev-dependencies]
-rstest = "0.10.0"
+rstest = "0.12.0"
rand_pcg = "0.3.1"
diff --git a/fbw-common/src/systems/shared/src/GPUManagement.ts b/fbw-common/src/systems/shared/src/GPUManagement.ts
index 121ec976fb5..7478cf2993f 100644
--- a/fbw-common/src/systems/shared/src/GPUManagement.ts
+++ b/fbw-common/src/systems/shared/src/GPUManagement.ts
@@ -8,6 +8,7 @@ import {
Instrument,
MappedSubject,
SimVarValueType,
+ Subject,
Wait,
} from '@microsoft/msfs-sdk';
import { GroundSupportEvents, MsfsElectricsEvents, MsfsFlightModelEvents, MsfsMiscEvents } from '@flybywiresim/fbw-sdk';
@@ -28,10 +29,19 @@ export class GPUManagement implements Instrument {
private readonly groundVelocity = ConsumerSubject.create(this.sub.on('msfs_ground_velocity'), 0);
+ private readonly cameraState = Subject.create(-1);
+
private readonly msfsExtPowerAvailStates = new Map>();
private readonly ExtPowerAvailStates = new Map>();
+ // state 2 is cockpit, state 3 is external
+ private readonly isIngame = MappedSubject.create(
+ ([gameState, cameraState]) => gameState === GameState.ingame && (cameraState === 2 || cameraState === 3),
+ GameStateProvider.get(),
+ this.cameraState,
+ );
+
private initialIngameFrame: boolean;
constructor(
private readonly bus: EventBus,
@@ -50,7 +60,7 @@ export class GPUManagement implements Instrument {
}
public init(): void {
- Wait.awaitSubscribable(GameStateProvider.get(), (state) => state === GameState.ingame, true).then(() => {
+ Wait.awaitSubscribable(this.isIngame, (state) => state, true).then(() => {
this.sub.on('gpu_toggle').handle(this.toggleGPU.bind(this));
this.gpuHookedUp.sub((v) => this.setEXTpower(v));
this.groundVelocity.sub((v) => {
@@ -69,6 +79,8 @@ export class GPUManagement implements Instrument {
this.setEXTpower(true);
}
this.initialIngameFrame = false;
+ } else {
+ this.cameraState.set(SimVar.GetSimVarValue('CAMERA STATE', 'enum'));
}
}
diff --git a/fbw-common/src/wasm/systems/systems/Cargo.toml b/fbw-common/src/wasm/systems/systems/Cargo.toml
index 8cef5e3b790..cbf6fe68a0a 100644
--- a/fbw-common/src/wasm/systems/systems/Cargo.toml
+++ b/fbw-common/src/wasm/systems/systems/Cargo.toml
@@ -9,13 +9,13 @@ uom = "0.36.0"
rand = { version = "0.8.0", features = ["small_rng"] }
rand_distr = "0.4.3"
rand_pcg = "0.3.1"
-ntest = "0.7.2"
-num-derive = "0.3.3"
-num-traits = "0.2.14"
-nalgebra = "0.25.0"
+ntest = "0.9.3"
+num-derive = "0.4.2"
+num-traits = "0.2.19"
+nalgebra = "0.33.0"
bounded-vec-deque = "0.1.1"
fxhash = "0.2.1"
bitflags = "1.3.2"
[dev-dependencies]
-rstest = "0.10.0"
+rstest = "0.12.0"
diff --git a/fbw-common/src/wasm/systems/systems_wasm/src/electrical.rs b/fbw-common/src/wasm/systems/systems_wasm/src/electrical.rs
index ab9e677cdc9..4e6ac67c301 100644
--- a/fbw-common/src/wasm/systems/systems_wasm/src/electrical.rs
+++ b/fbw-common/src/wasm/systems/systems_wasm/src/electrical.rs
@@ -1,35 +1,42 @@
#[cfg(not(target_arch = "wasm32"))]
-use crate::msfs::{legacy::execute_calculator_code, legacy::trigger_key_event};
+use crate::msfs::{legacy::trigger_key_event, legacy::trigger_key_event_ex1};
#[cfg(target_arch = "wasm32")]
-use msfs::{legacy::execute_calculator_code, legacy::trigger_key_event};
+use msfs::{legacy::trigger_key_event, legacy::trigger_key_event_ex1};
use crate::{ExecuteOn, MsfsAspectBuilder, Variable};
use msfs::sys::{
- KEY_APU_BLEED_AIR_SOURCE_SET, KEY_APU_OFF_SWITCH, KEY_APU_STARTER, KEY_FUELSYSTEM_PUMP_OFF,
- KEY_FUELSYSTEM_PUMP_ON, KEY_FUELSYSTEM_VALVE_CLOSE, KEY_FUELSYSTEM_VALVE_OPEN,
+ KEY_APU_BLEED_AIR_SOURCE_SET, KEY_APU_OFF_SWITCH, KEY_APU_STARTER,
+ KEY_ELECTRICAL_BUS_TO_BUS_CONNECTION_TOGGLE, KEY_FUELSYSTEM_PUMP_OFF, KEY_FUELSYSTEM_PUMP_ON,
+ KEY_FUELSYSTEM_VALVE_CLOSE, KEY_FUELSYSTEM_VALVE_OPEN, KEY_WING_FOLD_SET,
};
use std::error::Error;
use systems::shared::{to_bool, ElectricalBusType};
pub(super) fn electrical_buses(
- buses: [(ElectricalBusType, usize); N],
+ buses: [(ElectricalBusType, u32); N],
) -> impl FnOnce(&mut MsfsAspectBuilder) -> Result<(), Box> {
move |builder: &mut MsfsAspectBuilder| {
+ // dummy event to work around bug in MSFS, first event sent does seem to be ignored
+ trigger_key_event_ex1(KEY_WING_FOLD_SET, 0, 0, 0, 0, 0);
for bus in buses {
- const INFINITELY_POWERED_BUS_IDENTIFIER: usize = 1;
- let toggle_code = format!(
- "{} {} (>K:2:ELECTRICAL_BUS_TO_BUS_CONNECTION_TOGGLE)",
- INFINITELY_POWERED_BUS_IDENTIFIER, bus.1
- );
+ const INFINITELY_POWERED_BUS_IDENTIFIER: u32 = 1;
let variable = Variable::named(&format!("ELEC_{}_BUS_IS_POWERED", bus.0));
- // MSFS' starting state has all buses connected.
+
builder.init_variable(variable.clone(), 1.);
+
builder.on_change(
ExecuteOn::PostTick,
vec![variable],
Box::new(move |_, _| {
- execute_calculator_code::<()>(&toggle_code);
+ trigger_key_event_ex1(
+ KEY_ELECTRICAL_BUS_TO_BUS_CONNECTION_TOGGLE,
+ INFINITELY_POWERED_BUS_IDENTIFIER,
+ bus.1,
+ 0,
+ 0,
+ 0,
+ );
}),
);
}
diff --git a/fbw-common/src/wasm/systems/systems_wasm/src/lib.rs b/fbw-common/src/wasm/systems/systems_wasm/src/lib.rs
index 6e5e1982efb..56872764bea 100644
--- a/fbw-common/src/wasm/systems/systems_wasm/src/lib.rs
+++ b/fbw-common/src/wasm/systems/systems_wasm/src/lib.rs
@@ -93,7 +93,7 @@ impl<'a, 'b> MsfsSimulationBuilder<'a, 'b> {
/// as a power source for the other buses which will all be connected to it.
pub fn with_electrical_buses(
self,
- buses: [(ElectricalBusType, usize); N],
+ buses: [(ElectricalBusType, u32); N],
) -> Result> {
self.with_aspect(electrical_buses(buses))
}
diff --git a/fbw-common/src/wasm/systems/systems_wasm/src/msfs.rs b/fbw-common/src/wasm/systems/systems_wasm/src/msfs.rs
index bdf607718e7..62a4b14a6a7 100644
--- a/fbw-common/src/wasm/systems/systems_wasm/src/msfs.rs
+++ b/fbw-common/src/wasm/systems/systems_wasm/src/msfs.rs
@@ -11,6 +11,16 @@ pub(crate) mod legacy {
pub fn trigger_key_event(_event_id: ID32, _value: UINT32) {}
+ pub fn trigger_key_event_ex1(
+ _event_id: ID32,
+ _value0: UINT32,
+ _value1: UINT32,
+ _value2: UINT32,
+ _value3: UINT32,
+ _value4: UINT32,
+ ) {
+ }
+
#[derive(Debug)]
pub struct AircraftVariable {}