/// <summary> /// Retrieves the most overriden part for the UID provided /// </summary> /// <param name="uid">A part UID to search</param> /// <returns>The most overriden useable part, or null if the specified UID cannot be used or does not exist</returns> public IGCCorePart GetOverriddenPart(ushort uid) { IGCCorePart Result = null; BitArray CurrentTech = _team.CalculateDefs(); BitArray WorkingTech; IGCCorePart Part = (IGCCorePart)_team.Game.Core.Parts.GetObject(uid); if (Part != null) { do { WorkingTech = (BitArray)CurrentTech.Clone(); WorkingTech.And(Part.Techtree.Pres); if (!Part.Techtree.PreEquals(WorkingTech)) { break; // This part is unavailable! Stop looking } Result = Part; Part = (IGCCorePart)_team.Game.Core.Parts.GetObject((ushort)Part.OverridingUID); } while (Part != null); } return(Result); }
private void ReadFromFile(string fileName) { // try // { FileStream CoreFS = File.OpenRead(fileName); DataReader Reader = new DataReader(CoreFS); int Size; int CoreSize; short Tag; _coreHeader = Reader.ReadUInt(); CoreSize = Reader.ReadInt(); while (CoreFS.Position < (CoreSize + 8)) { Tag = Reader.ReadShort(); Size = Reader.ReadInt(); long Pos = CoreFS.Position; switch ((AGCObjectType)Tag) { case AGCObjectType.AGC_Constants: // 21 _coreConstants = new IGCCoreConstants(Reader); break; case AGCObjectType.AGC_StationType: // 31; _stationTypes.Add(new IGCCoreStationType(Reader)); break; case AGCObjectType.AGC_Civilization: // 27 _civs.Add(new IGCCoreCiv(Reader)); break; case AGCObjectType.AGC_Development: // 32 _devs.Add(new IGCCoreDevel(Reader)); break; case AGCObjectType.AGC_BucketStart: //29 _ships.Add(new IGCCoreShip(Reader)); break; case AGCObjectType.AGC_PartType: //30 IGCCorePart Part = null; if (Size == 24) { // It's a spec part. Look up the real part and add it instead IGCCorePartSpec Spec = new IGCCorePartSpec(Reader); ushort PartID = Spec.UID; ushort RealID = (ushort)Spec.Group; IGCCorePart Obj = null; switch (Spec.Slot) { case "invchaff": Obj = (IGCCorePart)_chaffs.GetObject(RealID); IGCCoreCounter Counter = (IGCCoreCounter)Obj; Counter.OverridingUID = Spec.OverridingUID; break; case "invsmissile": Obj = (IGCCorePart)_missiles.GetObject(RealID); IGCCoreMissile Missile = (IGCCoreMissile)Obj; Missile.OverridingUID = Spec.OverridingUID; Missile.LaunchCount = (short)Spec.PartType; Missile.QtyPerPack = (short)Spec.Amount; break; case "invsmine": Obj = (IGCCorePart)_mines.GetObject(RealID); if (Obj == null) { Obj = (IGCCorePart)_probes.GetObject(RealID); IGCCoreProbe Probe = (IGCCoreProbe)Obj; Probe.OverridingUID = Spec.OverridingUID; } else { IGCCoreMine Mine = (IGCCoreMine)Obj; Mine.OverridingUID = Spec.OverridingUID; } break; } if (Obj != null) { Obj.SpecUID = PartID; _parts.Add(Obj); } break; } Reader.Seek(376); short Type = Reader.ReadShort(); Reader.Seek(-378); // 1 = weapon, 2 = shield, 5 = cloak, 7 = after, 6 = default switch (Type) { case 1: Part = new IGCCorePartWeapon(Reader); break; case 2: //Part = new IGCCorePartShield(Reader); break; case 4: Part = new IGCCorePartShield(Reader); break; case 5: Part = new IGCCorePartCloak(Reader); break; case 7: Part = new IGCCorePartAfterburner(Reader); break; case 6: Part = new IGCCorePartPack(Reader); break; default: break; } if (Part != null) { _parts.Add(Part); } break; case AGCObjectType.AGC_ChaffType: // 26 _chaffs.Add(new IGCCoreCounter(Reader)); break; case AGCObjectType.AGC_MissileType: // 23 _missiles.Add(new IGCCoreMissile(Reader)); break; case AGCObjectType.AGC_MineType: // 24 _mines.Add(new IGCCoreMine(Reader)); break; case AGCObjectType.AGC_DroneType: _drones.Add(new IGCCoreDrone(Reader)); break; case AGCObjectType.AGC_ProbeType: _probes.Add(new IGCCoreProbe(Reader)); break; case AGCObjectType.AGC_ProjectileType: //22 _projectiles.Add(new IGCCoreProjectile(Reader)); break; case AGCObjectType.AGC_TreasureSet: _treasureSets.Add(new IGCCoreTreasureSet(Reader)); break; default: break; } if (CoreFS.Position != Pos + Size) { throw new Exception("Error occured while reading core file"); } } CoreFS.Close(); Reader = null; // } // catch (Exception e) // { // return; // } return; }
/// <summary> /// Determines whether or not this ship can mount the specified part /// </summary> /// <param name="part"></param> /// <returns></returns> public bool CanMountPart(IGCCorePart part, ShipSlots slot) { if (part == null) { return(CanUseSlot(slot)); } bool Result = false; BitArray SlotMask = null; // Find which SlotMask we need to compare int MaskIndex = -1; switch (part.ModuleType) { case AGCObjectType.AGC_ChaffType: if (slot == ShipSlots.Chaff || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Counter; } break; case AGCObjectType.AGC_MineType: if (slot == ShipSlots.Pack || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Pack; } break; case AGCObjectType.AGC_MissileType: if (slot == ShipSlots.Missile || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Missile; } break; case AGCObjectType.AGC_ProbeType: if (slot == ShipSlots.Pack || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Pack; } break; case AGCObjectType.AGC_PartType: switch (part.PartType) { case PartType.Afterburner: if (slot == ShipSlots.Booster || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Booster; } break; case PartType.Cloak: if (slot == ShipSlots.Cloak || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Cloak; } break; case PartType.Shield: if (slot == ShipSlots.Shield || (int)slot > 15) { MaskIndex = (int)ShipUseMasks.Shield; } break; case PartType.Pack: if ((int)slot < 16) // You can't mount ammo or fuel in bays { return(false); } else { SlotMask = new BitArray(16, true); } break; case PartType.Weapon: int Slot = (int)slot; if (Slot >= 8 && Slot < 16) { return(false); } if (Slot < 8) { if (_ship.WeaponMounts.Length == 0) { return(false); } if (Slot < 4) { SlotMask = (BitArray)_ship.WeaponMounts[Slot].PartMask.Clone(); } else { SlotMask = (BitArray)_ship.WeaponMounts[GetWeaponCount() + (Slot - 4)].PartMask.Clone(); } } else { SlotMask = new BitArray(16, true); } break; default: break; } break; default: break; } // Get the required slot mask for comparison if it isn't a gun/turret if (SlotMask == null) { if (MaskIndex == -1) { return(false); } SlotMask = (BitArray)_ship.UseMasks[MaskIndex].Clone(); } SlotMask.And(part.UseMask); // Check if part matches the slot mask if (Techtree.BitArrayEquals(SlotMask, part.UseMask) || (int)slot > 15) { // Part can be mounted. Is it available? BitArray CurrentDefs = _team.CalculateDefs(); CurrentDefs.And(part.Techtree.Pres); if (part.Techtree.PreEquals(CurrentDefs)) { Result = true; } } return(Result); }
public void AssignDefaultCargo() { // Add the default parts foreach (short id in _ship.DefaultLoadout) { if (id == -1) { continue; } IGCCorePart Part = GetOverriddenPart((ushort)id); // If the part doesn't exist, skip it if (Part == null) { continue; } if (Part is IGCCoreCounter && _chaff == null) { if (CanMountPart(Part, ShipSlots.Chaff)) { _chaff = (IGCCoreCounter)Part; } } if (Part is IGCCoreMine && _pack == null) { if (CanMountPart(Part, ShipSlots.Pack)) { _pack = Part; } } if (Part is IGCCoreMissile && _missile == null) { if (CanMountPart(Part, ShipSlots.Missile)) { _missile = (IGCCoreMissile)Part; } } if (Part is IGCCoreProbe && _pack == null) { if (CanMountPart(Part, ShipSlots.Pack)) { _pack = Part; } } if (Part is IGCCorePartAfterburner && _booster == null) { if (CanMountPart(Part, ShipSlots.Booster)) { _booster = (IGCCorePartAfterburner)Part; } } if (Part is IGCCorePartCloak && _cloak == null) { if (CanMountPart(Part, ShipSlots.Cloak)) { _cloak = (IGCCorePartCloak)Part; } } if (Part is IGCCorePartShield && _shield == null) { if (CanMountPart(Part, ShipSlots.Shield)) { _shield = (IGCCorePartShield)Part; } } if (Part is IGCCorePartWeapon) { int WeaponIndex = 0; int TurretIndex = 0; for (int i = 0; i < _ship.WeaponMounts.Length; i++) { IGCCoreShipMP Mount = _ship.WeaponMounts[i]; if (Mount.PartType == 1) { // it's a weapon if (CanMountPart(Part, (ShipSlots)(WeaponIndex))) { if (_weapons[WeaponIndex] == null) { _weapons[WeaponIndex] = (IGCCorePartWeapon)Part; } } WeaponIndex++; } else { // It's a turret! if (CanMountPart(Part, (ShipSlots)(TurretIndex + 4))) { if (_turrets[TurretIndex] == null) { _turrets[TurretIndex] = (IGCCorePartWeapon)Part; } } TurretIndex++; } } } } // Add default cargo bool AmmoRequired = (_ship.WeaponMounts.Length > 0); bool FuelRequired = CanUseSlot(ShipSlots.Booster); int SlotIndex = 0; // Add Slot 1: Missile, Pack, Fuel, Ammo, empty if (CanUseSlot(ShipSlots.Missile) && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = _missile; } if (CanUseSlot(ShipSlots.Pack) == true && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = _pack; } if (FuelRequired && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = FuelPack; } if (AmmoRequired == true && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = AmmoPack; } SlotIndex++; // Add Slot 2: (Pack), (Missile), Ammo, Fuel, empty if (_cargo[0] != _pack && CanUseSlot(ShipSlots.Pack) && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = _pack; } if (_cargo[0] != _missile && CanUseSlot(ShipSlots.Missile) && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = _missile; } if (AmmoRequired == true && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = AmmoPack; } if (FuelRequired && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = FuelPack; } SlotIndex++; // Add Slot 3: Fuel, ammo, empty if (FuelRequired && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = FuelPack; } if (AmmoRequired == true && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = AmmoPack; } SlotIndex++; // Add Slot 4: ammo, fuel, empty if (AmmoRequired && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = AmmoPack; } if (FuelRequired && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = FuelPack; } SlotIndex++; // Add Slot 5: fuel, ammo, empty if (FuelRequired && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = FuelPack; } if (AmmoRequired == true && _cargo[SlotIndex] == null) { _cargo[SlotIndex] = AmmoPack; } }