/// <summary> /// Returns true if a race part was chosen (even if that part is "no part"). /// </summary> public static bool TryAddRacePart(Pawn pawn, SexPartType sexPartType) { if (!TryGetRaceGroupDef(pawn, out var raceGroupDef)) { // No race, so nothing was chosen. return(false); } if (!RacePartDef_Helper.TryChooseRacePartDef(raceGroupDef, sexPartType, out var racePartDef)) { // Failed to find a part, so nothing was chosen. return(false); } if (racePartDef.IsNone) { // "no part" was explicitly chosen. return(true); } var target = sexPartType.GetBodyPartDef(); var bodyPartRecord = pawn.RaceProps.body.AllParts.Find(bpr => bpr.def == target); if (!racePartDef.TryGetHediffDef(out var hediffDef)) { // Failed to find hediffDef. return(false); } var hediff = RacePartDef_Helper.MakePart(hediffDef, pawn, bodyPartRecord, racePartDef); pawn.health.AddHediff(hediff, bodyPartRecord); // A part was chosen and added. return(true); }
public static BodyPartDef GetBodyPartDef(this SexPartType sexPartType) { return(sexPartType switch { SexPartType.Anus => xxx.anusDef, SexPartType.FemaleBreast => xxx.breastsDef, SexPartType.FemaleGenital => xxx.genitalsDef, SexPartType.MaleBreast => xxx.breastsDef, SexPartType.MaleGenital => xxx.genitalsDef, _ => throw new ArgumentException($"Unrecognized sexPartType: {sexPartType}"), });
public List <string> GetRacePartDefNames(SexPartType sexPartType) { return(sexPartType switch { SexPartType.Anus => anuses, SexPartType.FemaleBreast => femaleBreasts, SexPartType.FemaleGenital => femaleGenitals, SexPartType.MaleBreast => maleBreasts, SexPartType.MaleGenital => maleGenitals, _ => throw new ApplicationException($"Unrecognized sexPartType: {sexPartType}"), });
public static bool TryChooseRacePartDef(RaceGroupDef raceGroupDef, SexPartType sexPartType, out RacePartDef racePartDef) { var partNames = raceGroupDef.GetRacePartDefNames(sexPartType); if (partNames == null) { // Missing list, so nothing was chosen. racePartDef = null; return(false); } else if (!partNames.Any()) { // Empty list, so "no part" was chosen. racePartDef = RacePartDef.None; return(true); } var chances = raceGroupDef.GetChances(sexPartType); var hasChances = chances != null && chances.Count() > 0; if (hasChances && chances.Count() != partNames.Count()) { // No need for this to be runtime, should probably be a config error in RaceGroupDef. Log.Error($"[RJW] RaceGroupDef named {raceGroupDef.defName} has {partNames.Count()} parts but {chances.Count()} chances for {sexPartType}."); racePartDef = null; return(false); } string partName; if (hasChances) { var indexes = partNames.Select((x, i) => i); partName = partNames[indexes.RandomElementByWeight(i => chances[i])]; } else { partName = partNames.RandomElement(); } racePartDef = DefDatabase <RacePartDef> .GetNamedSilentFail(partName); if (racePartDef == null) { Log.Error($"[RJW] Could not find a RacePartDef named {partName} referenced by RaceGroupDef named {raceGroupDef.defName}."); return(false); } else { return(true); } }
public static bool TryAddSexPart(Pawn pawn, SexPartType sexPartType) { if (!TryGetRaceGroupDef(pawn, out var raceGroupDef)) { // No race, so nothing was chosen. return(false); } var parts = GetParts(raceGroupDef, sexPartType); if (parts == null) { // Missing list, so nothing was chosen. return(false); } else if (!parts.Any()) { // Empty list, so "no part" was chosen. return(true); } var target = BodyPartDefBySexPartType[sexPartType]; var part = pawn.RaceProps.body.AllParts.Find(bpr => bpr.def == target); HediffDef hediffDef = parts.RandomElement(); if (parts.Count() > 1) { List <float> partschances = GetPartsChances(raceGroupDef, sexPartType); if (partschances.Count() > 1) { float chance = Rand.Value; List <HediffDef> filteredparts = null; for (int i = 0; i < partschances.Count(); i++) { if (chance <= partschances[i]) { filteredparts.Add(parts[i]); } } if (filteredparts.Any()) { hediffDef = filteredparts.RandomElement(); } } } pawn.health.AddHediff(hediffDef, part); // A part was chosen and added. return(true); }
public static List <float> GetPartsChances(RaceGroupDef raceGroupDef, SexPartType sexPartType) { switch (sexPartType) { case SexPartType.Anus: return(raceGroupDef.chanceanuses); case SexPartType.FemaleBreast: return(raceGroupDef.chancefemaleBreasts); case SexPartType.FemaleGenital: return(raceGroupDef.chancefemaleGenitals); case SexPartType.MaleBreast: return(raceGroupDef.chancemaleBreasts); case SexPartType.MaleGenital: return(raceGroupDef.chancemaleGenitals); default: throw new ApplicationException($"Unrecognized sexPartType: {sexPartType}"); } }
public static bool TryAddRacePart(this Pawn pawn, SexPartType sexPartType) { return(RaceGroupDef_Helper.TryAddRacePart(pawn, sexPartType)); }