public override bool TryExecute(IncidentParms parms) { Log.Message("IncidentWorker_RefugeePodCrashInCave:TryExecute"); if (Find.Map.Biome != Util_CaveBiome.CaveBiomeDef) { return base.TryExecute(parms); } IntVec3 intVec = IntVec3.Invalid; TryFindRefugeePodSpot(out intVec); if (intVec.IsValid == false) { return false; } Faction faction = Find.FactionManager.FirstFactionOfDef(FactionDefOf.Spacer); PawnGenerationRequest request = new PawnGenerationRequest(PawnKindDefOf.SpaceRefugee, faction, PawnGenerationContext.NonPlayer, false, false, false, false, true, false, 20f, false, true, true, null, null, null, null, null, null); Pawn pawn = PawnGenerator.GeneratePawn(request); HealthUtility.GiveInjuriesToForceDowned(pawn); string label = "LetterLabelRefugeePodCrash".Translate(); string text = "RefugeePodCrash".Translate(); PawnRelationUtility.TryAppendRelationsWithColonistsInfo(ref text, ref label, pawn); Find.LetterStack.ReceiveLetter(label, text, LetterType.BadNonUrgent, intVec, null); DropPodUtility.MakeDropPodAt(intVec, new DropPodInfo { SingleContainedThing = pawn, openDelay = 180, leaveSlag = true }); return true; }
public static void GeneratePawns(PawnGroupMakerParms parms, PawnGroupMaker groupMaker, List <Pawn> outPawns, bool errorOnZeroResults = true) { bool canBringFood = parms.raidStrategy?.pawnsCanBringFood ?? true; // 15.08.2021 RW1.3 added total points parameter to .CanUsePawn // For now just using parms.points however unsure if this will mess other things up Predicate <Pawn> postGear = parms.raidStrategy == null ? null : new Predicate <Pawn>(p => parms.raidStrategy.Worker.CanUsePawn(parms.points, p, otherPawns: outPawns)); var madeOnePawnIncap = false; PawnGenUtility.cachedConvertedPawnKindDefs = new Dictionary <string, PawnKindDef>(); foreach (PawnGenOption pawnGenOption in SolarRaidGroupMaker.ChoosePawnGenByConstraint( pointsTotal: parms.points, options: groupMaker.options, groupParms: parms )) { PawnKindDef kind = pawnGenOption.kind; Faction faction = parms.faction; int tile = parms.tile; bool allowFood = canBringFood; bool inhabitants = parms.inhabitants; Predicate <Pawn> validatorPostGear = postGear; var request = new PawnGenerationRequest( kind: PawnGenUtility.ConvertDefAndStoreOld(original: kind), faction: faction, context: PawnGenerationContext.NonPlayer, tile: tile, forceGenerateNewPawn: false, newborn: false, allowDead: false, allowDowned: false, canGeneratePawnRelations: true, mustBeCapableOfViolence: true, colonistRelationChanceFactor: 1f, forceAddFreeWarmLayerIfNeeded: true, allowGay: true, allowFood: allowFood, inhabitant: inhabitants, certainlyBeenInCryptosleep: false, forceRedressWorldPawnIfFormerColonist: false, worldPawnFactionDoesntMatter: false, validatorPreGear: pa => !pa.skills.GetSkill(skillDef: Defs_Rimworld.MeleeSkill).TotallyDisabled, validatorPostGear: validatorPostGear, minChanceToRedressWorldPawn: null, fixedBiologicalAge: null, fixedChronologicalAge: null, fixedGender: null, fixedMelanin: null, fixedLastName: null ); Pawn pawn = PawnGenerator.GeneratePawn(request: request); if (parms.forceOneIncap && !madeOnePawnIncap) { pawn.health.forceIncap = true; pawn.mindState.canFleeIndividual = false; madeOnePawnIncap = true; } PawnFinaliser(pawn: pawn); outPawns.Add(item: pawn); } }
public virtual PawnGenerationRequest Notify_PawnGenerationRequest(PawnGenerationRequest req) { return(req); }
public override float GenerationChance(Pawn generated, Pawn other, PawnGenerationRequest request) { return(LovePartnerRelationUtility.LovePartnerRelationGenerationChance(generated, other, request, false) * base.BaseGenerationChanceFactor(generated, other, request)); }
protected override bool TryExecuteWorker(IncidentParms parms) { Map map = (Map)parms.target; IntVec3 spawnSpot; if (!this.TryFindSpawnSpot(map, out spawnSpot)) { return(false); } Faction faction; if (!this.TryFindEnemyFaction(out faction)) { return(false); } if (!GenCollection.Any(map.listerBuildings.allBuildingsColonist, (Building b) => b.def.IsCommsConsole && b.GetComp <CompPowerTrader>().PowerOn)) { if (Prefs.DevMode) { Log.Message("NeedsComms: No powered on comms-console found, ignoring chased refugee request."); } return(false); } int @int = Rand.Int; IncidentParms raidParms = StorytellerUtility.DefaultParmsNow(IncidentCategoryDefOf.ThreatBig, map); raidParms.forced = true; raidParms.faction = faction; raidParms.raidStrategy = RaidStrategyDefOf.ImmediateAttack; raidParms.raidArrivalMode = PawnsArrivalModeDefOf.EdgeWalkIn; raidParms.spawnCenter = spawnSpot; raidParms.points = Mathf.Max(raidParms.points * IncidentWorker_RefugeeChased.RaidPointsFactorRange.RandomInRange, faction.def.MinPointsToGeneratePawnGroup(PawnGroupKindDefOf.Combat)); raidParms.pawnGroupMakerSeed = new int?(@int); PawnGroupMakerParms defaultPawnGroupMakerParms = IncidentParmsUtility.GetDefaultPawnGroupMakerParms(PawnGroupKindDefOf.Combat, raidParms, false); defaultPawnGroupMakerParms.points = IncidentWorker_Raid.AdjustedRaidPoints(defaultPawnGroupMakerParms.points, raidParms.raidArrivalMode, raidParms.raidStrategy, defaultPawnGroupMakerParms.faction, PawnGroupKindDefOf.Combat); IEnumerable <PawnKindDef> pawnKinds = PawnGroupMakerUtility.GeneratePawnKindsExample(defaultPawnGroupMakerParms); PawnGenerationRequest request = new PawnGenerationRequest(PawnKindDefOf.SpaceRefugee, null, PawnGenerationContext.NonPlayer, -1, false, false, false, false, true, false, 20f, false, true, true, false, false, false, false, null, null, null, null, null, null, null, null); Pawn refugee = PawnGenerator.GeneratePawn(request); refugee.relations.everSeenByPlayer = true; string text = "RefugeeChasedInitial".Translate(refugee.Name.ToStringFull, refugee.story.Title, faction.def.pawnsPlural, faction.Name, refugee.ageTracker.AgeBiologicalYears, PawnUtility.PawnKindsToCommaList(pawnKinds, true), refugee.Named("PAWN")); text = text.AdjustedFor(refugee, "PAWN"); PawnRelationUtility.TryAppendRelationsWithColonistsInfo(ref text, refugee); DiaNode diaNode = new DiaNode(text); DiaOption diaOption = new DiaOption("RefugeeChasedInitial_Accept".Translate()); diaOption.action = delegate { GenSpawn.Spawn(refugee, spawnSpot, map, WipeMode.Vanish); refugee.SetFaction(Faction.OfPlayer, null); CameraJumper.TryJump(refugee); QueuedIncident qi = new QueuedIncident(new FiringIncident(IncidentDefOf.RaidEnemy, null, raidParms), Find.TickManager.TicksGame + IncidentWorker_RefugeeChased.RaidDelay.RandomInRange, 0); Find.Storyteller.incidentQueue.Add(qi); }; diaOption.resolveTree = true; diaNode.options.Add(diaOption); string text2 = "RefugeeChasedRejected".Translate(refugee.LabelShort, refugee); DiaNode diaNode2 = new DiaNode(text2); DiaOption diaOption2 = new DiaOption("OK".Translate()); diaOption2.resolveTree = true; diaNode2.options.Add(diaOption2); DiaOption diaOption3 = new DiaOption("RefugeeChasedInitial_Reject".Translate()); diaOption3.action = delegate { Find.WorldPawns.PassToWorld(refugee, PawnDiscardDecideMode.Decide); }; diaOption3.link = diaNode2; diaNode.options.Add(diaOption3); string title = "RefugeeChasedTitle".Translate(map.Parent.Label); Find.WindowStack.Add(new Dialog_NodeTreeWithFactionInfo(diaNode, faction, true, true, title)); Find.Archive.Add(new ArchivedDialog(diaNode.text, title, faction)); return(true); }
/// <summary> /// Tries to revert the given pawn. /// </summary> /// <param name="transformedPawn">The transformed pawn.</param> /// <returns></returns> public override bool TryRevert(Pawn transformedPawn) { Tuple <TransformedPawn, TransformedStatus> status = GameComp.GetTransformedPawnContaining(transformedPawn); if (status != null) { if (status.Item2 != TransformedStatus.Transformed) { return(false); } if (status.Item1 is TransformedPawnSingle inst) { if (TryRevertImpl(inst)) { GameComp.RemoveInstance(inst); return(true); } else { Log.Warning($"could not revert original pawn instance {inst}"); } } else { Log.Warning($"{nameof(SimpleMechaniteMutagen)} received \"{status.Item1?.GetType()?.Name ??"NULL"}\" but was expecting \"{nameof(TransformedPawnSingle)}\""); } return(false); } else { Log.Warning($"unable to find status for transformed pawn {transformedPawn.ThingID}"); } Hediff formerHuman = transformedPawn.health.hediffSet.hediffs.FirstOrDefault(h => h.def == TfHediffDefOf.TransformedHuman); if (formerHuman == null) { return(false); } PawnGenerationRequest request = TransformerUtility.GenerateRandomPawnFromAnimal(transformedPawn); Pawn pawnTf = PawnGenerator.GeneratePawn(request); pawnTf.needs.food.CurLevel = transformedPawn.needs.food.CurLevel; pawnTf.needs.rest.CurLevel = transformedPawn.needs.rest.CurLevel; Log.Message($"going to spawn {pawnTf.Name} {pawnTf.KindLabel}"); var spawned = (Pawn)GenSpawn.Spawn(pawnTf, transformedPawn.GetCorrectPosition(), transformedPawn.GetCorrectMap()); spawned.equipment.DestroyAllEquipment(); spawned.apparel.DestroyAll(); if (transformedPawn.Name is NameTriple nT) { spawned.Name = nT; //give the new random pawn the same name as the former human } for (var i = 0; i < 10; i++) { IntermittentMagicSprayer.ThrowMagicPuffDown(spawned.GetCorrectPosition().ToVector3(), spawned.GetCorrectMap()); IntermittentMagicSprayer.ThrowMagicPuffUp(spawned.GetCorrectPosition().ToVector3(), spawned.GetCorrectMap()); } AddReversionThought(spawned, formerHuman.CurStageIndex); transformedPawn.Destroy(); return(true); }
public static bool KinseyException(ref Pawn __result, Pawn generatedChild, Pawn existingChild, Gender genderToGenerate, PawnGenerationRequest childRequest, bool newlyGeneratedParentsWillBeSpousesIfNotGay) { if (PsychologyBase.ActivateKinsey()) { //TODO: Turn this into a transpiler instead of a prefix. float ageChronologicalYearsFloat = generatedChild.ageTracker.AgeChronologicalYearsFloat; float ageChronologicalYearsFloat2 = existingChild.ageTracker.AgeChronologicalYearsFloat; float num = (genderToGenerate != Gender.Male) ? 16f : 14f; float num2 = (genderToGenerate != Gender.Male) ? 45f : 50f; float num3 = (genderToGenerate != Gender.Male) ? 27f : 30f; float num4 = Mathf.Max(ageChronologicalYearsFloat, ageChronologicalYearsFloat2) + num; float maxChronologicalAge = num4 + (num2 - num); float midChronologicalAge = num4 + (num3 - num); var parameters = new object[] { num4, maxChronologicalAge, midChronologicalAge, num, generatedChild, existingChild, childRequest, null, null, null, null }; Traverse.Create(typeof(PawnRelationWorker_Sibling)).Method("GenerateParentParams", new Type[] { typeof(float), typeof(float), typeof(float), typeof(float), typeof(Pawn), typeof(Pawn), typeof(PawnGenerationRequest), typeof(float).MakeByRefType(), typeof(float).MakeByRefType(), typeof(float).MakeByRefType(), typeof(string).MakeByRefType() }).GetValue(parameters); float value = (float)parameters[7]; float value2 = (float)parameters[8]; float value3 = (float)parameters[9]; string last = (string)parameters[10]; bool allowGay = true; Pawn parent = null; if (genderToGenerate == Gender.Male && existingChild.GetMother() != null) { parent = existingChild.GetMother(); } else if (genderToGenerate == Gender.Female && existingChild.GetFather() != null) { parent = existingChild.GetFather(); } if (PsycheHelper.PsychologyEnabled(parent)) { float kinsey = 3 - PsycheHelper.Comp(parent).Sexuality.kinseyRating; float num5 = Mathf.InverseLerp(3f, 0f, -kinsey); if (newlyGeneratedParentsWillBeSpousesIfNotGay && last.NullOrEmpty() && Rand.Value < num5) { last = ((NameTriple)parent.Name).Last; allowGay = false; } } Faction faction = existingChild.Faction; if (faction == null || faction.IsPlayer) { bool tryMedievalOrBetter = faction != null && faction.def.techLevel >= TechLevel.Medieval; if (!Find.FactionManager.TryGetRandomNonColonyHumanlikeFaction(out faction, tryMedievalOrBetter, true, TechLevel.Undefined)) { faction = Faction.OfAncients; } } PawnKindDef kindDef = existingChild.kindDef; Faction faction2 = faction; bool forceGenerateNewPawn = true; bool allowDead = true; bool allowDowned = true; bool canGeneratePawnRelations = false; Gender? fixedGender = new Gender?(genderToGenerate); float? fixedMelanin = new float?(value3); string fixedLastName = last; PawnGenerationRequest request = new PawnGenerationRequest(kindDef, faction2, PawnGenerationContext.NonPlayer, -1, forceGenerateNewPawn, false, allowDead, allowDowned, canGeneratePawnRelations, false, 1f, false, allowGay, true, false, false, false, false, null, null, null, new float?(value), new float?(value2), fixedGender, fixedMelanin, fixedLastName); Pawn pawn = PawnGenerator.GeneratePawn(request); if (!Find.WorldPawns.Contains(pawn)) { Find.WorldPawns.PassToWorld(pawn, PawnDiscardDecideMode.Decide); } __result = pawn; return(false); } return(true); }
private static void GenerateParentParams(float minChronologicalAge, float maxChronologicalAge, float midChronologicalAge, float minBioAgeToHaveChildren, Pawn generatedChild, Pawn existingChild, PawnGenerationRequest childRequest, out float biologicalAge, out float chronologicalAge, out float melanin, out string lastName) { chronologicalAge = Rand.GaussianAsymmetric(midChronologicalAge, (midChronologicalAge - minChronologicalAge) / 2f, (maxChronologicalAge - midChronologicalAge) / 2f); chronologicalAge = Mathf.Clamp(chronologicalAge, minChronologicalAge, maxChronologicalAge); biologicalAge = Rand.Range(minBioAgeToHaveChildren, Mathf.Min(existingChild.RaceProps.lifeExpectancy, chronologicalAge)); if (existingChild.GetFather() != null) { melanin = ParentRelationUtility.GetRandomSecondParentSkinColor(existingChild.GetFather().story.melanin, existingChild.story.melanin, childRequest.FixedMelanin); } else if (existingChild.GetMother() != null) { melanin = ParentRelationUtility.GetRandomSecondParentSkinColor(existingChild.GetMother().story.melanin, existingChild.story.melanin, childRequest.FixedMelanin); } else if (!childRequest.FixedMelanin.HasValue) { melanin = PawnSkinColors.GetRandomMelaninSimilarTo(existingChild.story.melanin, 0f, 1f); } else { float num = Mathf.Min(childRequest.FixedMelanin.Value, existingChild.story.melanin); float num2 = Mathf.Max(childRequest.FixedMelanin.Value, existingChild.story.melanin); if (Rand.Value < 0.5f) { melanin = PawnSkinColors.GetRandomMelaninSimilarTo(num, 0f, num); } else { melanin = PawnSkinColors.GetRandomMelaninSimilarTo(num2, num2, 1f); } } lastName = null; if (!ChildRelationUtility.DefinitelyHasNotBirthName(existingChild) && ChildRelationUtility.ChildWantsNameOfAnyParent(existingChild)) { if (existingChild.GetMother() == null && existingChild.GetFather() == null) { if (Rand.Value < 0.5f) { lastName = ((NameTriple)existingChild.Name).Last; } } else { string last = ((NameTriple)existingChild.Name).Last; string b = null; if (existingChild.GetMother() != null) { b = ((NameTriple)existingChild.GetMother().Name).Last; } else if (existingChild.GetFather() != null) { b = ((NameTriple)existingChild.GetFather().Name).Last; } if (last != b) { lastName = last; } } } }
public override void GenerateForces(Map map, ResolveParams rp, ScatterOptions options) { Debug.Log(Debug.ForceGen, "Generating mechanoid forces"); CellRect rect = rp.rect; /*if (rect.minX < 15 || rect.minZ < 15 || rect.maxX > map.Size.x - 15 || rect.maxZ > map.Size.z - 15) { * return; //do not add enemies if we're on the map edge * } * * if (!CellFinder.TryFindRandomCellInsideWith(rect, (IntVec3 x) => x.Standable(map) && options.roomMap[x.x - rect.BottomLeft.x, x.z - rect.BottomLeft.z] > 1, out IntVec3 testCell)) { * return; //interrupt if there are no closed cells available * }*/ PawnKindDef pawnKindDef = null; if (powerMax == 0) { powerMax = rect.Area / 30.0f; } powerMax = ScalePointsToDifficulty(powerMax); float powerThreshold = (Math.Abs(Rand.Gaussian(0.5f, 1)) * powerMax) + 1; float cumulativePower = 0; Faction faction = Faction.OfMechanoids; Lord lord = LordMaker.MakeNewLord(lordJob: new LordJob_DefendPoint(rect.CenterCell), faction: faction, map: map, startingPawns: null); int tile = map.Tile; while (cumulativePower <= powerThreshold) { PawnKindDef currentPawnKindDef = (from kind in DefDatabase <PawnKindDef> .AllDefsListForReading where kind.RaceProps.IsMechanoid select kind).RandomElementByWeight((PawnKindDef kind) => 1f / kind.combatPower); PawnGenerationRequest request = new PawnGenerationRequest(currentPawnKindDef, faction, PawnGenerationContext.NonPlayer, tile, true, false, false, //allowDead is last false, true, true, 1f, false, true, true, true, false, false, false, true, 0, null, 1, null, null, null, null, null, null, null); IntVec3 cell = IntVec3.Invalid; // if (!CellFinder.TryFindRandomCellInsideWith(rect, (IntVec3 x) => x.Standable(map) && options.roomMap[x.x - rect.minX, x.z - rect.minZ] > 1, out cell)) { CellFinder.TryFindRandomSpawnCellForPawnNear(rect.CenterCell, map, out cell); // } if (cell != IntVec3.Invalid) { Pawn pawn = PawnGenerator.GeneratePawn(request); FilthMaker.TryMakeFilth(cell, map, ThingDefOf.Filth_Blood, 5); GenSpawn.Spawn(pawn, cell, map, WipeMode.Vanish); lord.AddPawn(pawn); cumulativePower += pawn.kindDef.combatPower; } else { break; //no more suitable cells } Debug.Log(Debug.ForceGen, "Spawned mechanoid of faction {0}", faction.Name); } }
public static void TryToShareChildrenForGeneratedLovePartner(Pawn generated, Pawn other, PawnGenerationRequest request, float extraChanceFactor) { if (generated.gender == other.gender) { return; } List<Pawn> list = other.relations.Children.ToList<Pawn>(); for (int i = 0; i < list.Count; i++) { Pawn pawn = list[i]; float num = 1f; if (generated.gender == Gender.Male) { num = ChildRelationUtility.ChanceOfBecomingChildOf(pawn, generated, other, null, new PawnGenerationRequest?(request), null); } else if (generated.gender == Gender.Female) { num = ChildRelationUtility.ChanceOfBecomingChildOf(pawn, other, generated, null, null, new PawnGenerationRequest?(request)); } num *= extraChanceFactor; if (Rand.Value < num) { if (generated.gender == Gender.Male) { pawn.SetFather(generated); } else if (generated.gender == Gender.Female) { pawn.SetMother(generated); } } } }
// // Static Methods // private static Pawn GenerateParent(Pawn generatedChild, Pawn existingChild, Gender genderToGenerate, PawnGenerationRequest childRequest, bool newlyGeneratedParentsWillBeSpousesIfNotGay) { float ageChronologicalYearsFloat = generatedChild.ageTracker.AgeChronologicalYearsFloat; float ageChronologicalYearsFloat2 = existingChild.ageTracker.AgeChronologicalYearsFloat; float num = (genderToGenerate != Gender.Male) ? 16f : 14f; float num2 = (genderToGenerate != Gender.Male) ? 45f : 50f; float num3 = (genderToGenerate != Gender.Male) ? 27f : 30f; float num4 = Mathf.Max(ageChronologicalYearsFloat, ageChronologicalYearsFloat2) + num; float maxChronologicalAge = num4 + (num2 - num); float midChronologicalAge = num4 + (num3 - num); float value; float value2; float value3; string last; PawnRelationWorker_Sibling.GenerateParentParams(num4, maxChronologicalAge, midChronologicalAge, num, generatedChild, existingChild, childRequest, out value, out value2, out value3, out last); bool allowGay = true; if (newlyGeneratedParentsWillBeSpousesIfNotGay && last.NullOrEmpty() && Rand.Value < 0.8f) { if (genderToGenerate == Gender.Male && existingChild.GetMother() != null && !existingChild.GetMother().story.traits.HasTrait(TraitDefOf.Gay)) { last = ((NameTriple)existingChild.GetMother().Name).Last; allowGay = false; } else if (genderToGenerate == Gender.Female && existingChild.GetFather() != null && !existingChild.GetFather().story.traits.HasTrait(TraitDefOf.Gay)) { last = ((NameTriple)existingChild.GetFather().Name).Last; allowGay = false; } } Faction faction = existingChild.Faction; if (faction == null || faction.IsPlayer) { bool tryMedievalOrBetter = faction != null && faction.def.techLevel >= TechLevel.Medieval; Find.FactionManager.TryGetRandomNonColonyHumanlikeFaction(out faction, tryMedievalOrBetter, true); } Gender?fixedGender = new Gender?(genderToGenerate); float? fixedMelanin = new float?(value3); string fixedLastName = last; PawnGenerationRequest request = new PawnGenerationRequest(existingChild.kindDef, faction, PawnGenerationContext.NonPlayer, null, true, false, true, true, false, false, 1f, false, allowGay, true, null, new float?(value), new float?(value2), fixedGender, fixedMelanin, fixedLastName); Pawn pawn = PawnGenerator.GeneratePawn(request); if (!Find.WorldPawns.Contains(pawn)) { Find.WorldPawns.PassToWorld(pawn, PawnDiscardDecideMode.KeepForever); } return(pawn); }
public static float LovePartnerRelationGenerationChance(Pawn generated, Pawn other, PawnGenerationRequest request, bool ex) { if (generated.ageTracker.AgeBiologicalYearsFloat < 14f) { return 0f; } if (other.ageTracker.AgeBiologicalYearsFloat < 14f) { return 0f; } if (generated.gender == other.gender && (!other.story.traits.HasTrait(TraitDefOf.Gay) || !request.AllowGay)) { return 0f; } if (generated.gender != other.gender && other.story.traits.HasTrait(TraitDefOf.Gay)) { return 0f; } float num = 1f; if (ex) { int num2 = 0; List<DirectPawnRelation> directRelations = other.relations.DirectRelations; for (int i = 0; i < directRelations.Count; i++) { if (LovePartnerRelationUtility.IsExLovePartnerRelation(directRelations[i].def)) { num2++; } } num = Mathf.Pow(0.2f, (float)num2); } else if (LovePartnerRelationUtility.HasAnyLovePartner(other)) { return 0f; } float num3 = (generated.gender != other.gender) ? 1f : 0.01f; float generationChanceAgeFactor = LovePartnerRelationUtility.GetGenerationChanceAgeFactor(generated); float generationChanceAgeFactor2 = LovePartnerRelationUtility.GetGenerationChanceAgeFactor(other); float generationChanceAgeGapFactor = LovePartnerRelationUtility.GetGenerationChanceAgeGapFactor(generated, other, ex); float num4 = 1f; if (generated.GetRelations(other).Any((PawnRelationDef x) => x.familyByBloodRelation)) { num4 = 0.01f; } float num5; if (request.FixedMelanin.HasValue) { num5 = ChildRelationUtility.GetMelaninSimilarityFactor(request.FixedMelanin.Value, other.story.melanin); } else { num5 = PawnSkinColors.GetMelaninCommonalityFactor(other.story.melanin); } return num * generationChanceAgeFactor * generationChanceAgeFactor2 * generationChanceAgeGapFactor * num3 * num5 * num4; }
public override void CreateRelation(Pawn generated, Pawn other, ref PawnGenerationRequest request) { bool num = other.GetMother() != null; bool flag = other.GetFather() != null; bool flag2 = Rand.Value < 0.85f; if (num && LovePartnerRelationUtility.HasAnyLovePartner(other.GetMother())) { flag2 = false; } if (flag && LovePartnerRelationUtility.HasAnyLovePartner(other.GetFather())) { flag2 = false; } if (!num) { Pawn newMother = GenerateParent(generated, other, Gender.Female, request, flag2); other.SetMother(newMother); } generated.SetMother(other.GetMother()); if (!flag) { Pawn newFather = GenerateParent(generated, other, Gender.Male, request, flag2); other.SetFather(newFather); } generated.SetFather(other.GetFather()); if (!num || !flag) { if (other.GetMother().story.traits.HasTrait(TraitDefOf.Gay) || other.GetFather().story.traits.HasTrait(TraitDefOf.Gay)) { other.GetFather().relations.AddDirectRelation(PawnRelationDefOf.ExLover, other.GetMother()); } else if (flag2) { Pawn mother = other.GetMother(); Pawn father = other.GetFather(); NameTriple nameTriple = mother.Name as NameTriple; father.relations.AddDirectRelation(PawnRelationDefOf.Spouse, mother); if (nameTriple != null) { PawnGenerationRequest request2 = default(PawnGenerationRequest); SpouseRelationUtility.ResolveNameForSpouseOnGeneration(ref request2, mother); string b = nameTriple.Last; string text = null; if (request2.FixedLastName != null) { b = request2.FixedLastName; } if (request2.FixedBirthName != null) { text = request2.FixedBirthName; } if (mother.story != null && (nameTriple.Last != b || mother.story.birthLastName != text)) { mother.story.birthLastName = text; } } } else { LovePartnerRelationUtility.GiveRandomExLoverOrExSpouseRelation(other.GetFather(), other.GetMother()); } } ResolveMyName(ref request, generated); ResolveMySkinColor(ref request, generated); }
private static Pawn GenerateParent(Pawn generatedChild, Pawn existingChild, Gender genderToGenerate, PawnGenerationRequest childRequest, bool newlyGeneratedParentsWillBeSpousesIfNotGay) { float ageChronologicalYearsFloat = generatedChild.ageTracker.AgeChronologicalYearsFloat; float ageChronologicalYearsFloat2 = existingChild.ageTracker.AgeChronologicalYearsFloat; float num = (genderToGenerate == Gender.Male) ? 14f : 16f; float num2 = (genderToGenerate == Gender.Male) ? 50f : 45f; float num3 = (genderToGenerate == Gender.Male) ? 30f : 27f; float num4 = Mathf.Max(ageChronologicalYearsFloat, ageChronologicalYearsFloat2) + num; float maxChronologicalAge = num4 + (num2 - num); float midChronologicalAge = num4 + (num3 - num); GenerateParentParams(num4, maxChronologicalAge, midChronologicalAge, num, generatedChild, existingChild, childRequest, out float biologicalAge, out float chronologicalAge, out float melanin, out string lastName); bool allowGay = true; Faction faction = existingChild.Faction; if (faction == null || faction.IsPlayer) { bool tryMedievalOrBetter = faction != null && (int)faction.def.techLevel >= 3; if (!Find.FactionManager.TryGetRandomNonColonyHumanlikeFaction(out faction, tryMedievalOrBetter, allowDefeated: true)) { faction = Faction.OfAncients; } } Pawn pawn = PawnGenerator.GeneratePawn(new PawnGenerationRequest(existingChild.kindDef, faction, PawnGenerationContext.NonPlayer, -1, forceGenerateNewPawn: true, newborn: false, allowDead: true, allowDowned: true, canGeneratePawnRelations: false, mustBeCapableOfViolence: false, 1f, forceAddFreeWarmLayerIfNeeded: false, allowGay, allowFood: true, allowAddictions: true, inhabitant: false, certainlyBeenInCryptosleep: false, forceRedressWorldPawnIfFormerColonist: false, worldPawnFactionDoesntMatter: false, 0f, null, 1f, null, null, null, null, null, biologicalAge, chronologicalAge, genderToGenerate, melanin, lastName)); if (!Find.WorldPawns.Contains(pawn)) { Find.WorldPawns.PassToWorld(pawn); } return(pawn); }
public static Pawn MakePawnFromGenomeSequence(GenomeSequence genomeSequence, Thing creator) { //int adultAge = (int)genome.pawnKindDef.RaceProps.lifeStageAges.Last().minAge; QEEMod.TryLog("Generating pawn..."); PawnGenerationRequest request = new PawnGenerationRequest( genomeSequence.pawnKindDef, faction: creator.Faction, forceGenerateNewPawn: true, canGeneratePawnRelations: false, fixedGender: genomeSequence.gender, fixedBiologicalAge: 0, fixedChronologicalAge: 0, allowFood: false); Pawn pawn = PawnGenerator.GeneratePawn(request); //No pregenerated equipment. pawn?.equipment?.DestroyAllEquipment(); pawn?.apparel?.DestroyAll(); pawn?.inventory?.DestroyAll(); //No pregenerated hediffs. pawn.health.hediffSet.Clear(); //Add Hediff marking them as a clone. QEEMod.TryLog("Adding hediffs to generated pawn"); pawn.health.AddHediff(QEHediffDefOf.QE_CloneStatus); if (genomeSequence.hediffInfos != null && genomeSequence.hediffInfos.Count > 0) { //add hediffs to pawn from defs in HediffInfo class foreach (HediffInfo h in genomeSequence.hediffInfos) { pawn.health.AddHediff(h.def, h.part); } } //Set everything else. if (pawn.story is Pawn_StoryTracker storyTracker) { QEEMod.TryLog("Setting Pawn_StoryTracker attributes for generated pawn..."); storyTracker.bodyType = genomeSequence.bodyType; storyTracker.crownType = genomeSequence.crownType; storyTracker.hairColor = genomeSequence.hairColor; storyTracker.hairDef = genomeSequence.hair ?? PawnHairChooser.RandomHairDefFor(pawn, pawn.Faction.def); storyTracker.melanin = genomeSequence.skinMelanin; //headGraphicPath is private, so we need Harmony to set its value if (genomeSequence.headGraphicPath != null) { QEEMod.TryLog("Setting headGraphicPath for generated pawn"); AccessTools.Field(typeof(Pawn_StoryTracker), "headGraphicPath").SetValue(storyTracker, genomeSequence.headGraphicPath); } else { //could use this code to make a random head, instead of the static graphic paths. //AccessTools.Field(typeof(Pawn_StoryTracker), "headGraphicPath").SetValue(storyTracker, //GraphicDatabaseHeadRecords.GetHeadRandom(genomeSequence.gender, PawnSkinColors.GetSkinColor(genomeSequence.skinMelanin), genomeSequence.crownType).GraphicPath); QEEMod.TryLog("No headGraphicPath in genome template, setting to default head"); string path = genomeSequence.gender == Gender.Male ? "Things/Pawn/Humanlike/Heads/Male/Male_Average_Normal" : "Things/Pawn/Humanlike/Heads/Female/Female_Narrow_Normal"; AccessTools.Field(typeof(Pawn_StoryTracker), "headGraphicPath").SetValue(storyTracker, path); } storyTracker.traits.allTraits.Clear(); QEEMod.TryLog("Setting traits for generated pawn"); foreach (ExposedTraitEntry trait in genomeSequence.traits) { //storyTracker.traits.GainTrait(new Trait(trait.def, trait.degree)); storyTracker.traits.allTraits.Add(new Trait(trait.def, trait.degree)); if (pawn.workSettings != null) { pawn.workSettings.Notify_DisabledWorkTypesChanged(); } if (pawn.skills != null) { pawn.skills.Notify_SkillDisablesChanged(); } if (!pawn.Dead && pawn.RaceProps.Humanlike) { pawn.needs.mood.thoughts.situational.Notify_SituationalThoughtsDirty(); } } QEEMod.TryLog("Setting backstory for generated pawn"); //Give random vatgrown backstory. storyTracker.childhood = DefDatabase <BackstoryDef> .GetNamed("Backstory_ColonyVatgrown").GetFromDatabase(); storyTracker.adulthood = null; } if (pawn.skills is Pawn_SkillTracker skillsTracker) { foreach (SkillRecord skill in skillsTracker.skills) { skill.Level = 0; skill.passion = Passion.None; skill.Notify_SkillDisablesChanged(); } List <SkillRecord> skillPassions = new List <SkillRecord>(); int skillsPicked = 0; int iterations = 0; //Pick 4 random skills to give minor passions to. while (skillsPicked < 4 && iterations < 1000) { SkillRecord randomSkill = skillsTracker.skills.RandomElement(); if (!skillPassions.Contains(randomSkill)) { skillPassions.Add(randomSkill); randomSkill.passion = Passion.Minor; skillsPicked++; } iterations++; } skillsPicked = 0; iterations = 0; //Pick 2 random skills to give major passions to. while (skillsPicked < 2 && iterations < 1000) { SkillRecord randomSkill = skillsTracker.skills.RandomElement(); if (!skillPassions.Contains(randomSkill)) { skillPassions.Add(randomSkill); randomSkill.passion = Passion.Major; skillsPicked++; } iterations++; } } if (pawn.workSettings is Pawn_WorkSettings workSettings) { workSettings.EnableAndInitialize(); } //Alien Races compatibility. if (CompatibilityTracker.AlienRacesActive) { AlienRaceCompat.SetFieldsToAlienComp(pawn, genomeSequence); } PortraitsCache.SetDirty(pawn); PortraitsCache.PortraitsCacheUpdate(); return(pawn); }
public override void Tick() { if (Spawned) { sustainer.Maintain(); Vector3 vector = Position.ToVector3Shifted(); IntVec3 c; if (Rand.MTBEventOccurs(FilthSpawnMTB, 1f, 1.TicksToSeconds()) && CellFinder.TryFindRandomReachableCellNear(Position, Map, FilthSpawnRadius, TraverseParms.For(TraverseMode.NoPassClosedDoors, Danger.Deadly, false), null, null, out c, 999999)) { FilthMaker.MakeFilth(c, Map, filthTypes.RandomElement(), 1); } if (Rand.MTBEventOccurs(DustMoteSpawnMTB, 1f, 1.TicksToSeconds())) { MoteMaker.ThrowDustPuffThick(new Vector3(vector.x, 0f, vector.z) { y = AltitudeLayer.MoteOverhead.AltitudeFor() }, Map, Rand.Range(1.5f, 3f), new Color(1f, 1f, 1f, 2.5f)); } if (secondarySpawnTick <= Find.TickManager.TicksGame) { sustainer.End(); Map map = Map; IntVec3 position = Position; Destroy(DestroyMode.Vanish); PawnKindDef kindDef = HiveUtility.GetFactionKindDef(PawnKindDef.Named("BI_Queen_Brown"), queenFaction); Queen queen = PawnGenerator.GeneratePawn(kindDef, queenFaction) as Queen; queen.hiveLocation = position; if (hiveLocation != null) { queen.hiveLocation = hiveLocation; } GenSpawn.Spawn(queen, CellFinder.RandomClosewalkCellNear(position, map, 4, null), map); if (insectsPoints > 0f) { List <PawnKindDef> spawnablePawnKinds = HiveUtility.GetFactionKindDefs(queenFaction); insectsPoints = Mathf.Max(insectsPoints, spawnablePawnKinds.Min((PawnKindDef x) => x.combatPower)); float pointsLeft = insectsPoints; List <Pawn> list = new List <Pawn>(); int num = 0; while (pointsLeft > 0f) { num++; if (num > 1000) { Log.Error("Too many iterations.", false); break; } IEnumerable <PawnKindDef> source = from x in spawnablePawnKinds where x.combatPower <= pointsLeft select x; PawnKindDef pawnKindDef; if (!source.TryRandomElement(out pawnKindDef)) { break; } PawnGenerationRequest request = new PawnGenerationRequest(pawnKindDef, queenFaction, PawnGenerationContext.NonPlayer, -1, true, true, false, false, false, false, 1f, false, false, true, false, false, false, false, null, null, null, null, null, null, null, null); Pawn pawn = PawnGenerator.GeneratePawn(request); GenSpawn.Spawn(pawn, CellFinder.RandomClosewalkCellNear(position, map, 2, null), map, WipeMode.Vanish); queen.spawnedInsects.Add(pawn); Lord lord = queen.Lord; if (lord == null) { lord = queen.CreateNewLord(); } lord.AddPawn(pawn); list.Add(pawn); pointsLeft -= pawnKindDef.combatPower; } } } } }
public static void GenerateStartingApparelFor(Pawn pawn, PawnGenerationRequest request) { if (!pawn.RaceProps.ToolUser || !pawn.RaceProps.IsFlesh) { return; } if (pawn.Faction == null) { Log.Error("Cannot generate apparel for faction-less pawn " + pawn); return; } pawn.apparel.DestroyAll(DestroyMode.Vanish); float randomInRange = pawn.kindDef.apparelMoney.RandomInRange; float mapTemperature; NeededWarmth neededWarmth = PawnApparelGenerator.ApparelWarmthNeededNow(pawn, request, out mapTemperature); bool flag = Rand.Value < pawn.kindDef.apparelAllowHeadwearChance; PawnApparelGenerator.debugSb = null; if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb = new StringBuilder(); PawnApparelGenerator.debugSb.AppendLine("Generating apparel for " + pawn); PawnApparelGenerator.debugSb.AppendLine("Money: " + randomInRange.ToString("F0")); PawnApparelGenerator.debugSb.AppendLine("Needed warmth: " + neededWarmth); PawnApparelGenerator.debugSb.AppendLine("Headwear allowed: " + flag); } if (randomInRange >= 0.001f) { int num = 0; while (true) { PawnApparelGenerator.GenerateWorkingPossibleApparelSetFor(pawn, randomInRange, flag); if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.Append(num.ToString().PadRight(5) + "Trying: " + PawnApparelGenerator.workingSet.ToString()); } if (num >= 10 || Rand.Value >= 0.85f) { goto IL_1FA; } float num2 = Rand.Range(0.45f, 0.8f); float totalPrice = PawnApparelGenerator.workingSet.TotalPrice; if (totalPrice >= randomInRange * num2) { goto IL_1FA; } if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.AppendLine(string.Concat(new string[] { " -- Failed: Spent $", totalPrice.ToString("F0"), ", < ", (num2 * 100f).ToString("F0"), "% of money." })); } IL_36D: num++; continue; IL_1FA: if (num < 20 && Rand.Value < 0.97f && !PawnApparelGenerator.workingSet.Covers(BodyPartGroupDefOf.Torso)) { if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.AppendLine(" -- Failed: Does not cover torso."); } goto IL_36D; } if (num < 30 && Rand.Value < 0.8f && PawnApparelGenerator.workingSet.CoatButNoShirt()) { if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.AppendLine(" -- Failed: Coat but no shirt."); } goto IL_36D; } if (num < 50) { bool mustBeSafe = num < 17; if (!PawnApparelGenerator.workingSet.SatisfiesNeededWarmth(neededWarmth, mustBeSafe, mapTemperature)) { if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.AppendLine(" -- Failed: Wrong warmth."); } goto IL_36D; } } if (num < 80 && PawnApparelGenerator.workingSet.IsNaked(pawn.gender)) { if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.AppendLine(" -- Failed: Naked."); } goto IL_36D; } break; } if (DebugViewSettings.logApparelGeneration) { PawnApparelGenerator.debugSb.Append(string.Concat(new object[] { " -- Approved! Total price: $", PawnApparelGenerator.workingSet.TotalPrice.ToString("F0"), ", TotalInsulationCold: ", PawnApparelGenerator.workingSet.TotalInsulationCold })); } } if ((!pawn.kindDef.apparelIgnoreSeasons || request.ForceAddFreeWarmLayerIfNeeded) && !PawnApparelGenerator.workingSet.SatisfiesNeededWarmth(neededWarmth, false, 21f)) { PawnApparelGenerator.workingSet.AddFreeWarmthAsNeeded(neededWarmth); } if (DebugViewSettings.logApparelGeneration) { Log.Message(PawnApparelGenerator.debugSb.ToString()); } PawnApparelGenerator.workingSet.GiveToPawn(pawn); PawnApparelGenerator.workingSet.Reset(null, null); }
public virtual bool TrySpawnPawns(Pawn harvester = null) { if (this.HarvestableNow) { int squigs = Squigs.Count(); int snots = Snots.Count(); int grots = Grots.Count(); int orks = Orks.Count(); int greenskins = squigs + snots + grots + orks; Rand.PushState(this.thingIDNumber); var spawnRoll = Rand.ValueSeeded(this.thingIDNumber); Rand.PopState(); if (spawnRoll < (SpawnChance * (/*HealthTuning.DeathOnDownedChance_NonColonyHumanlikeFromPopulationIntentCurve.Evaluate(StorytellerUtilityPopulation.PopulationIntent + greenskins) **/ Find.Storyteller.difficulty.enemyDeathOnDownedChanceFactor) * this.Growth)) { PawnKindDef pawnKindDef; bool OrkoidHarvester = harvester == null || harvester.isOrkoid(); if (OrkoidHarvester) { List <PawnGenOption> options = new List <PawnGenOption>() { new PawnGenOption(AdeptusPawnKindDefOf.OG_Squig, SquigChance * (OrkoidFungalUtility.SquigSpawnCurve.Evaluate(squigs))), new PawnGenOption(AdeptusPawnKindDefOf.OG_Snotling, SnotlingChance * (OrkoidFungalUtility.SnotSpawnCurve.Evaluate(snots))), new PawnGenOption(AdeptusPawnKindDefOf.OG_Grot_Wild, GrotChance * ((this.ageInt / this.def.plant.LifespanTicks) + OrkoidFungalUtility.GrotSpawnCurve.Evaluate(grots))), new PawnGenOption(AdeptusPawnKindDefOf.OG_Ork_Wild, OrkChance * ((this.ageInt / this.def.plant.LifespanTicks) + OrkoidFungalUtility.OrkSpawnCurve.Evaluate(orks))) }; pawnKindDef = options.InRandomOrder().RandomElementByWeight(x => x.selectionWeight).kind; Rand.PushState(); if (pawnKindDef == AdeptusPawnKindDefOf.OG_Squig) { Rand.PushState(); pawnKindDef = DefDatabase <PawnKindDef> .AllDefsListForReading.Where(x => x.RaceProps.Animal && x.defName.Contains("OG_") && x.defName.Contains("_Squig")).RandomElementByWeight(x => AdeptusMath.Inverse(x.race.BaseMarketValue)); Rand.PopState(); } Rand.PopState(); StringBuilder builder = new StringBuilder(); builder.Append(pawnKindDef.LabelCap + " Spawned"); builder.AppendLine(); foreach (var item in options) { builder.Append(" " + item.kind.LabelCap + " weighted at " + item.selectionWeight); } if (Prefs.DevMode) { Log.Message(builder.ToString()); } } else { pawnKindDef = AdeptusPawnKindDefOf.OG_Squig; } Faction faction = FungalProps.spawnwild || !OrkoidHarvester ? null : Faction.OfPlayer; PawnGenerationRequest pawnGenerationRequest = new PawnGenerationRequest(pawnKindDef, faction, PawnGenerationContext.NonPlayer, -1, true, true, false, false, true, true, 0f, fixedGender: Gender.None, fixedBiologicalAge: Age, fixedChronologicalAge: Age); Pawn pawn = PawnGenerator.GeneratePawn(pawnGenerationRequest); if (pawnKindDef.RaceProps.Humanlike) { /* * if (pawn.kindDef == OGOrkPawnKindDefOf.OG_Ork_Wild) * { * pawn.story.childhood.identifier = "Ork_Base_Child"; * } * else if (pawn.kindDef == OGOrkPawnKindDefOf.OG_Grot_Wild) * { * pawn.story.childhood.identifier = "Grot_Base_Child"; * } */ if (!FungalProps.spawnwild && (Faction.OfPlayer.def == AdeptusFactionDefOf.OG_Ork_PlayerTribe || Faction.OfPlayer.def == AdeptusFactionDefOf.OG_Ork_PlayerColony)) { PawnKindDef pawnKind; if (Faction.OfPlayer.def == AdeptusFactionDefOf.OG_Ork_PlayerTribe) { pawnKind = pawn.def.defName.Contains("Alien_Grot") ? AdeptusPawnKindDefOf.Tribesperson_OG_Grot : DefDatabase <PawnKindDef> .AllDefsListForReading.Where(x => x.defName.Contains("Tribesperson_OG_Ork")).RandomElementByWeight(x => AdeptusMath.Inverse(x.combatPower)); } else { pawnKind = pawn.def.defName.Contains("Alien_Grot") ? AdeptusPawnKindDefOf.Colonist_OG_Grot : DefDatabase <PawnKindDef> .AllDefsListForReading.Where(x => x.defName.Contains("Colonist_OG_Ork")).RandomElementByWeight(x => AdeptusMath.Inverse(x.combatPower)); } pawn.ChangeKind(pawnKind); } else { pawn.ChangeKind(PawnKindDefOf.WildMan); } pawn.story.bodyType = pawn.story.childhood.BodyTypeFor(pawn.gender); } if (GrowthRateFactor_Fertility < 1f) { foreach (Need need in pawn.needs.AllNeeds) { if (need.def != NeedDefOf.Rest) { need.CurLevel = 0.1f; } } } else { float level = GrowthRateFactor_Fertility - 1f; pawn.needs.food.CurLevel = level; pawn.needs.rest.CurLevel = 1f; if (pawn.RaceProps.Humanlike) { pawn.needs.mood.CurLevel = level; } } Hediff hediff = HediffMaker.MakeHediff(HediffDefOf.Malnutrition, pawn); hediff.Severity = Math.Min(1f - GrowthRateFactor_Fertility, 0.8f); pawn.health.AddHediff(hediff); GenSpawn.Spawn(pawn, this.Position, this.Map, 0); if (harvester != null && harvester.Faction == Faction.OfPlayer) { TaggedString taggedString = "AdeptusMechanicus.Ork.FungalHarvest_SuccessMessage".Translate(harvester.Name, pawn.Label); Messages.Message(taggedString, pawn, MessageTypeDefOf.PositiveEvent, true); } return(true); } } return(false); }
private static bool Prefix(Pawn pawn, PawnGenerationRequest request) { if (pawn.story == null) { return(false); } RaceAddonThingDef thingDef = pawn.def as RaceAddonThingDef; foreach (var backstory in pawn.story.AllBackstories) { List <TraitEntry> forcedTraits = backstory.forcedTraits; if (forcedTraits != null) { foreach (var traitEntry in forcedTraits) { if (traitEntry.def == null) { Log.Error("Null forced trait def on " + pawn.story.childhood, false); } else if (!pawn.story.traits.HasTrait(traitEntry.def) && RaceAddonTools.CheckTrait(pawn.def, traitEntry)) { pawn.story.traits.GainTrait(new Trait(traitEntry.def, traitEntry.degree, false)); } } } } if (thingDef != null) { foreach (var set in thingDef.raceAddonSettings.traitSetting.forcedTraits) { if (Rand.Chance(set.chance)) { if (set.traitDef == null) { Log.Error("Null forced trait def on " + thingDef.defName, false); } else if (!pawn.story.traits.HasTrait(set.traitDef) && RaceAddonTools.CheckTrait(pawn.def, set.traitDef, set.degree)) { pawn.story.traits.GainTrait(new Trait(set.traitDef, set.degree, false)); } } } } int traitCount = 0; if (thingDef != null) { traitCount = thingDef.raceAddonSettings.traitSetting.traitCount.RandomInRange; } else { traitCount = Rand.RangeInclusive(2, 3); } if (request.AllowGay && (LovePartnerRelationUtility.HasAnyLovePartnerOfTheSameGender(pawn) || LovePartnerRelationUtility.HasAnyExLovePartnerOfTheSameGender(pawn))) { Trait trait = new Trait(TraitDefOf.Gay, PawnGenerator.RandomTraitDegree(TraitDefOf.Gay), false); if (RaceAddonTools.CheckTrait(pawn.def, trait)) { pawn.story.traits.GainTrait(trait); } } while (pawn.story.traits.allTraits.Count < traitCount) { TraitDef newTraitDef = DefDatabase <TraitDef> .AllDefsListForReading.RandomElementByWeight((TraitDef tr) => tr.GetGenderSpecificCommonality(pawn.gender)); int degree = PawnGenerator.RandomTraitDegree(newTraitDef); if (!pawn.story.traits.HasTrait(newTraitDef) && RaceAddonTools.CheckTrait(pawn.def, newTraitDef, degree)) { if (newTraitDef == TraitDefOf.Gay) { if (!request.AllowGay) { continue; } if (LovePartnerRelationUtility.HasAnyLovePartnerOfTheOppositeGender(pawn) || LovePartnerRelationUtility.HasAnyExLovePartnerOfTheOppositeGender(pawn)) { continue; } } if (request.Faction == null || Faction.OfPlayerSilentFail == null || !request.Faction.HostileTo(Faction.OfPlayer) || newTraitDef.allowOnHostileSpawn) { if (!pawn.story.traits.allTraits.Any((Trait tr) => newTraitDef.ConflictsWith(tr)) && (newTraitDef.conflictingTraits == null || !newTraitDef.conflictingTraits.Any((TraitDef tr) => pawn.story.traits.HasTrait(tr)))) { if (newTraitDef.requiredWorkTypes == null || !pawn.OneOfWorkTypesIsDisabled(newTraitDef.requiredWorkTypes)) { if (!pawn.WorkTagIsDisabled(newTraitDef.requiredWorkTags)) { if (!pawn.story.childhood.DisallowsTrait(newTraitDef, degree) && (pawn.story.adulthood == null || !pawn.story.adulthood.DisallowsTrait(newTraitDef, degree))) { Trait trait2 = new Trait(newTraitDef, degree, false); if (pawn.mindState != null && pawn.mindState.mentalBreaker != null) { float num2 = pawn.mindState.mentalBreaker.BreakThresholdExtreme; num2 += trait2.OffsetOfStat(StatDefOf.MentalBreakThreshold); num2 *= trait2.MultiplierOfStat(StatDefOf.MentalBreakThreshold); if (num2 > 0.4f) { continue; } } pawn.story.traits.GainTrait(trait2); } } } } } } } return(false); }
public override void PawnDied(Corpse corpse) { PawnGenerationRequest pawnGenerationRequest; PawnKindDef pawnKindDef = corpse.InnerPawn.kindDef; Pawn pawn = corpse.InnerPawn; IntVec3 position = corpse.Position; Map map = corpse.Map; Faction faction = pawn.Faction; float bioyears = pawn.ageTracker.AgeBiologicalYears; float chronoyears = pawn.ageTracker.AgeChronologicalYears; Pawn_MindState mind = pawn.mindState; Pawn newPawn1 = null; Pawn newPawn2 = null; bool spawn = false; Lord lord = pawn.GetLord(); List <Thing> spawned = new List <Thing>(); if (map != null) { if (corpse.InnerPawn.kindDef == AdeptusPawnKindDefOf.OG_Chaos_Deamon_Lessar_Horror_Blue) { spawn = true; pawnKindDef = AdeptusPawnKindDefOf.OG_Chaos_Deamon_Lessar_Horror_Brimstone; } else if (corpse.InnerPawn.kindDef == AdeptusPawnKindDefOf.OG_Chaos_Deamon_Lessar_Horror_Pink) { spawn = true; pawnKindDef = AdeptusPawnKindDefOf.OG_Chaos_Deamon_Lessar_Horror_Blue; } if (spawn) { pawnGenerationRequest = new PawnGenerationRequest(pawnKindDef, corpse.InnerPawn.Faction, PawnGenerationContext.NonPlayer, -1, true, false, true, false, true, true, 20f, fixedBiologicalAge: bioyears, fixedChronologicalAge: chronoyears); newPawn1 = PawnGenerator.GeneratePawn(pawnGenerationRequest); newPawn2 = PawnGenerator.GeneratePawn(pawnGenerationRequest); spawned = new List <Thing>() { newPawn1, newPawn2 }; if (pawn.Faction != null) { if (map.mapPawns.SpawnedPawnsInFaction(pawn.Faction).Any((Pawn p) => p != newPawn1 && p != newPawn2 && p.GetLord() != null)) { bool validator(Thing p) => p != newPawn1 && p != newPawn2 && ((Pawn)p).GetLord() != null; Pawn p2 = (Pawn)GenClosest.ClosestThing_Global(position, map.mapPawns.SpawnedPawnsInFaction(newPawn1.Faction), 99999f, validator, null); lord = p2.GetLord(); } } if (lord == null) { try { LordJob_AssaultColony lordJob = new LordJob_AssaultColony(faction, false, false); lord = LordMaker.MakeNewLord((pawn.Faction), lordJob, map, null); } catch { // newPawn1.mindState.mentalStateHandler.TryStartMentalState(OGChaosDeamonDefOf.MentalState_OGChaosDeamon); // newPawn2.mindState.mentalStateHandler.TryStartMentalState(OGChaosDeamonDefOf.MentalState_OGChaosDeamon); } } else { try { newPawn1.mindState.duty = new PawnDuty(DutyDefOf.AssaultColony); newPawn2.mindState.duty = new PawnDuty(DutyDefOf.AssaultColony); } catch { // newPawn1.mindState.mentalStateHandler.TryStartMentalState(OGChaosDeamonDefOf.MentalState_OGChaosDeamon); // newPawn2.mindState.mentalStateHandler.TryStartMentalState(OGChaosDeamonDefOf.MentalState_OGChaosDeamon); } } if (spawn) { Pawn p = (Pawn)GenClosest.ClosestThing_Global(position, map.mapPawns.SpawnedPawnsInFaction(faction), 99999f, null, null); if (p.InMentalState) { if (p.MentalStateDef == MentalStateDefOf.PanicFlee || p.GetLord() == null || p.GetLord().Map == null) { spawn = false; } } } if (spawn && pawnKindDef != corpse.InnerPawn.kindDef && lord != null && map != null) { if (newPawn1 != null) { GenSpawn.Spawn(newPawn1, position, map, 0); if (lord != null) { lord.AddPawn(newPawn1); } } if (newPawn2 != null) { GenSpawn.Spawn(newPawn2, position, map, 0); if (lord != null) { lord.AddPawn(newPawn2); } } } } } if (position != null && map != null) { GenExplosion.DoExplosion(position, map, 1.9f, AdeptusDamageDefOf.OG_Chaos_Deamon_WarpfireDeath, corpse.InnerPawn, -1, -1f, null, null, null, null, null, 0f, 1, false, null, 0f, 1, 0f, false, null, spawned); } base.PawnDied(corpse); }
public override void CreateRelation(Pawn generated, Pawn other, ref PawnGenerationRequest request) { generated.relations.AddDirectRelation(PawnRelationDefOf.Lover, other); LovePartnerRelationUtility.TryToShareChildrenForGeneratedLovePartner(generated, other, request, 0.35f); PawnRelationWorker_Lover.ResolveMySkinColor(ref request, generated, other); }
public void Hatch() { try { PawnGenerationRequest request = new PawnGenerationRequest(this.Props.hatcherPawn, this.hatcheeFaction, PawnGenerationContext.NonPlayer, -1, false, true, false, false, true, false, 1f, false, true, true, true, false, false, false, false, 0f, 0f, null, 1f, null, null, null, null, null, null, null, null, null, null, null, null); for (int i = 0; i < this.parent.stackCount; i++) { Pawn pawn = PawnGenerator.GeneratePawn(request); if (PawnUtility.TrySpawnHatchedOrBornPawn(pawn, this.parent)) { if (pawn != null) { if (this.hatcheeParent != null) { if (pawn.playerSettings != null && this.hatcheeParent.playerSettings != null && this.hatcheeParent.Faction == this.hatcheeFaction) { pawn.playerSettings.AreaRestriction = this.hatcheeParent.playerSettings.AreaRestriction; } if (pawn.RaceProps.IsFlesh) { pawn.relations.AddDirectRelation(PawnRelationDefOf.Parent, this.hatcheeParent); } } if (this.otherParent != null && (this.hatcheeParent == null || this.hatcheeParent.gender != this.otherParent.gender) && pawn.RaceProps.IsFlesh) { pawn.relations.AddDirectRelation(PawnRelationDefOf.Parent, this.otherParent); } if (parent.Map != null) { List <Thing> ignoredThings = new List <Thing>(); List <Pawn> allPawnsSpawned = pawn.Map.mapPawns.AllPawnsSpawned; for (int k = 0; k < allPawnsSpawned.Count; k++) { if (allPawnsSpawned[k] != null && allPawnsSpawned[k].def.defName == pawn.def.defName) { ignoredThings.Add(allPawnsSpawned[k]); } } Thing pawnThing = pawn as Thing; ignoredThings.Add(pawnThing); if (AnimalBehaviours_Settings.flagExplodingAnimalEggs) { GenExplosion.DoExplosion(parent.Position, parent.Map, Props.range, DefDatabase <DamageDef> .GetNamed(Props.damageDef), parent, Props.damage, -1, SoundDef.Named(Props.soundDef), null, null, null, null, 0f, 1, false, null, 0f, 1, 0, false, null, ignoredThings); } } } if (this.parent.Spawned) { FilthMaker.TryMakeFilth(this.parent.Position, this.parent.Map, ThingDefOf.Filth_AmnioticFluid, 1, FilthSourceFlags.None); } } else { Find.WorldPawns.PassToWorld(pawn, PawnDiscardDecideMode.Discard); } } } finally { this.parent.Destroy(DestroyMode.Vanish); } }
public override bool AllowPawn(Pawn pawn, bool tryingToRedress, PawnGenerationRequest req) { return(allowedMelaninRange.Includes(pawn.story.melanin)); }
public Pawn XenomorphSpawnRequest() { Gender gender; bool QueenPresent = false; bool selected = Find.Selector.SingleSelectedThing == parent.pawn && Prefs.DevMode; List <PawnKindDef> pawnKindDefs = Props.pawnKindDefs; List <float> pawnKindWeights = Props.pawnKindWeights; PawnKindDef pawnKindDef = pawnKindDefs[pawnKindDefs.Count - 1]; int ind = 0; foreach (var p in MyMap.mapPawns.AllPawnsSpawned) { if (p.kindDef == XenomorphDefOf.RRY_Xenomorph_Queen) { QueenPresent = true; break; } } if (RoyaleEmbryo) { pawnKindDef = XenomorphDefOf.RRY_Xenomorph_Queen; } else { if (Pawn.kindDef.race == YautjaDefOf.RRY_Alien_Yautja && SettingsHelper.latest.AllowPredaliens)// && !predalienImpregnation) { pawnKindDef = XenomorphDefOf.RRY_Xenomorph_Predalien; } else if (Pawn.RaceProps.Humanlike) { pawnKindDef = Rand.Chance(0.5f) ? XenomorphDefOf.RRY_Xenomorph_Drone : XenomorphDefOf.RRY_Xenomorph_Warrior; } else if (Pawn.kindDef.race == ThingDefOf.Thrumbo && SettingsHelper.latest.AllowThrumbomorphs) { pawnKindDef = XenomorphDefOf.RRY_Xenomorph_Thrumbomorph; } else if (!Pawn.RaceProps.Humanlike && Pawn.BodySize < 0.9f) { pawnKindDef = XenomorphDefOf.RRY_Xenomorph_Runner; } else { while (pawnKindDef == null) { foreach (var PKDef in pawnKindDefs) { float hostSize = base.parent.pawn.BodySize; bool hostHumanlike = base.parent.pawn.RaceProps.Humanlike; float spawnRoll = ((Rand.Range(1, 100)) * hostSize); if (PKDef == XenomorphDefOf.RRY_Xenomorph_Queen) { if ((QueenPresent || predalienImpregnation || RoyalPresent)) { spawnRoll = 0; } else { spawnRoll *= 2; } } else if (predalienImpregnation) { spawnRoll = 0; if (PKDef == XenomorphDefOf.RRY_Xenomorph_Runner) { spawnRoll *= 2; } else if (PKDef == XenomorphDefOf.RRY_Xenomorph_Drone) { spawnRoll *= 2; } } else if (hostHumanlike) { if (PKDef == XenomorphDefOf.RRY_Xenomorph_Runner) { spawnRoll = 0; } if (PKDef == XenomorphDefOf.RRY_Xenomorph_Warrior) { spawnRoll *= 2; } else if (PKDef == XenomorphDefOf.RRY_Xenomorph_Drone) { spawnRoll *= 2; } } if (spawnRoll > (100 - pawnKindWeights[ind])) { pawnKindDef = PKDef; break; } ind++; } } } } if (pawnKindDef == XenomorphDefOf.RRY_Xenomorph_Queen) { gender = Gender.Female; } else { gender = Gender.None; } if (Prefs.DevMode) { // Log.Message(string.Format("spawning: {0}", pawnKindDef.label)); parent.pawn.resultingXenomorph(); } bool BeViolent = pawnKindDef == XenomorphDefOf.RRY_Xenomorph_Thrumbomorph ? true : true; PawnGenerationRequest request = new PawnGenerationRequest(pawnKindDef, Find.FactionManager.FirstFactionOfDef(pawnKindDef.defaultFactionType), PawnGenerationContext.NonPlayer, -1, true, true, false, false, true, false, 20f, fixedGender: gender); Pawn pawn = PawnGenerator.GeneratePawn(request); XenomorphPawn XP = pawn as XenomorphPawn; if (XP != null) { XP.HostRace = Pawn.def; } /* * XP.Drawer.renderer.graphics.nakedGraphic.colorTwo = HostBloodColour; * pawn.Notify_ColorChanged(); */ pawn.ageTracker.CurKindLifeStage.bodyGraphicData.colorTwo = HostBloodColour; XP.Drawer.renderer.graphics.ResolveAllGraphics(); return(pawn); }
private static bool on_begin_DoBirthSpawn(ref Pawn mother, ref Pawn father) { //TODO: Set pregnant hediff to torso //--Log.Message("patches_pregnancy::PATCH_Hediff_Pregnant::DoBirthSpawn() called"); var mother_name = (mother != null) ? mother.NameStringShort : "NULL"; var father_name = (father != null) ? father.NameStringShort : "NULL"; if (mother == null) { Log.Error("Hediff_Pregnant::DoBirthSpawn() - no mother defined"); return(false); } if (father == null) { Log.Warning("Hediff_Pregnant::DoBirthSpawn() - no father defined"); } // get a reference to the hediff we are applying Hediff_Pregnant self = (Hediff_Pregnant)mother.health.hediffSet.GetFirstHediffOfDef(HediffDef.Named("Pregnant")); // determine litter size int litter_size = (mother.RaceProps.litterSizeCurve == null) ? 1 : Mathf.RoundToInt(Rand.ByCurve(mother.RaceProps.litterSizeCurve, 300)); if (litter_size < 1) { litter_size = 1; } float skin_whiteness = Rand.Range(0, 1); string last_name = null; // send a message about giving birth ////--Log.Message("Hediff_Pregnancy::DoBirthSpawn( " + mother_name + ", " + father_name + ", " + chance_successful + " ) - generating baby pawns"); if (self.Visible && PawnUtility.ShouldSendNotificationAbout(mother)) { Messages.Message("GivingBirth".Translate(new object[] { mother.LabelIndefinite() }).CapitalizeFirst(), mother, MessageTypeDefOf.NeutralEvent); } ////--Log.Message("Hediff_Pregnancy::DoBirthSpawn( " + mother_name + ", " + father_name + ", " + chance_successful + " ) - creating spawn request"); List <Pawn> siblings = new List <Pawn>(); for (int i = 0; i < litter_size; i++) { Pawn spawn_parent = mother; if (father != null && Mod_Settings.pregnancy_use_parent_method && (100 * Rand.Value) > Mod_Settings.pregnancy_weight_parent) { spawn_parent = father; } PawnGenerationRequest request = new PawnGenerationRequest(spawn_parent.kindDef, spawn_parent.Faction, PawnGenerationContext.NonPlayer, spawn_parent.Map.Tile, false, true, false, false, false, false, 1, false, true, true, false, false, false, false, null, null, 0, 0, null, skin_whiteness, last_name); ////--Log.Message("Hediff_GenericPregnancy::DoBirthSpawn( " + mother_name + ", " + father_name + ", " + chance_successful + " ) - spawning baby"); Pawn baby = PawnGenerator.GeneratePawn(request); if (PawnUtility.TrySpawnHatchedOrBornPawn(baby, mother)) { if (baby.playerSettings != null && mother.playerSettings != null) { baby.playerSettings.AreaRestriction = mother.playerSettings.AreaRestriction; } if (baby.RaceProps.IsFlesh) { baby.relations.AddDirectRelation(PawnRelationDefOf.Parent, mother); if (father != null) { baby.relations.AddDirectRelation(PawnRelationDefOf.Parent, father); } foreach (Pawn sibling in siblings) { baby.relations.AddDirectRelation(PawnRelationDefOf.Sibling, sibling); } siblings.Add(baby); //inject RJW_BabyState to the newborn if RimWorldChildren is not active if (!xxx.RimWorldChildrenIsActive && baby.kindDef.race == ThingDefOf.Human && baby.ageTracker.CurLifeStageIndex <= 1 && baby.ageTracker.AgeBiologicalYears < 1 && !baby.Dead) { // Clean out drug randomly generated drug addictions baby.health.hediffSet.Clear(); baby.health.AddHediff(HediffDef.Named("RJW_BabyState"), null, null); Hediff_SimpleBaby babystate = (Hediff_SimpleBaby)baby.health.hediffSet.GetFirstHediffOfDef(HediffDef.Named("RJW_BabyState")); if (babystate != null) { babystate.GrowUpTo(0, true); } } } } else { Find.WorldPawns.PassToWorld(baby, PawnDiscardDecideMode.Discard); } } ////--Log.Message("Hediff_Pregnancy::DoBirthSpawn( " + mother_name + ", " + father_name + ", " + chance_successful + " ) - removing pregnancy"); mother.health.RemoveHediff(self); return(false); }
//reworked to use my own code instead of generator code nicked from vanilla Rimworld public static bool TryGenerateSidearmFor(Pawn pawn, float chance, float budgetMultiplier, PawnGenerationRequest request) { if ( pawn is null || SimpleSidearms.saveData is null || //not yet in game chance < 0.01f || pawn.kindDef.weaponTags == null || pawn.kindDef.weaponTags.Count == 0 || !pawn.RaceProps.ToolUser || !pawn.RaceProps.Humanlike || !pawn.health.capacities.CapableOf(PawnCapacityDefOf.Manipulation) || (pawn.story != null && pawn.story.DisabledWorkTagsBackstoryAndTraits.OverlapsWithOnAnyWorkType(WorkTags.Violent)) ) { return(false); }
/// <summary> /// Tries to revert the given pawn. /// </summary> /// <param name="transformedPawn">The transformed pawn.</param> /// <returns></returns> public override bool TryRevert(Pawn transformedPawn) { if (transformedPawn == null) { throw new ArgumentNullException(nameof(transformedPawn)); } var pawnStatus = GameComp.GetTransformedPawnContaining(transformedPawn); var sState = transformedPawn.GetSapienceState(); if (sState == null) { return(false); } if (pawnStatus != null) { if (pawnStatus.Value.status != TransformedStatus.Transformed) { return(false); } if (pawnStatus.Value.pawn is MergedPawns merged) { if (sState.StateDef != def.transformedSapienceState) { return(false); } if (TryRevertImpl(merged)) { GameComp.RemoveInstance(merged); return(true); } } return(false); } if (sState.StateDef == def.transformedSapienceState) { ThoughtDef thoughtDef = null; for (var i = 0; i < 2; i++) { PawnGenerationRequest request = TransformerUtility.GenerateRandomPawnFromAnimal(transformedPawn); Pawn pawnTf = PawnGenerator.GeneratePawn(request); pawnTf.needs.food.CurLevel = transformedPawn.needs.food.CurInstantLevel; pawnTf.needs.rest.CurLevel = transformedPawn.needs.rest.CurLevel; var spawnedPawn = (Pawn)GenSpawn.Spawn(pawnTf, transformedPawn.PositionHeld, transformedPawn.MapHeld); spawnedPawn.apparel.DestroyAll(); spawnedPawn.equipment.DestroyAllEquipment(); for (var j = 0; j < 10; j++) { IntermittentMagicSprayer.ThrowMagicPuffDown(spawnedPawn.Position.ToVector3(), spawnedPawn.MapHeld); IntermittentMagicSprayer.ThrowMagicPuffUp(spawnedPawn.Position.ToVector3(), spawnedPawn.MapHeld); } _scratchArray[i] = spawnedPawn; } PawnRelationDef relationDef; bool relationIsMergeMate = thoughtDef == def.revertedThoughtGood; relationDef = relationIsMergeMate ? TfRelationDefOf.MergeMate : TfRelationDefOf.ExMerged; _scratchArray[0].relations.AddDirectRelation(relationDef, _scratchArray[1]); CheckForBrainDamage(transformedPawn, _scratchArray[0], _scratchArray[1]); transformedPawn.Destroy(); return(true); } return(false); }
// Credit goes to Justin C for the Zombie Apocalypse code. // Taken from Verse.ZombieMod_Utility public static Pawn GenerateZombiePawnFromSource(Pawn sourcePawn) { PawnKindDef pawnKindDef = PawnKindDef.Named("ReanimatedCorpse"); Faction factionDirect = Find.FactionManager.FirstFactionOfDef(FactionDefOf.AncientsHostile); Pawn pawn = (Pawn)ThingMaker.MakeThing(pawnKindDef.race, null); pawn.kindDef = pawnKindDef; pawn.SetFactionDirect(factionDirect); pawn.pather = new Pawn_PathFollower(pawn); pawn.ageTracker = new Pawn_AgeTracker(pawn); pawn.health = new Pawn_HealthTracker(pawn); pawn.jobs = new Pawn_JobTracker(pawn); pawn.mindState = new Pawn_MindState(pawn); pawn.filth = new Pawn_FilthTracker(pawn); pawn.needs = new Pawn_NeedsTracker(pawn); pawn.stances = new Pawn_StanceTracker(pawn); pawn.natives = new Pawn_NativeVerbs(pawn); PawnComponentsUtility.CreateInitialComponents(pawn); if (pawn.RaceProps.ToolUser) { pawn.equipment = new Pawn_EquipmentTracker(pawn); pawn.carryTracker = new Pawn_CarryTracker(pawn); pawn.apparel = new Pawn_ApparelTracker(pawn); pawn.inventory = new Pawn_InventoryTracker(pawn); } if (pawn.RaceProps.Humanlike) { pawn.ownership = new Pawn_Ownership(pawn); pawn.skills = new Pawn_SkillTracker(pawn); pawn.relations = new Pawn_RelationsTracker(pawn); pawn.story = new Pawn_StoryTracker(pawn); pawn.workSettings = new Pawn_WorkSettings(pawn); } if (pawn.RaceProps.intelligence <= Intelligence.ToolUser) { pawn.caller = new Pawn_CallTracker(pawn); } //pawn.gender = Gender.None; pawn.gender = sourcePawn.gender; Cthulhu.Utility.GenerateRandomAge(pawn, pawn.Map); pawn.needs.SetInitialLevels(); if (pawn.RaceProps.Humanlike) { string headGraphicPath = sourcePawn.story.HeadGraphicPath; typeof(Pawn_StoryTracker).GetField("headGraphicPath", BindingFlags.Instance | BindingFlags.NonPublic).SetValue(pawn.story, headGraphicPath); pawn.story.melanin = sourcePawn.story.melanin; pawn.story.crownType = sourcePawn.story.crownType; pawn.story.hairColor = sourcePawn.story.hairColor; NameTriple name = sourcePawn.Name as NameTriple; pawn.Name = name; pawn.story.childhood = sourcePawn.story.childhood; pawn.story.adulthood = sourcePawn.story.adulthood; pawn.story.hairDef = sourcePawn.story.hairDef; foreach (Trait current in sourcePawn.story.traits.allTraits) { pawn.story.traits.GainTrait(current); } //pawn.story.GenerateSkillsFromBackstory(); } GenerateZombieApparelFromSource(pawn, sourcePawn); PawnGenerationRequest con = new PawnGenerationRequest(); PawnInventoryGenerator.GenerateInventoryFor(pawn, con); //Graphic nakedBodyGraphic = GraphicGetter_NakedHumanlike.GetNakedBodyGraphic(sourcePawn.story.bodyType, ShaderDatabase.CutoutSkin, new Color(0.37f, 0.48f, 0.35f, 1f)); Graphic nakedBodyGraphic = GraphicDatabase.Get <Graphic_Multi>(sourcePawn.story.bodyType.bodyNakedGraphicPath, ShaderDatabase.CutoutSkin, Vector2.one, new Color(0.37f, 0.48f, 0.35f, 1f)); Graphic headGraphic = GraphicDatabase.Get <Graphic_Multi>(sourcePawn.story.HeadGraphicPath, ShaderDatabase.CutoutSkin, Vector2.one, new Color(0.37f, 0.48f, 0.35f, 1f)); Graphic hairGraphic = GraphicDatabase.Get <Graphic_Multi>(sourcePawn.story.hairDef.texPath, ShaderDatabase.Cutout, Vector2.one, sourcePawn.story.hairColor); pawn.Drawer.renderer.graphics.headGraphic = headGraphic; pawn.Drawer.renderer.graphics.nakedGraphic = nakedBodyGraphic; pawn.Drawer.renderer.graphics.hairGraphic = hairGraphic; return(pawn); }
public virtual bool AllowWorldGeneratedPawn(Pawn pawn, bool tryingToRedress, PawnGenerationRequest req) { return(true); }
public static ReanimatedPawn DoGenerateZombiePawnFromSource(Pawn sourcePawn, bool isBerserk = true, bool oathOfHastur = false) { PawnKindDef pawnKindDef = PawnKindDef.Named("ReanimatedCorpse"); Faction factionDirect = isBerserk ? Find.FactionManager.FirstFactionOfDef(FactionDefOf.AncientsHostile) : Faction.OfPlayer; ReanimatedPawn pawn = (ReanimatedPawn)ThingMaker.MakeThing(pawnKindDef.race, null); try { pawn.kindDef = pawnKindDef; pawn.SetFactionDirect(factionDirect); PawnComponentsUtility.CreateInitialComponents(pawn); pawn.gender = sourcePawn.gender; pawn.ageTracker.AgeBiologicalTicks = sourcePawn.ageTracker.AgeBiologicalTicks; pawn.ageTracker.AgeChronologicalTicks = sourcePawn.ageTracker.AgeChronologicalTicks; pawn.workSettings = new Pawn_WorkSettings(pawn); if (pawn.workSettings != null && sourcePawn.Faction.IsPlayer) { pawn.workSettings.EnableAndInitialize(); } pawn.needs.SetInitialLevels(); //Add hediffs? //Add relationships? if (pawn.RaceProps.Humanlike) { pawn.story.melanin = sourcePawn.story.melanin; pawn.story.crownType = sourcePawn.story.crownType; pawn.story.hairColor = sourcePawn.story.hairColor; pawn.story.childhood = sourcePawn.story.childhood; pawn.story.adulthood = sourcePawn.story.adulthood; pawn.story.bodyType = sourcePawn.story.bodyType; pawn.story.hairDef = sourcePawn.story.hairDef; if (!oathOfHastur) { foreach (Trait current in sourcePawn.story.traits.allTraits) { pawn.story.traits.GainTrait(current); } } else { pawn.story.traits.GainTrait(new Trait(TraitDef.Named("Cults_OathtakerHastur2"), 0, true)); pawn.story.traits.GainTrait(new Trait(TraitDefOf.Psychopath, 0, true)); SkillFixer(pawn, sourcePawn); RelationshipFixer(pawn, sourcePawn); AddedPartFixer(pawn, sourcePawn); } //pawn.story.GenerateSkillsFromBackstory(); NameTriple nameTriple = sourcePawn.Name as NameTriple; if (!oathOfHastur) { pawn.Name = new NameTriple(nameTriple.First, string.Concat(new string[] { "* ", Translator.Translate("Reanimated"), " ", nameTriple.Nick, " *" }), nameTriple.Last); } else { pawn.Name = nameTriple; } } string headGraphicPath = sourcePawn.story.HeadGraphicPath; typeof(Pawn_StoryTracker).GetField("headGraphicPath", BindingFlags.Instance | BindingFlags.NonPublic).SetValue(pawn.story, headGraphicPath); GenerateZombieApparelFromSource(pawn, sourcePawn); PawnGenerationRequest con = new PawnGenerationRequest(); PawnInventoryGenerator.GenerateInventoryFor(pawn, con); GiveZombieSkinEffect(pawn, sourcePawn as ReanimatedPawn, oathOfHastur); if (isBerserk) { pawn.mindState.mentalStateHandler.TryStartMentalState(MentalStateDefOf.Berserk); } //Log.Message(pawn.Name.ToStringShort); return(pawn); } catch (Exception e) { Cthulhu.Utility.DebugReport(e.ToString()); } return(null); }
/*private static void AddJoyAndComfortNeed(Pawn pawn) { // TODO: does not work anymore... Log.Message("Try to add joy to " + pawn.Name.ToStringShort); if (pawn.needs.TryGetNeed(NeedDefOf.Joy) == null) { MethodInfo addNeed = typeof(Pawn_NeedsTracker).GetMethod("AddNeed", BindingFlags.Instance | BindingFlags.NonPublic); addNeed.Invoke(pawn.needs, new object[] { DefDatabase<NeedDef>.GetNamed("Joy", true) }); pawn.needs.joy.CurLevel = Rand.Range(0.5f, 1f); } if (pawn.needs.comfort == null) { MethodInfo addNeed = typeof(Pawn_NeedsTracker).GetMethod("AddNeed", BindingFlags.Instance | BindingFlags.NonPublic); addNeed.Invoke(pawn.needs, new object[] { DefDatabase<NeedDef>.GetNamed("Comfort", true) }); pawn.needs.comfort.CurLevel = Rand.Range(0.75f, 1f); } }*/ public static Pawn GeneratePawn(PawnKindDef kindDef) { Pawn pawn = null; // Generate a new pawn until it respects all criteria. PawnGenerationRequest request = new PawnGenerationRequest( kind: kindDef, faction: OG_Util.FactionOfMiningCo, forceGenerateNewPawn: true, mustBeCapableOfViolence: true, canGeneratePawnRelations: false); for (int tryIndex = 0; tryIndex <= 20; tryIndex++) { pawn = PawnGenerator.GeneratePawn(kindDef, OG_Util.FactionOfMiningCo); if (kindDef == OG_Util.OutpostTechnicianDef) { if (pawn.story.WorkTagIsDisabled(WorkTags.Hauling) || pawn.story.WorkTagIsDisabled(WorkTags.Cleaning) || pawn.story.WorkTagIsDisabled(WorkTags.ManualDumb) || pawn.story.WorkTagIsDisabled(WorkTags.PlantWork) || pawn.story.WorkTagIsDisabled(WorkTags.Firefighting) || pawn.story.WorkTagIsDisabled(WorkTags.Scary)) { pawn.Destroy(); pawn = null; if (tryIndex == 20) { Log.Message("MiningCo. OutpostGenerator: cannot generate requested technician pawn."); } } } else { if (pawn.story.WorkTagIsDisabled(WorkTags.Violent) || pawn.story.WorkTagIsDisabled(WorkTags.Firefighting)) { pawn.Destroy(); pawn = null; if (tryIndex == 20) { Log.Message("MiningCo. OutpostGenerator: cannot generate requested soldier pawn."); } } } if (pawn != null) { break; } }; // Generate apparel and weapon. GeneratePawnApparelAndWeapon(ref pawn, kindDef); // TODO: add joy and comfort needs. // Enable work settings. pawn.workSettings.EnableAndInitialize(); if (kindDef == OG_Util.OutpostTechnicianDef) { List<WorkTypeDef> allDefsListForReading = DefDatabase<WorkTypeDef>.AllDefsListForReading; for (int workTypeIndex = 0; workTypeIndex < allDefsListForReading.Count; workTypeIndex++) { // Ensure doctor, repair and growing are enabled. WorkTypeDef workTypeDef = allDefsListForReading[workTypeIndex]; if (workTypeDef.alwaysStartActive || (workTypeDef == WorkTypeDefOf.Doctor) || (workTypeDef == WorkTypeDefOf.Repair) || (workTypeDef == WorkTypeDefOf.Growing)) { if (pawn.story.WorkTypeIsDisabled(workTypeDef) == false) { pawn.workSettings.SetPriority(workTypeDef, 3); if (workTypeDef == WorkTypeDefOf.Repair) { pawn.workSettings.SetPriority(workTypeDef, 4); // So dead bodies are hauled away before repairing walls. } } } else { pawn.workSettings.Disable(workTypeDef); } } } // For soldiers, restrict allowed works to only firefighting and doctor (to rescue downed pawns). else { List<WorkTypeDef> allDefsListForReading = DefDatabase<WorkTypeDef>.AllDefsListForReading; for (int workTypeIndex = 0; workTypeIndex < allDefsListForReading.Count; workTypeIndex++) { WorkTypeDef workTypeDef = allDefsListForReading[workTypeIndex]; if ((workTypeDef == WorkTypeDefOf.Firefighter) || (workTypeDef == WorkTypeDefOf.Doctor)) { if (pawn.story.WorkTypeIsDisabled(workTypeDef) == false) { pawn.workSettings.SetPriority(workTypeDef, 3); } } else { pawn.workSettings.Disable(workTypeDef); } } } // Set allowed area. pawn.playerSettings = new Pawn_PlayerSettings(pawn); pawn.playerSettings.AreaRestriction = OG_Util.FindOutpostArea(); // Add a bonus mood boost. pawn.needs.mood.thoughts.memories.TryGainMemoryThought(OG_Util.MiningCoEmployeeThoughtDef); return pawn; }
// Token: 0x060029EE RID: 10734 RVA: 0x0013DA2C File Offset: 0x0013BE2C private void TrySpawnPawns() { if (this.pointsLeft <= 0f) { return; } if (!this.parent.Spawned) { return; } // Log.Message(string.Format("parent Spawned: {0}", this.parent.Spawned)); if (this.lord == null) { IntVec3 invalid; if (!CellFinder.TryFindRandomCellNear(this.parent.Position, this.parent.Map, 5, (IntVec3 c) => c.Standable(this.parent.Map) && this.parent.Map.reachability.CanReach(c, this.parent, PathEndMode.Touch, TraverseParms.For(TraverseMode.PassDoors, Danger.Deadly, false)), out invalid, -1)) { Log.Error("Found no place for Pawns to defend " + this, false); invalid = IntVec3.Invalid; } LordJob_PawnsDefendShip lordJob = new LordJob_PawnsDefendShip(this.parent, this.parent.Faction, 21f, invalid); this.lord = LordMaker.MakeNewLord(OfFaction, lordJob, this.parent.Map, null); } try { while (this.pointsLeft > 0f) { PawnGenOption kindOption; PawnKindDef kind; if (this.parent is Building_HiveLike_CrashedShipPart _HiveShip) { _HiveShip.spawnablePawnKinds.TryRandomElement(out kind); } else if (!(from opt in PawnKinds where opt.kind.combatPower <= this.pointsLeft select opt).TryRandomElementByWeight((PawnGenOption x) => x.selectionWeight, out kindOption)) { if (PawnKinds.NullOrEmpty()) { // Log.Message(string.Format("PawnKinds.NullOrEmpty")); } // Log.Message(string.Format("try spawn 2a")); break; } else { kind = kindOption.kind; } // Log.Message(string.Format("try spawn 3")); IntVec3 center; if (!(from cell in GenAdj.CellsAdjacent8Way(this.parent) where this.CanSpawnPawnAt(cell) select cell).TryRandomElement(out center)) { break; } // Log.Message(string.Format("try spawn 4")); PawnGenerationRequest request = new PawnGenerationRequest(kind, faction, PawnGenerationContext.NonPlayer, -1, true, false, false, false, true, false, 1f); // Log.Message(string.Format("try spawn 5")); Pawn pawn = PawnGenerator.GeneratePawn(request); // Log.Message(string.Format("try spawn 6")); if (!GenPlace.TryPlaceThing(pawn, center, this.parent.Map, ThingPlaceMode.Near, null, null)) { // Log.Message(string.Format("try spawn 6b")); Find.WorldPawns.PassToWorld(pawn, PawnDiscardDecideMode.Discard); break; } // Log.Message(string.Format("try spawn 7")); this.lord.AddPawn(pawn); // Log.Message(string.Format("pawn: {0} to Lord: {1}", pawn.LabelShortCap, this.lord)); this.pointsLeft -= pawn.kindDef.combatPower; } } finally { // Log.Message(string.Format("Finally {0} points left", this.pointsLeft)); this.pointsLeft = 0f; // Log.Message(string.Format("set points left to {0} ", this.pointsLeft)); } SoundDefOf.PsychicPulseGlobal.PlayOneShotOnCamera(this.parent.Map); }