public override void Draw() { base.Draw(); CompPowerBattery comp = base.GetComp <CompPowerBattery>(); GenDraw.FillableBarRequest r = default(GenDraw.FillableBarRequest); r.center = this.DrawPos + Vector3.up * 0.1f; r.size = Building_StuffedBattery.BarSize; r.fillPercent = comp.StoredEnergy / comp.Props.storedEnergyMax; r.filledMat = Building_StuffedBattery.BarFilledMat; r.unfilledMat = Building_StuffedBattery.BarUnfilledMat; r.margin = 0.15f; Rot4 rotation = base.Rotation; rotation.Rotate(RotationDirection.Clockwise); r.rotation = rotation; GenDraw.DrawFillableBar(r); if (this.ticksToExplode > 0 && base.Spawned) { base.Map.overlayDrawer.DrawOverlay(this, OverlayTypes.BurningWick); } }
/* * public override void CompTick() * { * if (GenTicks.TicksGame % GenTicks.TickLongInterval == 0) * { * HistoricalPowerUsage.Add(GenTicks.TicksGame, PowerUsage); * HistoricalUptime.Add(GenTicks.TicksGame, Uptime); * HistoricalUsetime.Add(GenTicks.TicksGame, Usetime); * } * } * * public override void CompTickRare() * { * if (GenTicks.TicksGame % GenTicks.TickLongInterval == 0) * { * HistoricalPowerUsage.Add(GenTicks.TicksGame, PowerUsage); * HistoricalUptime.Add(GenTicks.TicksGame, Uptime); * HistoricalUsetime.Add(GenTicks.TicksGame, Usetime); * } * } */ public override void Initialize(CompProperties props) { CompPowerBattery powerBattery = parent.GetComp <CompPowerBattery>(); if (powerBattery != null) { intMaxPowerUsage = Math.Max(Math.Abs(powerBattery.Props.storedEnergyMax), maxPowerUsage); } CompPowerPlant powerPlant = parent.GetComp <CompPowerPlant>(); if (powerPlant != null) { intMaxPowerUsage = Math.Max(Math.Abs(powerPlant.Props.basePowerConsumption), maxPowerUsage); } CompPowerTrader powerTrader = parent.GetComp <CompPowerTrader>(); if (powerTrader != null) { intMaxPowerUsage = Math.Max(Math.Abs(powerTrader.Props.basePowerConsumption), maxPowerUsage); } }
public override void Resolve(ResolveParams rp) { Map map = BaseGen.globalSettings.map; batteries.Clear(); foreach (IntVec3 item in rp.rect) { List <Thing> thingList = item.GetThingList(map); for (int i = 0; i < thingList.Count; i++) { CompPowerBattery compPowerBattery = thingList[i].TryGetComp <CompPowerBattery>(); if (compPowerBattery != null && !batteries.Contains(compPowerBattery)) { batteries.Add(compPowerBattery); } } } for (int j = 0; j < batteries.Count; j++) { float num = Rand.Range(0.1f, 0.3f); batteries[j].SetStoredEnergyPct(Mathf.Min(batteries[j].StoredEnergyPct + num, 1f)); } batteries.Clear(); }
public static Toil FinalizeIngestAnything(Pawn ingester, TargetIndex ingestibleInd, CompEatWeirdFood comp) { Toil toil = new Toil(); toil.initAction = delegate() { Pawn actor = toil.actor; Job curJob = actor.jobs.curJob; Thing thing = curJob.GetTarget(ingestibleInd).Thing; float num = ingester.needs.food.NutritionWanted; if (curJob.overeat) { num = Mathf.Max(num, 0.75f); } float num2 = comp.Props.nutrition;// thing.Ingested(ingester, num); if (comp.Props.fullyDestroyThing) { if (comp.Props.drainBattery) { Building_Battery battery = thing as Building_Battery; if (battery != null) { CompPowerBattery compPower = battery.TryGetComp <CompPowerBattery>(); compPower.SetStoredEnergyPct(compPower.StoredEnergyPct - comp.Props.percentageDrain); } else { thing.Destroy(DestroyMode.Vanish); } } else { thing.Destroy(DestroyMode.Vanish); } } else { if (thing.def.useHitPoints) { thing.HitPoints -= (int)(thing.MaxHitPoints * comp.Props.percentageOfDestruction); if (thing.HitPoints <= 0) { thing.Destroy(DestroyMode.Vanish); } } else { int thingsToDestroy = (int)(comp.Props.percentageOfDestruction * thing.def.stackLimit); //Log.Message(thingsToDestroy.ToString()); thing.stackCount = thing.stackCount - thingsToDestroy; //Log.Message(thing.stackCount.ToString()); if (thing.stackCount < 10) { thing.Destroy(DestroyMode.Vanish); } } if ((actor.def.defName == "AA_AngelMoth") && (actor.Faction == Faction.OfPlayer) && (thing.TryGetComp <CompQuality>() != null) && (thing.TryGetComp <CompQuality>().Quality == QualityCategory.Legendary)) { actor.health.AddHediff(HediffDef.Named("AA_AteFinestClothes")); } } if (comp.Props.hediffWhenEaten != "") { actor.health.AddHediff(HediffDef.Named(comp.Props.hediffWhenEaten)); } if (comp.Props.advanceLifeStage && actor.Map != null) { comp.currentFeedings++; if (comp.currentFeedings >= comp.Props.advanceAfterXFeedings) { if (comp.Props.fissionAfterXFeedings) { if (!comp.Props.fissionOnlyIfTamed || actor.Faction.IsPlayer) { for (int i = 0; i < comp.Props.numberOfOffspring; i++) { PawnGenerationRequest request = new PawnGenerationRequest(PawnKindDef.Named(comp.Props.defToFissionTo), actor.Faction, PawnGenerationContext.NonPlayer, -1, true, true, false, false, true, false, 1f, false, true, true, false, false); Pawn newPawn = PawnGenerator.GeneratePawn(request); newPawn.playerSettings.AreaRestriction = actor.playerSettings.AreaRestriction; newPawn.relations.AddDirectRelation(PawnRelationDefOf.Parent, actor); GenSpawn.Spawn(newPawn, actor.Position, actor.Map, WipeMode.Vanish); } actor.Destroy(); } } else { PawnGenerationRequest request = new PawnGenerationRequest(PawnKindDef.Named(comp.Props.defToAdvanceTo), actor.Faction, PawnGenerationContext.NonPlayer, -1, true, true, false, false, true, false, 1f, false, true, true, false, false); Pawn newPawn = PawnGenerator.GeneratePawn(request); if (!actor.Name.ToString().UncapitalizeFirst().Contains(actor.def.label)) { newPawn.Name = actor.Name; } newPawn.training = actor.training; newPawn.health = actor.health; newPawn.foodRestriction = actor.foodRestriction; newPawn.playerSettings.AreaRestriction = actor.playerSettings.AreaRestriction; GenSpawn.Spawn(newPawn, actor.Position, actor.Map, WipeMode.Vanish); actor.Destroy(); } } } if (!ingester.Dead) { ingester.needs.food.CurLevel += num2; } ingester.records.AddTo(RecordDefOf.NutritionEaten, num2); }; toil.defaultCompleteMode = ToilCompleteMode.Instant; return(toil); }
private void DrawBattery( CompPowerBattery battery ) { if ( battery == null ) { throw new ArgumentNullException( "battery" ); } var color = Color.clear; // blue if gaining energy if ( battery.PowerNet?.CurrentEnergyGainRate() > 1f ) color = GenUI.MouseoverColor; // green if draining but has power else if ( battery.StoredEnergy > 1f ) color = Color.green; // red if out of power else color = Color.red; MiniMap_Utilities.DrawThing( texture, battery.parent, color ); }
private void ChargeFromOther(CompPowerBattery battery, float charge) { battery.DrawPower(charge); AddEnergy(charge); }
public override void Tick() { base.Tick(); if (this.StoredEnergy > 0) { this.StoredEnergy -= 0.01f; } else { if (!this.Downed) { Hediff hediff = HediffMaker.MakeHediff(ProfSchmilvsPokemon.DefOfs.HediffDefOf.OutOfPower, this); this.health.AddHediff(hediff); } } if (closestCompPower == null && this.StoredEnergy >= this.storedEnergyMax * 0.21f && this.Faction != null) { if (this.repairJob == null) { List <Thing> toRepair = base.Map.listerBuildingsRepairable.RepairableBuildings(this.Faction); if (!toRepair.NullOrEmpty()) { this.repairJob = toRepair[0]; this.jobs.ClearQueuedJobs(); this.pather.StartPath(new LocalTargetInfo(this.repairJob.Position), Verse.AI.PathEndMode.Touch); } } else { if (this.repairJob.MaxHitPoints == this.repairJob.HitPoints) { base.Map.listerBuildingsRepairable.Notify_BuildingRepaired((Building)this.repairJob); this.repairJob = null; this.jobs.ClearQueuedJobs(); } else { if (this.Position.AdjacentTo8WayOrInside(this.repairJob.Position)) { this.repairing(); } else if (this.pather.Destination != new LocalTargetInfo(this.repairJob.Position)) { this.pather.StartPath(new LocalTargetInfo(this.repairJob.Position), Verse.AI.PathEndMode.Touch); } } } } if (closestCompPower != null && this.StoredEnergy >= this.storedEnergyMax) { closestCompPower = null; this.jobs.ClearQueuedJobs(); } if (this.Downed) { if (this.StoredEnergy < this.storedEnergyMax * 0.2f) { List <CompPower> dummylist = Spawner.spawnerPokemon.PowerComps; if (!dummylist.NullOrEmpty()) { float distance = 999999f; foreach (CompPower cp in dummylist) { float compareDistance = this.Position.DistanceTo(cp.parent.Position); if (compareDistance < distance) { distance = compareDistance; closestCompPower = cp; } } } } if (this.Position.AdjacentTo8WayOrInside(this.closestCompPower.parent.Position)) { PowerNet pn = this.closestCompPower.PowerNet; if (pn != null) { float currentEnergy = pn.CurrentStoredEnergy(); if (currentEnergy >= 0.5f) { List <CompPowerBattery> cpb = pn.batteryComps; CompPowerBattery bat = null; foreach (CompPowerBattery c in cpb) { if (c.StoredEnergy >= 0.5f) { bat = c; break; } } if (bat != null) { this.StoredEnergy += 0.5f; bat.DrawPower(0.5f); } } } } if (this.StoredEnergy > this.storedEnergyMax * 0.2f) { List <Hediff> heds = this.health.hediffSet.hediffs; if (!heds.NullOrEmpty()) { Hediff oop = null; foreach (Hediff h in heds) { if (h.def.Equals(ProfSchmilvsPokemon.DefOfs.HediffDefOf.OutOfPower)) { oop = h; } } if (oop != null) { this.health.RemoveHediff(oop); } } } } else { if (closestCompPower == null) { if (this.StoredEnergy > 0 && this.StoredEnergy < this.storedEnergyMax * 0.2f) { List <CompPower> dummylist = Spawner.spawnerPokemon.PowerComps; if (!dummylist.NullOrEmpty()) { float distance = 999999f; foreach (CompPower cp in dummylist) { float compareDistance = this.Position.DistanceTo(cp.parent.Position); if (compareDistance < distance) { distance = compareDistance; closestCompPower = cp; } } this.pather.StartPath(new LocalTargetInfo(this.closestCompPower.parent.Position), Verse.AI.PathEndMode.OnCell); } } } else { if (this.Position.AdjacentTo8WayOrInside(this.closestCompPower.parent.Position)) { PowerNet pn = this.closestCompPower.PowerNet; if (pn != null) { float currentEnergy = pn.CurrentStoredEnergy(); if (currentEnergy >= 0.5f) { List <CompPowerBattery> cpb = pn.batteryComps; CompPowerBattery bat = null; foreach (CompPowerBattery c in cpb) { if (c.StoredEnergy >= 0.5f) { bat = c; break; } } if (bat != null) { this.StoredEnergy += 0.5f; bat.DrawPower(0.5f); this.evolve(); } } } } else { if (this.pather.Destination != new LocalTargetInfo(this.closestCompPower.parent.Position)) { this.jobs.ClearQueuedJobs(); this.pather.StartPath(new LocalTargetInfo(this.closestCompPower.parent.Position), Verse.AI.PathEndMode.Touch); } } } } }
public override void SpawnSetup(Map map, bool respawningAfterLoad) { base.SpawnSetup(map, respawningAfterLoad); batteryComp = GetComp <CompPowerBattery>(); }
public override void PostMake() { base.PostMake(); batteryComp = GetComp <CompPowerBattery>(); }
protected override void Impact(Thing hitThing) { Map map = base.Map; base.Impact(hitThing); ThingDef def = this.def; Pawn caster = this.launcher as Pawn; if (!this.initialized) { ModOptions.SettingsRef settingsRef = new ModOptions.SettingsRef(); CompAbilityUserMagic comp = caster.GetComp <CompAbilityUserMagic>(); pwrVal = comp.MagicData.MagicPowerSkill_Sabotage.FirstOrDefault((MagicPowerSkill x) => x.label == "TM_Sabotage_pwr").level; verVal = comp.MagicData.MagicPowerSkill_Sabotage.FirstOrDefault((MagicPowerSkill x) => x.label == "TM_Sabotage_ver").level; if (caster.story.traits.HasTrait(TorannMagicDefOf.Faceless)) { MightPowerSkill mpwr = caster.GetComp <CompAbilityUserMight>().MightData.MightPowerSkill_Mimic.FirstOrDefault((MightPowerSkill x) => x.label == "TM_Mimic_pwr"); MightPowerSkill mver = caster.GetComp <CompAbilityUserMight>().MightData.MightPowerSkill_Mimic.FirstOrDefault((MightPowerSkill x) => x.label == "TM_Mimic_ver"); pwrVal = mpwr.level; verVal = mver.level; } this.arcaneDmg = comp.arcaneDmg; if (settingsRef.AIHardMode && !caster.IsColonist) { pwrVal = 3; verVal = 3; } SoundInfo info = SoundInfo.InMap(new TargetInfo(base.Position, this.Map, false), MaintenanceType.None); info.pitchFactor = .5f; info.volumeFactor = .8f; SoundDefOf.PsychicPulseGlobal.PlayOneShot(info); Effecter SabotageEffect = TorannMagicDefOf.TM_SabotageExplosion.Spawn(); SabotageEffect.Trigger(new TargetInfo(base.Position, this.Map, false), new TargetInfo(base.Position, this.Map, false)); SabotageEffect.Cleanup(); targetCells = GenRadial.RadialCellsAround(base.Position, this.def.projectile.explosionRadius, true).ToList(); this.targetThings = new List <SabotageThing>(); this.targetThings.Clear(); this.initialized = true; Pawn targetPawn = null; Building targetBuilding = null; for (int i = 0; i < this.targetCells.Count; i++) { var targetCell = this.targetCells[i]; if (Rand.Chance((.5f + (.1f * verVal)) * this.arcaneDmg)) { float rnd = Rand.Range(0, 1f); targetPawn = targetCell.GetFirstPawn(this.Map); if (targetPawn != null) { if (TM_Calc.IsRobotPawn(targetPawn)) { TM_Action.DoAction_SabotagePawn(targetPawn, caster, rnd, pwrVal, this.arcaneDmg, this.launcher); this.age = this.duration; } else { targetPawn = null; //Log.Message("pawn not a robot, mechanoid, or android"); } } targetBuilding = targetCell.GetFirstBuilding(this.Map); if (targetPawn == null && targetBuilding != null) { CompPower compP = targetBuilding.GetComp <CompPower>(); CompPowerTrader cpt = targetBuilding.GetComp <CompPowerTrader>(); if (compP != null && compP.Props.basePowerConsumption != 0 && cpt != null && cpt.powerOutputInt != 0) { if (true) { //stun/electrical explosion GenExplosion.DoExplosion(targetBuilding.Position, base.Map, 2 + pwrVal + Mathf.RoundToInt(cpt.powerOutputInt / 400), DamageDefOf.Stun, null); GenExplosion.DoExplosion(targetBuilding.Position, base.Map, 1 + pwrVal + Mathf.RoundToInt(cpt.powerOutputInt / 600), TMDamageDefOf.DamageDefOf.TM_ElectricalBurn, null); } else { } } Building_Battery targetBattery = targetBuilding as Building_Battery; if (targetBattery != null && targetBattery.def.thingClass.ToString() == "RimWorld.Building_Battery") { CompPowerBattery compB = targetBattery.GetComp <CompPowerBattery>(); if (rnd <= .5f) { Traverse.Create(root: targetBattery).Field(name: "ticksToExplode").SetValue(Rand.Range(40, 130) - (5 * pwrVal)); compB.SetStoredEnergyPct(.81f); } else { GenExplosion.DoExplosion(targetBattery.Position, base.Map, 2 + pwrVal + Mathf.RoundToInt(compB.StoredEnergy / 200), DamageDefOf.EMP, null); compB.DrawPower(compB.StoredEnergy); } } Building_TurretGun targetTurret = targetBuilding as Building_TurretGun; if (targetTurret != null && targetTurret.gun != null) { if (rnd <= .5f) { targetTurret.SetFaction(Faction.OfAncientsHostile, null); } else { GenExplosion.DoExplosion(targetTurret.Position, base.Map, 2 + pwrVal, TMDamageDefOf.DamageDefOf.TM_ElectricalBurn, null); //20 default damage } } } else { //Log.Message("no thing to sabotage"); } targetPawn = null; targetBuilding = null; } } } else if (this.targetThings.Count > 0) { this.age = this.duration; } else { this.age = this.duration; } }
public static void GenerateRoomFromLayout(List <string> layoutList, CellRect roomRect, Map map, StructureLayoutDef rld, bool generateConduit = true) { bool parentFaction = map.ParentFaction != null; if (rld.roofGrid != null) { GenerateRoofGrid(rld.roofGrid, roomRect, map); } List <string> allSymbList = new List <string>(); foreach (string str in layoutList) { allSymbList.AddRange(str.Split(',')); } int l = 0; foreach (IntVec3 cell in roomRect) { if (l < allSymbList.Count && allSymbList[l] != ".") { SymbolDef temp = DefDatabase <SymbolDef> .GetNamedSilentFail(allSymbList[l]); Thing thing; if (temp != null) { if (temp.isTerrain && temp.terrainDef != null) { GenerateTerrainAt(map, cell, temp.terrainDef); } else if (temp.pawnKindDefNS != null && CGO.factionSettlement?.shouldRuin == false) { if (temp.lordJob != null) { Lord lord = CreateNewLord(temp.lordJob, map, cell); for (int i = 0; i < temp.numberToSpawn; i++) { Pawn pawn = temp.spawnPartOfFaction ? PawnGenerator.GeneratePawn(temp.pawnKindDefNS, map.ParentFaction) : PawnGenerator.GeneratePawn(temp.pawnKindDefNS); if (pawn != null) { if (temp.isSlave && parentFaction) { pawn.guest.SetGuestStatus(map.ParentFaction, GuestStatus.Prisoner); } GenSpawn.Spawn(pawn, cell, map, WipeMode.FullRefund); lord.AddPawn(pawn); } } } else { for (int i = 0; i < temp.numberToSpawn; i++) { Pawn pawn = temp.spawnPartOfFaction ? PawnGenerator.GeneratePawn(temp.pawnKindDefNS, map.ParentFaction) : PawnGenerator.GeneratePawn(temp.pawnKindDefNS); if (pawn != null) { if (temp.isSlave && parentFaction) { pawn.guest.SetGuestStatus(map.ParentFaction, GuestStatus.Prisoner); } GenSpawn.Spawn(pawn, cell, map, WipeMode.FullRefund); } } } } else if (temp.thingDef?.category == ThingCategory.Item && cell.Walkable(map)) { thing = ThingMaker.MakeThing(temp.thingDef, temp.stuffDef ?? (temp.thingDef.stuffCategories?.Count > 0 ? GenStuff.RandomStuffFor(temp.thingDef) : null)); thing.stackCount = Mathf.Clamp(Rand.RangeInclusive(1, temp.thingDef.stackLimit), 1, 75); CompQuality quality = thing.TryGetComp <CompQuality>(); quality?.SetQuality(QualityUtility.GenerateQualityBaseGen(), ArtGenerationContext.Outsider); GenSpawn.Spawn(thing, cell, map, WipeMode.FullRefund); thing.SetForbidden(true, false); } else if (temp.thingDef != null) { thing = ThingMaker.MakeThing(temp.thingDef, temp.thingDef.CostStuffCount > 0 ? (temp.stuffDef ?? temp.thingDef.defaultStuff ?? ThingDefOf.WoodLog) : null); CompRefuelable refuelable = thing.TryGetComp <CompRefuelable>(); refuelable?.Refuel(refuelable.Props.fuelCapacity); CompPowerBattery battery = thing.TryGetComp <CompPowerBattery>(); battery?.AddEnergy(battery.Props.storedEnergyMax); if (thing is Building_CryptosleepCasket cryptosleepCasket && Rand.Value < temp.chanceToContainPawn) { Pawn pawn = GeneratePawnForContainer(temp, map); if (!cryptosleepCasket.TryAcceptThing(pawn)) { pawn.Destroy(); } } else if (thing is Building_CorpseCasket corpseCasket && Rand.Value < temp.chanceToContainPawn) { Pawn pawn = GeneratePawnForContainer(temp, map); if (!corpseCasket.TryAcceptThing(pawn)) { pawn.Destroy(); } } else if (thing is Building_Crate crate) { List <Thing> thingList = new List <Thing>(); if (map.ParentFaction == Faction.OfPlayer && temp.thingSetMakerDefForPlayer != null) { thingList = temp.thingSetMakerDefForPlayer.root.Generate(new ThingSetMakerParams()); } else if (temp.thingSetMakerDef != null) { thingList = temp.thingSetMakerDef.root.Generate(new ThingSetMakerParams()); } foreach (Thing t in thingList) { t.stackCount = Math.Min((int)(t.stackCount * temp.crateStackMultiplier), t.def.stackLimit); } thingList.ForEach(t => { if (!crate.TryAcceptThing(t, false)) { t.Destroy(); } }); } if (thing.def.category == ThingCategory.Pawn && CGO.factionSettlement?.shouldRuin == true) { l++; continue; } else if (cell.GetFirstMineable(map) is Mineable m && thing.def.designationCategory == DesignationCategoryDefOf.Security) { l++; continue; } else if (thing.def.category == ThingCategory.Plant && cell.GetTerrain(map).fertility > 0.5 && cell.Walkable(map)) // If it's a plant { Plant plant = thing as Plant; plant.Growth = temp.plantGrowth; // apply the growth GenSpawn.Spawn(plant, cell, map, WipeMode.VanishOrMoveAside); } else if (thing.def.category == ThingCategory.Building) { if (!cell.GetTerrain(map).affordances.Contains(TerrainAffordanceDefOf.Heavy)) { if (thing.def.building.isNaturalRock) { TerrainDef t = DefDatabase <TerrainDef> .GetNamedSilentFail($"{thing.def.defName}_Rough"); map.terrainGrid.SetTerrain(cell, t ?? TerrainDefOf.Soil); foreach (IntVec3 intVec3 in CellRect.CenteredOn(cell, 1)) { if (!intVec3.GetTerrain(map).BuildableByPlayer) { map.terrainGrid.SetTerrain(intVec3, t ?? TerrainDefOf.Soil); } } } else { map.terrainGrid.SetTerrain(cell, TerrainDefOf.Bridge); } } if (thing.def.rotatable) { GenSpawn.Spawn(thing, cell, map, new Rot4(temp.rotation.AsInt), WipeMode.VanishOrMoveAside); } else { GenSpawn.Spawn(thing, cell, map, WipeMode.VanishOrMoveAside); } if (parentFaction) { thing.SetFactionDirect(map.ParentFaction); } } if (generateConduit && rld.spawnConduits && !thing.def.mineable && (thing.def.passability == Traversability.Impassable || thing.def.IsDoor) && map.ParentFaction?.def.techLevel >= TechLevel.Industrial) // Add power cable under all impassable { Thing c = ThingMaker.MakeThing(ThingDefOf.PowerConduit); if (parentFaction) { c.SetFactionDirect(map.ParentFaction); } GenSpawn.Spawn(c, cell, map, WipeMode.FullRefund); } // Handle mortar and mortar pawns if (thing?.def?.building?.buildingTags?.Count > 0) { if (thing.def.building.IsMortar && thing.def.category == ThingCategory.Building && thing.def.building.buildingTags.Contains("Artillery_MannedMortar") && thing.def.HasComp(typeof(CompMannable)) && parentFaction) { // Spawn pawn Lord singlePawnLord = LordMaker.MakeNewLord(map.ParentFaction, new LordJob_ManTurrets(), map, null); PawnGenerationRequest value = new PawnGenerationRequest(map.ParentFaction.RandomPawnKind(), map.ParentFaction, PawnGenerationContext.NonPlayer, map.Tile, mustBeCapableOfViolence: true, inhabitant: true); ResolveParams rpPawn = new ResolveParams { faction = map.ParentFaction, singlePawnGenerationRequest = new PawnGenerationRequest?(value), rect = CellRect.SingleCell(thing.InteractionCell), singlePawnLord = singlePawnLord }; BaseGen.symbolStack.Push("pawn", rpPawn); // Spawn shells ThingDef shellDef = TurretGunUtility.TryFindRandomShellDef(thing.def, false, true, map.ParentFaction.def.techLevel, false, 250f); if (shellDef != null) { ResolveParams rpShell = new ResolveParams { faction = map.ParentFaction, singleThingDef = shellDef, singleThingStackCount = Rand.RangeInclusive(8, Math.Min(12, shellDef.stackLimit)) }; BaseGen.symbolStack.Push("thing", rpShell); } } } }
public float GetEnergyStored(float currentEnergyOtherSide) { if (thisBattery.PowerNet == null) { //Logger.MessageFormat(this, "No PowerNet found."); reloadedEnergyCalculated = true; oldDuplicateEnergy = duplicateEnergy = 1.0f; return(0.0f); } List <CompPowerBattery> networkBatteries = this.AvailableBatteries(); oldNetworkEnergy = networkEnergy; oldDuplicateEnergy = duplicateEnergy; duplicateEnergy = currentEnergyOtherSide; float duplicateEnergyChange = duplicateEnergy - oldDuplicateEnergy; networkEnergy = networkBatteries.Select(x => x.StoredEnergy).DefaultIfEmpty(0.0f).Sum(); float networkMaxEnergy = networkBatteries.Select(x => x.Props.storedEnergyMax).DefaultIfEmpty(0.0f).Sum(); energyGained = networkEnergy - oldNetworkEnergy; energyReturned = duplicateEnergyChange; //Logger.MessageFormat(this, "{0}, Old duplicate energy: {1}, new duplicate energy: {2}, Duplicate energy change: {3}, network: {4}/{5}", this.parent.GetType().ToString(), oldDuplicateEnergy, duplicateEnergy, duplicateEnergyChange, networkEnergy, networkMaxEnergy); if (reloadedEnergyCalculated && duplicateEnergyChange != 0.0f) { float networkEnergyPlusDuplicate = networkEnergy + duplicateEnergyChange; // If more energy lost in duplicate battery than available in duplicated network if (networkEnergyPlusDuplicate < 0.0f) { if (networkEnergy > 0.0f) { // Drain the whole thing foreach (CompPowerBattery battery in networkBatteries) { battery.SetStoredEnergyPct(0.0f); } networkEnergy = 0.0f; //Logger.MessageFormat(this, "Network drained"); } } // If more energy gained in duplicate battery than the network can hold else if (networkEnergyPlusDuplicate > networkMaxEnergy) { if (networkEnergy < networkMaxEnergy) { // Max the whole thing foreach (CompPowerBattery battery in networkBatteries) { battery.SetStoredEnergyPct(1.0f); } networkEnergy = networkMaxEnergy; //Logger.MessageFormat(this, "Network filled"); } } else if (oldDuplicateEnergy > 0.0f) { if (duplicateEnergyChange > 0.0f) { List <CompPowerBattery> shuffledBatteries = new List <CompPowerBattery>(); shuffledBatteries.AddRange(networkBatteries); float totalEnergyToGive = duplicateEnergyChange; int i = 0; while (totalEnergyToGive > 0.0f && i < shuffledBatteries.Count) { CompPowerBattery compPowerBattery = shuffledBatteries[i]; float energyCanRecieve = (compPowerBattery.Props.storedEnergyMax - compPowerBattery.StoredEnergy); float energyToGive = Mathf.Min(totalEnergyToGive, energyCanRecieve); compPowerBattery.AddEnergy(energyToGive / compPowerBattery.Props.efficiency); totalEnergyToGive -= energyToGive; ++i; } } else if (duplicateEnergyChange < 0.0f) { List <CompPowerBattery> shuffledBatteries = new List <CompPowerBattery>(); shuffledBatteries.AddRange(networkBatteries); float totalEnergyToGive = -duplicateEnergyChange; int i = 0; while (totalEnergyToGive > 0.0f && i < shuffledBatteries.Count) { CompPowerBattery compPowerBattery = shuffledBatteries[i]; float energyCanRemove = compPowerBattery.StoredEnergy; float energyToRemove = Mathf.Min(totalEnergyToGive, energyCanRemove); compPowerBattery.DrawPower(energyToRemove); totalEnergyToGive -= energyToRemove; ++i; } } //Logger.MessageFormat(this, "Duplicate energy change: {0}, energy returned to network: {1}", energyGained, energyReturned); } } reloadedEnergyCalculated = true; // Add in any extra energy stored in the sharer if (currentEnergyOtherSide > networkMaxEnergy) { networkEnergy += (currentEnergyOtherSide - networkMaxEnergy); } duplicateEnergy = networkEnergy; return(networkEnergy); }
public override void PostSpawnSetup(bool respawningAfterLoad) { base.PostSpawnSetup(respawningAfterLoad); thisBattery = this.parent.GetComp <CompPowerBattery>(); }
protected override IEnumerable <Toil> MakeNewToils() { this.FailOnDestroyedNullOrForbidden(PowerDestIndex); AddFailCondition(() => energyNeed == null); yield return(Toils_Reserve.Reserve(PowerDestIndex)); if (!TargetB.IsValid) { yield return(Toils_Goto.GotoThing(PowerDestIndex, PathEndMode.ClosestTouch)); } else { yield return(Toils_Reserve.Reserve(AlternateDestIndex)); yield return(Toils_Goto.GotoThing(AlternateDestIndex, PathEndMode.OnCell)); } Toil rechargeToil = new Toil(); rechargeToil.tickAction = delegate { //Drain the powernet. CompPowerBattery compBattery = powerBuilding.PowerComp?.PowerNet?.batteryComps?.FirstOrDefault(battery => battery.StoredEnergy > PowerNetEnergyDrainedPerTick); if (compBattery != null) { compBattery.DrawPower(PowerNetEnergyDrainedPerTick); //Add to our energy. energyNeed.CurLevel += energyNeed.MaxLevel / MaxTicksSpentCharging; } ticksSpentCharging++; }; rechargeToil.AddEndCondition(delegate { if (powerBuilding == null || powerBuilding.PowerComp == null /*|| temporaryTrader == null*/) { return(JobCondition.Incompletable); } if (powerBuilding.PowerComp?.PowerNet.CurrentStoredEnergy() < PowerNetEnergyDrainedPerTick) { return(JobCondition.Incompletable); } if (energyNeed.CurLevelPercentage >= 0.99f) { return(JobCondition.Succeeded); } if (ticksSpentCharging > MaxTicksSpentCharging) { return(JobCondition.Incompletable); } return(JobCondition.Ongoing); }); if (!TargetB.IsValid) { rechargeToil.FailOnCannotTouch(PowerDestIndex, PathEndMode.ClosestTouch); } else { rechargeToil.FailOnCannotTouch(AlternateDestIndex, PathEndMode.OnCell); } rechargeToil.WithProgressBar(TargetIndex.A, () => energyNeed.CurLevelPercentage, false); rechargeToil.defaultCompleteMode = ToilCompleteMode.Never; yield return(rechargeToil); }