#ifdef WORKBENCH // Explicit isolated fixture. Native seating, dismounts, retries and release are // observed; the runway, escaped phase and fault injection are arranged inputs. class ERR_CessnaBoardingFixtureFlight : ERR_PlaneFlight { int TestMode; int Dismounts; int MaximumAttempts; float LastAttemptAt; float MinimumAttemptGap = 100000; bool FaultFailed; protected override bool PrepareCrewSeat(ERR_PlaneCrewSeat entry, int index, float now) { int before = entry.Attempts; bool ready = super.PrepareCrewSeat(entry, index, now); if (index == 0 && entry.Attempts != before) { if (LastAttemptAt > 0) MinimumAttemptGap = Math.Min(MinimumAttemptGap, now - LastAttemptAt); LastAttemptAt = now; MaximumAttempts = entry.Attempts; } if (TestMode == 1 && index == 0 && ready && Dismounts < 3) { CompartmentAccessComponent access = CompartmentAccessComponent.Cast(entry.Actor.FindComponent(CompartmentAccessComponent)); bool accepted = access && access.GetOutVehicle(EGetOutType.TELEPORT, -1, ECloseDoorAfterActions.INVALID, false); PrintFormat("ERR CESSNA INJECT native dismount accepted=%1 attempt=%2", accepted, entry.Attempts); if (!accepted) FaultFailed = true; Dismounts++; return false; } // Keep the capture case in preparation after native seating, so takeover is // tested while retries are still enabled rather than during established flight. if (TestMode >= 2) return false; return ready; } bool OriginalCrewReady() { if (m_CrewSeats.Count() != 2 || Actors.Count() != 2) return false; foreach (ERR_PlaneCrewSeat entry : m_CrewSeats) if (!OwnsCrewSeat(entry) || !CrewSeated(entry) || entry.Agent.GetLOD() != 0 || !entry.Agent.IsAIActivated()) return false; return true; } bool RatesRestored() { vector actual; return Aircraft && !m_HeldInputs && ERR_CessnaBridge.Rates(Aircraft, m_InputRates, actual) && actual == m_InputRates; } void FixtureDelete() { Stop(); foreach (IEntity actor : Actors) if (actor) SCR_EntityHelper.DeleteEntityAndChildren(actor); Actors.Clear(); m_CrewSeats.Clear(); Pilot = null; if (Crew) SCR_EntityHelper.DeleteEntityAndChildren(Crew); Crew = null; if (Aircraft) SCR_EntityHelper.DeleteEntityAndChildren(Aircraft); Aircraft = null; } } modded class ERR_PlaneRecon { void ERR_BoardingFixtureInstall(ERR_PlaneFlight flight) { if (m_Current) m_Current.Stop(); m_Checked = true; m_Enabled = false; m_Current = flight; } } modded class ERR_GameMode { protected ref ERR_CessnaBoardingFixtureFlight m_ERRBoardingFlight; protected ref ERR_CessnaCatalog m_ERRBoardingCatalog; protected ref ERR_PlaneRunway m_ERRBoardingRunway; protected int m_ERRBoardingCase; protected float m_ERRBoardingDeadline, m_ERRBoardingStarted, m_ERRCaptureAt; protected bool m_ERRBoardingReady, m_ERRPilotKilled; protected override void EOnInit(IEntity owner) { super.EOnInit(owner); string enabled, outcome; if (SCR_Global.IsEditMode() || !Replication.IsServer() || !System.GetCLIParam("errBaseSmoke", enabled) || enabled != "1" || !System.GetCLIParam("errSmokeOutcome", outcome) || outcome != "plane-boarding") return; m_ERRBoardingDeadline = System.GetTickCount() + 250000; OnStop().Insert(ERR_BoardingFixtureStop); GetGame().GetCallqueue().CallLater(ERR_BoardingFixtureTick, 100, true); } protected bool ERR_BoardingCheck(bool value, string detail) { if (value) { Print("ERR SMOKE PASS: cessna " + detail); return true; } Print("ERR SMOKE FAIL: cessna " + detail, LogLevel.ERROR); ERR_BoardingFixtureStop(); return false; } protected void ERR_BoardingFixtureStop() { GetGame().GetCallqueue().Remove(ERR_BoardingFixtureTick); if (m_ERRBoardingFlight) m_ERRBoardingFlight.FixtureDelete(); } protected bool ERR_BoardingFixtureStart(int kind, float now) { m_ERRBoardingCase = kind; m_ERRBoardingStarted = now; m_ERRBoardingReady = false; if (m_ERRBoardingFlight) m_ERRBoardingFlight.FixtureDelete(); m_ERRBoardingFlight = new ERR_CessnaBoardingFixtureFlight(); m_ERRBoardingFlight.TestMode = kind; ERR_HQ.Get().PlaneRecon().ERR_BoardingFixtureInstall(m_ERRBoardingFlight); return ERR_BoardingCheck(m_ERRBoardingFlight.Start(this, m_ERRBoardingCatalog.Prefab, m_ERRBoardingRunway.Position, m_ERRBoardingRunway.Heading), "starts original West crew case=" + kind.ToString()); } protected void ERR_BoardingFixtureTick() { if (System.GetTickCount() > m_ERRBoardingDeadline) { ERR_BoardingCheck(false, "overall fixture deadline"); return; } if (!Active() || !ERR_HQ.Get()) return; float now = GetWorld().GetWorldTime(); if (!m_ERRBoardingCatalog) { if (Phase() != ERR_Phase.PRISON || !GetGame().GetPlayerController() || !GetGame().GetPlayerController().GetControlledEntity()) return; if (!ERR_BoardingCheck(EnemyFaction().GetFactionKey() == "US", "normal faction settings selected US/West enemy")) return; if (!ERR_BoardingCheck(ERR_CessnaBridge.Available() && ERR_CessnaBridge.Initialize(), "optional installed addon bridge loads")) return; m_ERRBoardingCatalog = new ERR_CessnaCatalog(); m_ERRBoardingCatalog.Find(); if (!ERR_BoardingCheck(!m_ERRBoardingCatalog.Prefab.IsEmpty(), "installed Cessna prefab resolves")) return; Transition(ERR_Phase.RADIO_SEARCH); if (!ERR_BoardingCheck(Phase() == ERR_Phase.RADIO_SEARCH, "preparation runs after arranged prison escape")) return; m_ERRBoardingRunway = new ERR_PlaneRunway(); return; } if (!m_ERRBoardingFlight) { if (!m_ERRBoardingRunway.Tick()) { if (m_ERRBoardingRunway.Exhausted) ERR_BoardingCheck(false, "native airport survey finds a departure corridor"); return; } PrintFormat("ERR CESSNA RUNWAY position=%1 heading=%2", m_ERRBoardingRunway.Position, m_ERRBoardingRunway.Heading); ERR_BoardingFixtureStart(0, now); return; } if (m_ERRBoardingCase == 0) { if (m_ERRBoardingFlight.Lost || m_ERRBoardingFlight.Captured) { ERR_BoardingCheck(false, "normal flight retains crew ownership"); return; } if (!m_ERRBoardingReady && m_ERRBoardingFlight.OriginalCrewReady()) { m_ERRBoardingReady = true; if (!ERR_BoardingCheck(true, "both original West crew occupy exact assigned seats with LOD0 and active agents")) return; } if (!m_ERRBoardingFlight.Airborne()) return; if (!ERR_BoardingCheck(m_ERRBoardingReady && m_ERRBoardingFlight.EnteredService(), "native engine start and airport takeoff after verified seating")) return; ERR_BoardingFixtureStart(1, now); return; } if (m_ERRBoardingCase == 1) { if (m_ERRBoardingFlight.FaultFailed) { ERR_BoardingCheck(false, "native dismount fault injection accepted"); return; } if (m_ERRBoardingFlight.EnteredService()) { ERR_BoardingCheck(false, "unseated pilot must block service"); return; } if (!m_ERRBoardingFlight.Lost) return; if (!ERR_BoardingCheck(m_ERRBoardingFlight.Dismounts == 3 && m_ERRBoardingFlight.MaximumAttempts == 3, "three real native seatings/dismounts exhaust the original pilot retry budget")) return; if (!ERR_BoardingCheck(m_ERRBoardingFlight.MinimumAttemptGap >= 5000, "native boarding retries retain five second cooldown")) return; if (!ERR_BoardingCheck(now - m_ERRBoardingStarted >= 45000 && now - m_ERRBoardingStarted < 46500, "original 45 second preparation deadline remains bounded")) return; if (!ERR_BoardingCheck(!m_ERRBoardingFlight.Aircraft && !m_ERRBoardingFlight.Crew && m_ERRBoardingFlight.Actors.IsEmpty(), "failed setup cleans original aircraft and crew")) return; ERR_BoardingFixtureStart(2, now); return; } if (m_ERRBoardingCase == 3) { if (m_ERRBoardingFlight.Captured) { ERR_BoardingCheck(false, "dead original pilot is a preparation failure, not capture"); return; } if (!m_ERRPilotKilled) { if (!m_ERRBoardingFlight.OriginalCrewReady()) return; DamageManagerComponent damage = DamageManagerComponent.Cast(m_ERRBoardingFlight.Pilot.FindComponent(DamageManagerComponent)); if (!ERR_BoardingCheck(damage != null, "original pilot damage manager resolves")) return; damage.SetHealthScaled(0); m_ERRPilotKilled = true; Print("ERR CESSNA INJECT original pilot killed during preparation"); return; } if (!m_ERRBoardingFlight.Lost) return; if (!ERR_BoardingCheck(!m_ERRBoardingFlight.EnteredService() && !m_ERRBoardingFlight.Aircraft && !m_ERRBoardingFlight.Crew, "dead pilot reaches normal preparation failure and cleanup without a replacement actor")) return; ERR_BoardingFixtureStop(); Print("ERR SMOKE COMPLETE: cessna West crew native seating after escaped phase, bounded dismount/retry failure, preparation capture release and dead pilot cleanup; arranged fixture, not multiplayer qualification"); return; } if (m_ERRCaptureAt == 0) { if (m_ERRBoardingFlight.Lost) { ERR_BoardingCheck(false, "capture setup survives native preparation"); return; } if (!m_ERRBoardingFlight.OriginalCrewReady()) return; if (!ERR_BoardingCheck(!m_ERRBoardingFlight.EnteredService() && ERR_Actors.SetFaction(m_ERRBoardingFlight.Pilot, PlayerFaction()), "arranges pilot faction takeover during preparation")) return; m_ERRCaptureAt = now; return; } if (now - m_ERRCaptureAt < 5500) return; m_ERRBoardingFlight.CancelSetup(); if (!ERR_BoardingCheck(m_ERRBoardingFlight.Captured && !m_ERRBoardingFlight.Lost && !m_ERRBoardingFlight.EnteredService(), "preparation takeover releases before another retry")) return; if (!ERR_BoardingCheck(ERR_Actors.Alive(m_ERRBoardingFlight.Aircraft) && m_ERRBoardingFlight.Actors.Count() == 2 && m_ERRBoardingFlight.RatesRestored(), "takeover preserves aircraft/crew and restores original controls")) return; ERR_BoardingFixtureStart(3, now); } } #endif