public static bool PreFix(CapacityImpactorBodyPartHealth __instance, ref string __result, Pawn pawn) { HediffSet hediffSet = pawn.health.hediffSet; BodyPartRecord record = __instance.bodyPart; __result = $"{record.LabelCap}: {hediffSet.GetPartHealth(record)} / {hediffSet.GetPartMaxHealth(record)}"; return(false); }
public static void RemoveCommUnit(X2_AIRobot pawn) { // Do not remove, if one of the following work types: if (pawn.workSettings.GetPriority(WorkTypeDefOf.Doctor) > 0 || pawn.workSettings.GetPriority(WorkTypeDefOf.Handling) > 0 || pawn.workSettings.GetPriority(WorkTypeDefOf.Warden) > 0) { return; } PawnCapacityDef activity = PawnCapacityDefOf.Talking; if (pawn.health.capacities.CapableOf(activity)) { HediffSet hediffSet = pawn.health.hediffSet; IEnumerable <BodyPartRecord> notMissingParts = hediffSet.GetNotMissingParts(); BodyPartRecord bodyPart = notMissingParts.Where(p => p.def.defName == "AIRobot_CommUnit").FirstOrDefault(); if (bodyPart != null) { DamageInfo damageInfo = new DamageInfo(DamageDefOf.EMP, Mathf.RoundToInt(hediffSet.GetPartHealth(bodyPart)), 0f, -1f, null, bodyPart, null, DamageInfo.SourceCategory.ThingOrUnknown, null); //pawn.TakeDamage(damageInfo); Hediff_MissingPart hediff_MissingPart = (Hediff_MissingPart)HediffMaker.MakeHediff(HediffDefOf.MissingBodyPart, pawn, null); hediff_MissingPart.IsFresh = false; hediff_MissingPart.lastInjury = null; pawn.health.AddHediff(hediff_MissingPart, bodyPart, damageInfo); pawn.health.Notify_HediffChanged(hediff_MissingPart); pawn.apparel.Notify_LostBodyPart(); } } }
public static void DamageUntilDownedWithSpecialOptions(Pawn p, bool allowBleedingWounds = true, DamageDef damageDef = null, ThingDef weapon = null) { if (!p.health.Downed) { if (p.apparel != null) { foreach (Apparel apparel in p.apparel.WornApparel) { if (apparel.def.StatBaseDefined(StatDefOf.SmokepopBeltRadius)) { p.apparel.Remove(apparel); break; } } } HediffSet hediffSet = p.health.hediffSet; p.health.forceIncap = true; IEnumerable <BodyPartRecord> source = HittablePartsViolence(hediffSet).Where(x => !p.health.hediffSet.hediffs .Any(y => y.Part == x && y.CurStage?.partEfficiencyOffset < 0f)).ToList(); int num = 0; while (num < 300 && !p.Downed && source.Any <BodyPartRecord>()) { num++; BodyPartRecord bodyPartRecord = source.RandomElementByWeight((BodyPartRecord x) => x.coverageAbs); int num2 = Mathf.RoundToInt(hediffSet.GetPartHealth(bodyPartRecord)) - 3; if (num2 >= 8) { if (bodyPartRecord.depth == BodyPartDepth.Outside) { if (!allowBleedingWounds && bodyPartRecord.def.bleedRate > 0f) { damageDef = DamageDefOf.Blunt; } else { if (damageDef == null || damageDef == DamageDefOf.Flame) { damageDef = HealthUtility.RandomViolenceDamageType(); } } } else { damageDef = DamageDefOf.Blunt; } int num3 = Rand.RangeInclusive(Mathf.RoundToInt((float)num2 * 0.65f), num2); HediffDef hediffDefFromDamage = HealthUtility.GetHediffDefFromDamage(damageDef, p, bodyPartRecord); if (!p.health.WouldDieAfterAddingHediff(hediffDefFromDamage, bodyPartRecord, (float)num3)) { DamageDef def = damageDef; float amount = (float)num3; float armorPenetration = 999f; BodyPartRecord hitPart = bodyPartRecord; DamageInfo dinfo = new DamageInfo(def, amount, armorPenetration, -1f, null, hitPart, weapon); dinfo.SetAllowDamagePropagation(false); p.TakeDamage(dinfo); } } } if (p.Dead) { StringBuilder stringBuilder = new StringBuilder(); stringBuilder.AppendLine(p + " died during GiveInjuriesToForceDowned"); for (int i = 0; i < p.health.hediffSet.hediffs.Count; i++) { stringBuilder.AppendLine(" -" + p.health.hediffSet.hediffs[i].ToString()); } Log.Error(stringBuilder.ToString()); } p.health.forceIncap = false; } }
public static bool AddDirect(HediffSet __instance, Hediff hediff, DamageInfo?dinfo = null, DamageWorker.DamageResult damageResult = null) { if (hediff.def == null) { Log.Error("Tried to add health diff with null def. Canceling."); return(false); } if (hediff.Part != null && !__instance.GetNotMissingParts().Contains(hediff.Part)) { Log.Error("Tried to add health diff to missing part " + hediff.Part); return(false); } hediff.ageTicks = 0; hediff.pawn = __instance.pawn; bool flag = false; for (int i = 0; i < __instance.hediffs.Count; i++) { if (__instance.hediffs[i].TryMergeWith(hediff)) { flag = true; } } if (!flag) { lock (__instance) { //List<Hediff> newHediffs = new List<Hediff>(__instance.hediffs) { hediff }; //__instance.hediffs = newHediffs; __instance.hediffs.Add(hediff); } hediff.PostAdd(dinfo); if (__instance.pawn.needs != null && __instance.pawn.needs.mood != null) { __instance.pawn.needs.mood.thoughts.situational.Notify_SituationalThoughtsDirty(); } } bool flag2 = hediff is Hediff_MissingPart; if (!(hediff is Hediff_MissingPart) && hediff.Part != null && hediff.Part != __instance.pawn.RaceProps.body.corePart && __instance.GetPartHealth(hediff.Part) == 0f && hediff.Part != __instance.pawn.RaceProps.body.corePart) { bool flag3 = __instance.HasDirectlyAddedPartFor(hediff.Part); Hediff_MissingPart hediff_MissingPart = (Hediff_MissingPart)HediffMaker.MakeHediff(HediffDefOf.MissingBodyPart, __instance.pawn); hediff_MissingPart.IsFresh = !flag3; hediff_MissingPart.lastInjury = hediff.def; __instance.pawn.health.AddHediff(hediff_MissingPart, hediff.Part, dinfo); damageResult?.AddHediff(hediff_MissingPart); if (flag3) { if (dinfo.HasValue) { hediff_MissingPart.lastInjury = HealthUtility.GetHediffDefFromDamage(dinfo.Value.Def, __instance.pawn, hediff.Part); } else { hediff_MissingPart.lastInjury = null; } } flag2 = true; } __instance.DirtyCache(); if (flag2 && __instance.pawn.apparel != null) { __instance.pawn.apparel.Notify_LostBodyPart(); } if (hediff.def.causesNeed != null && !__instance.pawn.Dead) { __instance.pawn.needs.AddOrRemoveNeedsAsAppropriate(); } return(false); }
public static bool CalculatePartEfficiency(ref float __result, HediffSet diffSet, BodyPartRecord part, bool ignoreAddedParts = false, List <CapacityImpactor> impactors = null) { BodyPartRecord rec; for (rec = part.parent; rec != null; rec = rec.parent) { if (diffSet.HasDirectlyAddedPartFor(rec)) { Hediff_AddedPart hediff_AddedPart = (from x in diffSet.GetHediffs <Hediff_AddedPart>() where x.Part == rec select x).First(); impactors?.Add(new CapacityImpactorHediff { hediff = hediff_AddedPart }); __result = hediff_AddedPart.def.addedPartProps.partEfficiency; return(false); } } if (part.parent != null && diffSet.PartIsMissing(part.parent)) { __result = 0f; return(false); } float num = 1f; if (!ignoreAddedParts) { for (int i = 0; i < diffSet.hediffs.Count; i++) { Hediff_AddedPart hediff_AddedPart2 = diffSet.hediffs[i] as Hediff_AddedPart; if (hediff_AddedPart2 != null && hediff_AddedPart2.Part == part) { num *= hediff_AddedPart2.def.addedPartProps.partEfficiency; if (hediff_AddedPart2.def.addedPartProps.partEfficiency != 1f) { impactors?.Add(new CapacityImpactorHediff { hediff = hediff_AddedPart2 }); } } } } float b = -1f; float num2 = 0f; bool flag = false; for (int j = 0; j < diffSet.hediffs.Count; j++) { Hediff hediff1 = diffSet.hediffs[j]; if (hediff1 != null && hediff1.Part == part && hediff1.CurStage != null) { HediffStage curStage = hediff1.CurStage; num2 += curStage.partEfficiencyOffset; flag |= curStage.partIgnoreMissingHP; if (curStage.partEfficiencyOffset != 0f && curStage.becomeVisible) { impactors?.Add(new CapacityImpactorHediff { hediff = hediff1 }); } } } if (!flag) { float num3 = diffSet.GetPartHealth(part) / part.def.GetMaxHealth(diffSet.pawn); if (num3 != 1f) { if (DamageWorker_AddInjury.ShouldReduceDamageToPreservePart(part)) { num3 = Mathf.InverseLerp(0.1f, 1f, num3); } impactors?.Add(new CapacityImpactorBodyPartHealth { bodyPart = part }); num *= num3; } } num += num2; if (num > 0.0001f) { num = Mathf.Max(num, b); } __result = Mathf.Max(num, 0f); return(false); }