internal void Update() { if (timeSinceSpoken == -2) { if (DuckUtils.GetNearestPlayerToPosition(speaker.GetPosition(), 3000) != null) { audioSystem.PlayAudio(CalAudioClip.GreetingsMartianColonists); timeSinceSpoken = -1; } return; } var playerVisiting = DuckUtils.GetNearestPlayerToPosition(speaker.GetPosition(), 50) != null; if (timeSinceSpoken == -1 && playerVisiting) { audioSystem.PlayAudio(CalAudioClip.WelcomeMikiScrap); timeSinceSpoken = AudioCommentTime; } else if (timeSinceSpoken >= 0 && timeSinceSpoken < AudioMaxTime) { timeSinceSpoken++; } else if (timeSinceSpoken == AudioMaxTime && playerVisiting) { audioSystem.PlayAudioRandomChance(1.0, CalAudioClip.TellAllFriends, CalAudioClip.TiredOfGrindingCrap, CalAudioClip.NewMikiScrapsOpen); timeSinceSpoken = AudioCommentTime; } var scrap = scrapIn.GetItemAmount(scrapMetal); if (scrap > 0) { ProcessScrap(scrap > 500 ? 500 : scrap); } if (playerVisiting) { UpdateFurnaceState(); } }
internal void SpawnConvoy() { var baseToSpawnAt = ChooseSpawningBase(); if (baseToSpawnAt != null) { CalFactions.Gcorp.Ships.SpawnConvoyTransport(baseToSpawnAt); //TODO make this work for any faction audioSystem.PlayAudioRandomChance(0.1, CalAudioClip.ConvoyDispatched1, CalAudioClip.ConvoyDispatched2, CalAudioClip.ConvoyDispatched3); } }
private void GiveOrdersToUnassignedShips() { bool bFoundBackup = false; while (unitialisedNewGrids.Count > 0) { var grid = unitialisedNewGrids.Dequeue(); if (!grid.IsControlledByFaction("GCORP")) { continue; } var roleAndUnitType = PrefabGrid.GetRoleAndUnitType(grid); if (roleAndUnitType == null) { // V26 debug ModLog.Info("Discarding grid because no role found"); continue; } var unitType = roleAndUnitType.Value.UnitType; switch (roleAndUnitType.Value.UnitRole) { case UnitRole.Delivery: var cargoType = CargoType.GenerateRandomCargo(random); LoadCargo(grid, cargoType); if (cargoType.subtypeName == "SteelPlate") { audioSystem.PlayAudioRandomChance(0.1, AudioClip.SteelPlateConvoyDispatched, AudioClip.ConvoyDispatched1); } else if (cargoType.subtypeName == "MetalGrid") { audioSystem.PlayAudioRandomChance(1, AudioClip.MetalGridConvoyDispatched); } else if (cargoType.subtypeName == "Construction") { audioSystem.PlayAudioRandomChance(0.1, AudioClip.ConstructionConvoyDispatched); } else if (cargoType.subtypeName == "InteriorPlate") { audioSystem.PlayAudioRandomChance(0.1, AudioClip.InteriorPlateConvoyDispatched); } else if (cargoType.subtypeName == "Girder") { audioSystem.PlayAudioRandomChance(0.1, AudioClip.GirderConvoyDispatched); } else if (cargoType.subtypeName == "SmallTube") { audioSystem.PlayAudioRandomChance(0.1, AudioClip.SmallTubeConvoyDispatched); } else if (cargoType.subtypeName == "LargeTube") { audioSystem.PlayAudioRandomChance(0.2, AudioClip.LargeTubeConvoyDispatched); } else if (cargoType.subtypeName == "Motor") { audioSystem.PlayAudioRandomChance(0.75, AudioClip.MotorConvoyDispatched); } else if (cargoType.subtypeName == "Display") { audioSystem.PlayAudioRandomChance(0.2, AudioClip.DisplayConvoyDispatched); } else if (cargoType.subtypeName == "BulletproofGlass") { audioSystem.PlayAudioRandomChance(0.3, AudioClip.BulletproofGlassConvoyDispatched); } else if (cargoType.subtypeName == "Computer") { audioSystem.PlayAudioRandomChance(0.2, AudioClip.ComputerConvoyDispatched); } else if (cargoType.subtypeName == "Reactor") { audioSystem.PlayAudioRandomChance(0.75, AudioClip.ReactorConvoyDispatched); } else if (cargoType.subtypeName == "Medical") { audioSystem.PlayAudioRandomChance(0.7, AudioClip.MedicalConvoyDispatched); } else if (cargoType.subtypeName == "RadioCommunication") { audioSystem.PlayAudioRandomChance(0.5, AudioClip.RadioCommunicationConvoyDispatched); } else if (cargoType.subtypeName == "Explosives") { audioSystem.PlayAudioRandomChance(0.5, AudioClip.ExplosivesConvoyDispatched); } else if (cargoType.subtypeName == "SolarCell") { audioSystem.PlayAudioRandomChance(0.5, AudioClip.SolarCellConvoyDispatched); } else if (cargoType.subtypeName == "PowerCell") { audioSystem.PlayAudioRandomChance(0.75, AudioClip.PowerCellConvoyDispatched); } else if (cargoType.subtypeName == "NATO_5p56x45mm") { audioSystem.PlayAudioRandomChance(0.5, AudioClip.NATO_5p56x45mmConvoyDispatched); } else if (cargoType.subtypeName == "NATO_25x184mm") { audioSystem.PlayAudioRandomChance(0.5, AudioClip.NATO25x184mmConvoyDispatched); } else if (cargoType.subtypeName == "Missile200mm") { audioSystem.PlayAudioRandomChance(0.5, AudioClip.Missile200mmConvoyDispatched); } else if (cargoType.subtypeName == "Uranium") { audioSystem.PlayAudioRandomChance(1, AudioClip.UraniumConvoyDispatched); } else // we don't know what it is.. { audioSystem.PlayAudioRandomChance(0.1, AudioClip.ConvoyDispatched1, AudioClip.ConvoyDispatched2, AudioClip.ConvoyDispatched3); } string sPrefix = "T"; if (unitType == UnitType.Air) { sPrefix += "A"; } else { sPrefix += "G"; } grid.SetAllBeaconNames(sPrefix + random.Next(10000, 99999) + " - " + cargoType.GetDisplayName() + " Shipment", 200f); // V31 set short until initialize check timeout var destination = unitType == UnitType.Air ? airConvoyDestinationPosition : groundConvoyDestinationPosition; // ModLog.Info("Air Destination=" + airConvoyDestinationPosition.ToString()); // ModLog.Info("GND Destination=" + groundConvoyDestinationPosition.ToString()); // ModLog.Info("Chosen Dest=" + destination.ToString()); SetDestination(grid, destination); RegisterConvoy(grid, NpcGroupState.Travelling, unitType, destination, MyAPIGateway.Session.GameDateTime); var planet = DuckUtils.FindPlanetInGravity(grid.GetPosition()); if (planet != null) { convoySpawner.SpawnConvoyEscorts(grid, unitType, planet); } break; case UnitRole.Escort: var group = FindNearestJoinableNpcGroup(grid.GetPosition(), unitType); if (group == null) { ModLog.Error("Escort ship spawned but can't find a group to join!"); grid.CloseAll(); } else { grid.SetAllBeaconNames("E" + random.Next(10000, 99999) + " - " + EscortName, 2500f); // V31 shorten escort beacon range to decrease hud spam var nearestPlanet = DuckUtils.FindPlanetInGravity(grid.GetPosition()); if (nearestPlanet != null) { group.JoinAsEscort(grid, unitType, nearestPlanet); } } break; case UnitRole.Backup: var gCorpBase = baseManager.FindBaseWantingBackup(); // V26 bFoundBackup = true; if (gCorpBase == null) { gCorpBase = baseManager.FindBaseNear(grid.GetPosition()); } if (gCorpBase == null) { ModLog.Error("Backup ship spawned but can't find the base that asked for it!"); grid.CloseAll(); break; } var backupPosition = gCorpBase.GetBackupPosition(); grid.SendToPosition(backupPosition); // backup debug string sBeacon = "M" + random.Next(10000, 99999) + " Investigating Backup Call"; // ModLog.Info("Backup Found:" + sBeacon); // ModLog.Info(" Destination=" + backupPosition.ToString()); grid.SetAllBeaconNames(sBeacon, 20000f); var backupGroup = new BackupGroup(NpcGroupState.Travelling, backupPosition, grid, heatSystem, audioSystem, MyAPIGateway.Session.GameDateTime); //damageSensor.RegisterDamageObserver(grid.EntityId, backupGroup); npcGroups.Add(backupGroup); break; case UnitRole.Bomb: bool hasSensors = false; var slimBlocks = new List <IMySlimBlock>(); grid.GetBlocks(slimBlocks, b => b.FatBlock is IMySensorBlock); if (slimBlocks.Count > 0) { hasSensors = true; } grid.GetBlocks(slimBlocks, b => b.FatBlock is IMyWarhead); foreach (var slim in slimBlocks) { var wh = slim.FatBlock as IMyWarhead; wh.IsArmed = true; if (!hasSensors) // if no sensors, start the countdown { ModLog.Info("BOMB: no sensors: Starting timer"); wh.StartCountdown(); } } break; default: continue; } } if (bFoundBackup) { baseManager.ClearBaseBackupRequests(); } }
internal override void Update() { CheckEscortsAlive(); if (!leader.IsControlledByNpcFaction()) { GroupState = NpcGroupState.Disbanding; InitiateDisbandProtocols(); } else if ((GroupState == NpcGroupState.Travelling || GroupState == NpcGroupState.InCombat) && Vector3D.DistanceSquared(Destination, leader.GetPosition()) < 200.0 * 200) // increase to 200 to allow for variations in height. // && Vector3D.Distance(Destination, leader.GetPosition()) < 100.0) { ArrivalObserver.GroupArrivedIntact(); audioSystem.PlayAudioRandomChance(0.1, CalAudioClip.ConvoyArrivedSafely); GroupState = NpcGroupState.Disbanding; InitiateDisbandProtocols(); ResetBeaconNames(); } if (GroupState == NpcGroupState.Disbanding) { AttemptDespawning(); return; } if (DuckUtils.IsAnyPlayerNearPosition(leader.GetPosition(), 1000) && GroupState == NpcGroupState.Travelling) { GroupState = NpcGroupState.InCombat; InitiateAttackProtocols(); } if (GroupState == NpcGroupState.InCombat) { var player = DuckUtils.GetNearestPlayerToPosition(leader.GetPosition(), 4000); if (player == null) { GroupState = NpcGroupState.Travelling; // Return to normal, cowardly players have run off or died ResetBeaconNames(); if (escortDic.Count > 0) //todo maybe check if the escorts are actually alive? Dunno if doing this already { audioSystem.PlayAudio(CalAudioClip.DisengagingFromHostile, CalAudioClip.TargetLost); } else { audioSystem.PlayAudio(CalAudioClip.PursuitEvaded, CalAudioClip.SensorsLostTrack); } } else { SendArmedEscortsNearPosition(player.GetPosition()); // Use same position as when escorting, to avoid collisions } } if (GroupState == NpcGroupState.Travelling) { foreach (var entry in escortDic) { SendEscortToGrid(entry.Key, entry.Value, leader); } } }
internal override void Update() { CheckEscortsAlive(); if (!leader.IsControlledByFaction("GCORP")) { GroupState = NpcGroupState.Disbanding; InitiateDisbandProtocols(); } else if ((GroupState == NpcGroupState.Travelling || GroupState == NpcGroupState.InCombat) && Vector3D.DistanceSquared(Destination, leader.GetPosition()) < 300.0 * 300) // increase to 300 to allow for variations in height. V26 // && Vector3D.DistanceSquared(Destination, leader.GetPosition()) < 200.0*200) // increase to 200 to allow for variations in height. // && Vector3D.Distance(Destination, leader.GetPosition()) < 100.0) { string sBeacons = ""; var slimBlocks2 = new List <IMySlimBlock>(); leader.GetBlocks(slimBlocks2, b => b.FatBlock is IMyBeacon); foreach (var slim2 in slimBlocks2) { var beacon = slim2.FatBlock as IMyBeacon; sBeacons += beacon.CustomName; } ModLog.Info("Group Arrived at destination: " + leader.CustomName + " " + sBeacons); ArrivalObserver.GroupArrivedIntact(); audioSystem.PlayAudioRandomChance(0.1, AudioClip.ConvoyArrivedSafely); GroupState = NpcGroupState.Disbanding; InitiateDisbandProtocols(); ResetBeaconNames(); } // ModLogs are for DEBUG nav script // ModLog.Info("Convoy update:" + leader.CustomName+" ID:"+leader.EntityId.ToString() + " State:"+GroupState.ToString()); if ((GroupState == NpcGroupState.Travelling)) { var currentTime = MyAPIGateway.Session.GameDateTime; if (GroupSpawnTime + convoyInitiateTime < currentTime) { leader.SetAllBeaconNames(null, 20000f); } bool bKeenAutopilotActive = false; var slimBlocks = new List <IMySlimBlock>(); leader.GetBlocks(slimBlocks, b => b.FatBlock is IMyRemoteControl); IMyRemoteControl remoteControl = null; foreach (var slim in slimBlocks) { remoteControl = slim.FatBlock as IMyRemoteControl; bKeenAutopilotActive = remoteControl.IsAutoPilotEnabled; // ModLog.Info("Keen Autopilot:" + bKeenAutopilotActive.ToString()); break; } slimBlocks.Clear(); leader.GetBlocks(slimBlocks, b => b.FatBlock is IMyProgrammableBlock); foreach (var slim in slimBlocks) { var block = slim.FatBlock as IMyProgrammableBlock; if (block == null) { continue; } if (block.CustomName.Contains("NAV")) { if (!bKeenAutopilotActive && GroupSpawnTime + convoyInitiateTime < currentTime // delay check for mode change. ) { if (//!bKeenAutopilotActive && block.DetailedInfo.Contains("mode=0") || block.DetailedInfo.Contains("mode=-1")) { if (remoteControl == null) { // nothing left to do. Remove it (and try again) GroupState = NpcGroupState.Inactive; // this will cause NpcGroupManager to spawn a new convoy to replace this one. return; } // force it to use Keen Autopilot remoteControl.ClearWaypoints(); remoteControl.AddWaypoint(Destination, "Target"); remoteControl.SpeedLimit = 10; remoteControl.SetAutoPilotEnabled(true); /* * // debug output * var slimBlocks2 = new List<IMySlimBlock>(); * leader.GetBlocks(slimBlocks2, b => b.FatBlock is IMyBeacon); * string sBeacons = ""; * foreach(var slim2 in slimBlocks2) * { * var beacon = slim2.FatBlock as IMyBeacon; * sBeacons += beacon.CustomName; * } * * // it didn't get the command! * // GroupState = NpcGroupState.Inactive; // this will cause NpcGroupManager to spawn a new convoy to replace this one. * ModLog.Info("Autopilot recovery because leader NAV not in correct mode: "+ sBeacons); */ } break; } // ModLog.Info("PB:"+block.CustomName+"\n"+"DetailedInfo=:\n" + block.DetailedInfo); } } // Following is just debug info /* * leader.GetBlocks(slimBlocks, b => b.FatBlock is IMyGyro); * foreach (var slim in slimBlocks) * { * var block = slim.FatBlock as IMyGyro; * if (block!=null && block.CustomName.Contains("NAV")) * { * ModLog.Info("G:"+block.CustomName + "\n"); * } * } */ } if (GroupState == NpcGroupState.Disbanding) { AttemptDespawning(); return; } if (DuckUtils.IsAnyPlayerNearPosition(leader.GetPosition(), 1000) && GroupState == NpcGroupState.Travelling) { GroupState = NpcGroupState.InCombat; InitiateAttackProtocols(); } if (GroupState == NpcGroupState.InCombat) { var player = DuckUtils.GetNearestPlayerToPosition(leader.GetPosition(), 4000); if (player == null) { GroupState = NpcGroupState.Travelling; // Return to normal, cowardly players have run off or died ResetBeaconNames(); if (escortDic.Count > 0) //todo maybe check if the escorts are actually alive? Dunno if doing this already { audioSystem.PlayAudio(AudioClip.DisengagingFromHostile, AudioClip.TargetLost); } else { audioSystem.PlayAudio(AudioClip.PursuitEvaded, AudioClip.SensorsLostTrack); } } else { SendArmedEscortsNearPosition(player.GetPosition()); // Use same position as when escorting, to avoid collisions } } if (GroupState == NpcGroupState.Travelling) { foreach (var entry in escortDic) { SendEscortToGrid(entry.Key, entry.Value, leader); } } }