public static ResearchProjectDef ApplyPointsToExpertise(float points, Pawn pawn)
        {
            ResearchManager    researchManager = Find.ResearchManager;
            ResearchProjectDef result;

            if (!researchManager.AnyProjectIsAvailable)
            {
                result = null;
            }
            else
            {
                IEnumerable <ResearchProjectDef> source = from x in DefDatabase <ResearchProjectDef> .AllDefsListForReading
                                                          where x.CanStartNow
                                                          select x;
                source.TryRandomElementByWeight((ResearchProjectDef x) => 1f / x.baseCost, out result);
                points *= 12f; //stangely, that number is 121f on the mod source. I'm assuming that's a typo.
                float         total    = result.baseCost;
                CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                if (techComp != null)
                {
                    Dictionary <ResearchProjectDef, float> expertise = techComp.expertise;
                    float num = result.GetProgress(expertise);
                    num += points / total;
                    expertise[result] = (num > 1) ? 1 : num;
                }
            }
            return(result);
        }
Example #2
0
        protected Toil FinalizeTraining()
        {
            Toil finalizeTraining = new Toil();

            finalizeTraining.initAction = delegate
            {
                Pawn actor = finalizeTraining.actor;
                if (!practice)
                {
                    ThingDef      weapon   = job.targetB.Thing.def;
                    CompKnowledge techComp = actor.TryGetComp <CompKnowledge>();
                    bool          safe     = true;
                    if (unknown)
                    {
                        safe = !CheckExperimentFail(actor, TargetThingB);
                    }
                    if (!techComp.proficientWeapons.Contains(weapon) && safe)
                    {
                        LearnWeaponGroup(weapon, actor, techComp);
                    }
                }
                job.bill.Notify_IterationCompleted(actor, new List <Thing> {
                });
                actor.jobs.EndCurrentJob(JobCondition.Succeeded, false);
            };
            finalizeTraining.defaultCompleteMode = ToilCompleteMode.Instant;
            finalizeTraining.FailOnDespawnedOrNull(TargetIndex.A);
            return(finalizeTraining);
        }
        public static void CarefullyFinishProject(this ResearchProjectDef project, Thing place)
        {
            bool careful = !project.prerequisites.NullOrEmpty();
            List <ResearchProjectDef> prerequisitesCopy = new List <ResearchProjectDef>();

            if (careful)
            {
                prerequisitesCopy.AddRange(project.prerequisites);
                project.prerequisites.Clear();
            }
            Find.ResearchManager.FinishProject(project);
            if (careful)
            {
                project.prerequisites.AddRange(prerequisitesCopy);
            }
            Messages.Message("MessageFiledTech".Translate(project.label), place, MessageTypeDefOf.TaskCompletion, true);
            using (IEnumerator <Pawn> enumerator = currentPawns.GetEnumerator())
            {
                while (enumerator.MoveNext())
                {
                    CompKnowledge techComp = enumerator.Current.TryGetComp <CompKnowledge>();
                    techComp.homework?.RemoveAll(x => x == project);
                }
            }
            currentPawnsCache.Clear();
        }
Example #4
0
        public static void Learned(this ResearchProjectDef tech, float amount, float recipeCost, Pawn researcher, bool research = false)
        {
            float total = research ? tech.baseCost : recipeCost *tech.StuffCostFactor();

            amount *= research ? ResearchPointsPerWorkTick : StudyPointsPerWorkTick;
            amount *= researcher.GetStatValue(StatDefOf.GlobalLearningFactor, true); //Because, why not?
            CompKnowledge techComp = researcher.TryGetComp <CompKnowledge>();
            Dictionary <ResearchProjectDef, float> expertise = techComp.expertise;

            foreach (ResearchProjectDef sucessor in expertise.Keys.Where(x => x.IsKnownBy(researcher)))
            {
                if (!sucessor.prerequisites.NullOrEmpty() && sucessor.prerequisites.Contains(tech))
                {
                    amount *= 2;
                    break;
                }
            }
            if (researcher != null && researcher.Faction != null)
            {
                amount /= tech.CostFactor(techComp.techLevel);
            }
            if (DebugSettings.fastResearch)
            {
                amount *= 500f;
            }
            if (researcher != null && research)
            {
                researcher.records.AddTo(RecordDefOf.ResearchPointsResearched, amount);
            }
            float num = tech.GetProgress(expertise);

            num            += amount / total;
            expertise[tech] = num;
        }
        public override bool ShouldSkip(Pawn pawn, bool forced = false)
        {
            CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();

            if (techComp != null)
            {
                return(techComp.expertise == null || techComp.homework.NullOrEmpty());
            }
            return(true);
        }
Example #6
0
        protected bool CheckExperimentFail(Pawn tester, Thing weapon)
        {
            float         num      = 1f;
            float         delta    = 1f;
            CompKnowledge techComp = tester.TryGetComp <CompKnowledge>();

            if (techComp != null)
            {
                delta = (int)techComp.techLevel / (int)weapon.def.techLevel;
            }
            float factor = WeaponExperimentChanceFactor.Evaluate(delta);

            num *= factor;
            num  = Mathf.Min(num, 0.98f);
            if (Prefs.LogVerbose)
            {
                Log.Message($"[HumanResources] Experiment weapon calculation for {tester} vs. {weapon.def}: techLevel diff is {delta} -> chance factor is {num}");
            }
            Job       job    = this.job;
            RecipeDef recipe = job.bill.recipe;

            if (!Rand.Chance(num))     //Determined by the tech level difference according to curve.
            {
                if (Rand.Chance(0.5f)) //50% chance the failure is harmless;
                {
                    techComp?.AddWeaponTrauma(weapon.def);
                    if (Rand.Chance(0.5f))     //25% chance the weapon just takes some damage;
                    {
                        if (Rand.Chance(0.2f)) //5% chance the weapon is destroyed;
                        {
                            Find.LetterStack.ReceiveLetter("LetterLabelWeaponTestFailed".Translate(weapon.def.Named("WEAPON")), "MessageMedicalWeaponTestFailureRidiculous".Translate(tester.LabelShort, tester.LabelShort, weapon.def.Named("WEAPON"), tester.Named("TESTER"), recipe.Named("RECIPE")), LetterDefOf.NegativeEvent, tester, null, null, null, null);
                            Backfire(tester, weapon);
                            weapon.Destroy();
                        }
                        else //20% chance the weapon backfires.
                        {
                            Find.LetterStack.ReceiveLetter("LetterLabelWeaponTestFailed".Translate(weapon.def.Named("WEAPON")), "MessageWeaponTestFailureCatastrophic".Translate(tester.LabelShort, tester.LabelShort, weapon.def.Named("WEAPON"), tester.Named("TESTER"), recipe.Named("RECIPE")), LetterDefOf.NegativeEvent, tester, null, null, null, null);
                            Backfire(tester, weapon);
                        }
                    }
                    else
                    {
                        Find.LetterStack.ReceiveLetter("LetterLabelWeaponTestFailed".Translate(weapon.def.Named("WEAPON")), "MessageWeaponTestFailureMinor".Translate(tester.LabelShort, tester.LabelShort, weapon.def.Named("WEAPON"), tester.Named("TESTER"), recipe.Named("RECIPE")), LetterDefOf.NegativeEvent, tester, null, null, null, null);
                        float damageFactor = 4 - delta;
                        Scratch(weapon, damageFactor);
                    }
                }
                else
                {
                    Messages.Message("WeaponTestFail".Translate(tester, weapon.def), MessageTypeDefOf.NegativeEvent);
                }
                return(true);
            }
            return(false);
        }
Example #7
0
        private static IEnumerable <Widgets.DropdownMenuElement <Pawn> > GeneratePawnRestrictionOptions(this ResearchProjectDef tech, bool completed)
        {
            SkillDef skill = SkillDefOf.Intellectual;

            using (IEnumerator <Pawn> enumerator = tech.SortedPawns().GetEnumerator())
            {
                while (enumerator.MoveNext())
                {
                    Pawn          pawn      = enumerator.Current;
                    CompKnowledge techComp  = pawn.TryGetComp <CompKnowledge>();
                    bool          known     = tech.IsKnownBy(pawn);
                    WorkTypeDef   workGiver = (completed || known) ? TechDefOf.HR_Learn : WorkTypeDefOf.Research;
                    string        header    = known ? TechStrings.headerWrite : completed ? TechStrings.headerRead : TechStrings.headerResearch;
                    if (techComp != null && (techComp.homework.NullOrEmpty() || !techComp.homework.Contains(tech)))
                    {
                        if (pawn.WorkTypeIsDisabled(workGiver))
                        {
                            yield return(new Widgets.DropdownMenuElement <Pawn>
                            {
                                option = new FloatMenuOption(string.Format("{0}: {1} ({2})", header, pawn.LabelShortCap, "WillNever".Translate(workGiver.verb)), null, MenuOptionPriority.DisabledOption, null, null, 0f, null, null),
                                payload = pawn
                            });
                        }
                        else if (!pawn.workSettings.WorkIsActive(workGiver))
                        {
                            yield return(new Widgets.DropdownMenuElement <Pawn>
                            {
                                option = new FloatMenuOption(string.Format("{0}: {1} ({2})", header, pawn.LabelShortCap, "NotAssigned".Translate()), delegate()
                                {
                                    techComp.AssignBranch(tech);
                                }, MenuOptionPriority.VeryLow, null, null, 0f, null, null),
                                payload = pawn
                            });
                        }
                        else
                        {
                            yield return(new Widgets.DropdownMenuElement <Pawn>
                            {
                                option = new FloatMenuOption(string.Format("{0}: {1} ({2} {3})", new object[]
                                {
                                    header,
                                    pawn.LabelShortCap,
                                    pawn.skills.GetSkill(skill).Level,
                                    skill.label
                                }),
                                                             delegate() { techComp.AssignBranch(tech); },
                                                             MenuOptionPriority.Default, null, null, 0f, null, null),
                                payload = pawn
                            });
                        }
                    }
                }
            }
            yield break;
        }
Example #8
0
        public static bool IsKnownBy(this ResearchProjectDef tech, Pawn pawn)
        {
            CompKnowledge techComp  = pawn.TryGetComp <CompKnowledge>();
            var           expertise = techComp.expertise;

            if (expertise != null)
            {
                return(expertise.ContainsKey(tech) && techComp.expertise[tech] >= 1f);
            }
            return(false);
        }
        public override bool ShouldSkip(Pawn pawn, bool forced = false)
        {
            CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();

            if (techComp != null && !techComp.homework.NullOrEmpty())
            {
                bool result = !techComp.homework.Any(x => !x.IsFinished && !x.IsKnownBy(pawn));
                return(result);
            }
            return(true);
        }
Example #10
0
 public static void WipeAssignments(this ResearchProjectDef project)
 {
     using (IEnumerator <Pawn> enumerator = currentPawns.GetEnumerator())
     {
         while (enumerator.MoveNext())
         {
             CompKnowledge techComp = enumerator.Current.TryGetComp <CompKnowledge>();
             techComp.homework?.RemoveAll(x => x == project);
         }
     }
     currentPawnsCache.Clear();
 }
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            Building_ResearchBench Desk = t as Building_ResearchBench;

            if (Desk != null && pawn.CanReserve(t, 1, -1, null, forced))
            {
                CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                bool          result   = techComp.homework.Any(x => !x.IsFinished && x.CanBeResearchedAt(Desk, false) && !x.IsKnownBy(pawn) && x.RequisitesKnownBy(pawn));
                return(result);
            }
            return(false);
        }
Example #12
0
        protected override IEnumerable <ThingDef> StudyWeapons(Bill bill, Pawn pawn)
        {
            CompKnowledge          techComp    = pawn.TryGetComp <CompKnowledge>();
            IEnumerable <ThingDef> known       = techComp.knownWeapons;
            IEnumerable <ThingDef> craftable   = techComp.craftableWeapons;
            IEnumerable <ThingDef> available   = unlocked.weapons.Concat(craftable);
            IEnumerable <ThingDef> chosen      = bill.ingredientFilter.AllowedThingDefs;
            IEnumerable <ThingDef> feared      = techComp.fearedWeapons;
            IEnumerable <ThingDef> unavailable = chosen.Except(known).Where(x => !available.Contains(x));
            var result = feared.EnumerableNullOrEmpty() ? chosen.Intersect(unavailable) : chosen.Intersect(unavailable).Except(feared);

            return(result);
        }
        public override Job JobOnThing(Pawn pawn, Thing thing, bool forced = false)
        {
            int tick = Find.TickManager.TicksGame;

            if (actualJob == null || lastVerifiedJobTick != tick || Find.TickManager.Paused)
            {
                actualJob = null;
                IBillGiver billGiver = thing as IBillGiver;
                if (billGiver != null && ThingIsUsableBillGiver(thing) && billGiver.BillStack.AnyShouldDoNow && billGiver.UsableForBillsAfterFueling())
                {
                    if (CheckLibrarySpace(thing)) //check library space
                    {
                        LocalTargetInfo target = thing;
                        if (pawn.CanReserve(target, 1, -1, null, forced) && !thing.IsBurning() && !thing.IsForbidden(pawn)) //basic desk availabilty
                        {
                            CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                            IEnumerable <ResearchProjectDef> homework = techComp.homework;
                            var intersection = techComp.knownTechs.Where(x => !x.IsFinished).Intersect(homework);
                            if (intersection.Any()) //check homework
                            {
                                billGiver.BillStack.RemoveIncompletableBills();
                                foreach (Bill bill in RelevantBills(thing, pawn))
                                {
                                    if (bill.Allows(intersection)) //check bill filter vs. homework
                                    {
                                        actualJob           = StartOrResumeBillJob(pawn, billGiver, target);
                                        lastVerifiedJobTick = tick;
                                        break;
                                    }
                                    else if (!JobFailReason.HaveReason)
                                    {
                                        JobFailReason.Is("ForbiddenAssignment".Translate());
                                    }
                                }
                            }
                            else if (!JobFailReason.HaveReason)
                            {
                                JobFailReason.Is("NoAssignment".Translate(pawn));
                            }
                        }
                    }
                    else if (!JobFailReason.HaveReason)
                    {
                        JobFailReason.Is("NoSpaceInLibrary".Translate());
                    }
                }
            }
            return(actualJob);
        }
        public override bool CanBeUsedBy(Pawn p, out string failReason)
        {
            failReason = null;
            CompKnowledge techComp = p.TryGetComp <CompKnowledge>();

            if (techComp != null)
            {
                if (!techComp.homework.NullOrEmpty())
                {
                    return(techComp.homework.Any(x => !x.IsFinished));
                }
            }
            failReason = "NoActiveResearchProjectToFinish".Translate();
            return(false);
        }
        protected virtual IEnumerable <ThingDef> StudyWeapons(Bill bill, Pawn pawn)
        {
            CompKnowledge          techComp    = pawn.TryGetComp <CompKnowledge>();
            IEnumerable <ThingDef> known       = techComp.knownWeapons;
            IEnumerable <ThingDef> craftable   = techComp.craftableWeapons;
            IEnumerable <ThingDef> allowed     = unlocked.weapons.Concat(craftable);
            IEnumerable <ThingDef> chosen      = bill.ingredientFilter.AllowedThingDefs;
            IEnumerable <ThingDef> viable      = chosen.Intersect(allowed).Except(known);
            IEnumerable <ThingDef> unavailable = chosen.Except(viable);

            if (viable.EnumerableNullOrEmpty() && !unavailable.EnumerableNullOrEmpty())
            {
                string thoseWeapons = "ThoseWeapons".Translate();
                string listing      = (unavailable.EnumerableCount() < 10) ? unavailable.Select(x => x.label).ToStringSafeEnumerable() : thoseWeapons;
                JobFailReason.Is("MissingRequirementToLearnWeapon".Translate(pawn, listing));
            }
            return(viable);
        }
Example #16
0
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            //Log.Message(pawn + " is looking for a document job...");
            Building_WorkTable Desk = t as Building_WorkTable;

            if (Desk != null)
            {
                var relevantBills = RelevantBills(Desk, pawn);
                if (!CheckJobOnThing(pawn, t, forced) | relevantBills.EnumerableNullOrEmpty())
                {
                    return(false);
                }
                CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                return(techComp.knownTechs.Where(x => !x.IsFinished).Intersect(techComp.homework).Any());
            }
            //Log.Message("case 4");
            return(false);
        }
        protected virtual IEnumerable <ThingDef> StudyWeapons(Bill bill, Pawn pawn)
        {
            CompKnowledge          techComp    = pawn.TryGetComp <CompKnowledge>();
            IEnumerable <ThingDef> known       = techComp.knownWeapons;
            IEnumerable <ThingDef> craftable   = techComp.knownTechs.SelectMany(x => x.UnlockedWeapons());
            IEnumerable <ThingDef> available   = ModBaseHumanResources.unlocked.weapons.Concat(craftable);
            IEnumerable <ThingDef> chosen      = bill.ingredientFilter.AllowedThingDefs;
            IEnumerable <ThingDef> unavailable = chosen.Except(known).Where(x => !available.Contains(x));

            if (!unavailable.EnumerableNullOrEmpty())
            {
                string thoseWeapons = "ThoseWeapons".Translate();
                string listing      = (unavailable.EnumerableCount() < 10) ? unavailable.Select(x => x.label).ToStringSafeEnumerable() : thoseWeapons;
                JobFailReason.Is("MissingRequirementToLearnWeapon".Translate(pawn, listing));
            }
            var result = chosen.Intersect(available).Except(known);

            return(result);
        }
        public override void DoEffect(Pawn usedBy)
        {
            base.DoEffect(usedBy);
            CompKnowledge             techComp   = usedBy.TryGetComp <CompKnowledge>();
            var                       candidates = techComp.homework.Where(x => !x.IsFinished && (x.requiredResearchBuilding == null || (bool)ResearchableInfo.GetValue(x)));
            List <ResearchProjectDef> means      = new List <ResearchProjectDef>();

            foreach (ResearchProjectDef tech in candidates)
            {
                if (tech.prerequisites != null)
                {
                    means.AddRange(candidates.Where(x => tech.prerequisites.Contains(x)));
                }
            }
            ResearchProjectDef result = candidates.Except(means).RandomElement();

            if (techComp.LearnTech(result) && result.prerequisites != null)
            {
                techComp.homework.RemoveAll(x => result.prerequisites.Contains(x));
            }
        }
Example #19
0
        public static bool RequisitesKnownBy(this ResearchProjectDef tech, Pawn pawn)
        {
            CompKnowledge techComp  = pawn.TryGetComp <CompKnowledge>();
            var           expertise = techComp.expertise;

            if (expertise != null)
            {
                //1. test if any descendent is known
                if (expertise.Where(x => x.Value >= 1 && !x.Key.prerequisites.NullOrEmpty() && x.Key.prerequisites.Contains(tech)).Any())
                {
                    return(true);
                }
                //2. test if all ancestors are known
                if (!tech.prerequisites.NullOrEmpty())
                {
                    return(tech.prerequisites.All(x => x.IsKnownBy(pawn)));
                }
            }
            //3. test if there are any ancestors
            return(tech.prerequisites.NullOrEmpty());
        }
Example #20
0
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            //Log.Message(pawn + " is looking for a research job...");
            Building_WorkTable Desk = t as Building_WorkTable;

            if (Desk != null)
            {
                var relevantBills = RelevantBills(Desk, pawn);
                if (!CheckJobOnThing(pawn, t, forced) | relevantBills.EnumerableNullOrEmpty())
                {
                    //Log.Message("...no job on desk.");
                    return(false);
                }
                List <ResearchProjectDef> studyMaterial = new List <ResearchProjectDef>();
                //Log.Message("...relevant bills: " + RelevantBills(Desk, pawn).Count);
                foreach (Bill bill in relevantBills)
                {
                    //Log.Message("...checking recipe: " + bill.recipe+", on bill "+bill.GetType());
                    //Log.Message("...selected techs count: " + bill.SelectedTech().ToList().Count());
                    studyMaterial.AddRange(bill.SelectedTech().Where(x => !x.IsFinished && x.TechprintRequirementMet && (x.requiredResearchBuilding == null || (bool)AccessTools.Property(typeof(ResearchProjectDef), "PlayerHasAnyAppropriateResearchBench").GetValue(x))));
                }
                availableTechs = studyMaterial;
                //Log.Message("...studyMaterial count is " + studyMaterial.Count());
                CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                techComp.AssignHomework(studyMaterial);
                //Log.Message("...homework count is " + techComp.HomeWork.Count());
                //if (techComp.HomeWork.Count() > 0) return true;
                if (studyMaterial.Intersect(techComp.HomeWork).Any())
                {
                    return(true);
                }
                if (!JobFailReason.HaveReason)
                {
                    JobFailReason.Is("AlreadyKnowsThoseProjects".Translate(pawn), null);
                }
                return(false);
            }
            //Log.Message("case 4");
            return(false);
        }
        protected void LearnWeaponGroup(ThingDef weapon, Pawn pawn, CompKnowledge techComp)
        {
            bool groupRanged = ModBaseHumanResources.LearnRangedWeaponsByGroup && weapon.IsRangedWeapon;
            bool groupMelee  = ModBaseHumanResources.LearnMeleeWeaponsByGroup && weapon.IsMeleeWeapon;

            if (TechTracker.FindTechs(weapon).Any() && (groupRanged || groupMelee))
            {
                foreach (ThingDef sister in TechTracker.FindTech(weapon).Weapons)
                {
                    if ((groupRanged && sister.IsRangedWeapon) || (groupMelee && sister.IsMeleeWeapon))
                    {
                        techComp.LearnWeapon(sister);
                        Messages.Message("MessageTrainingComplete".Translate(pawn, sister), MessageTypeDefOf.TaskCompletion);
                    }
                }
            }
            else
            {
                techComp.LearnWeapon(weapon);
                Messages.Message("MessageTrainingComplete".Translate(pawn, weapon), MessageTypeDefOf.TaskCompletion);
            }
        }
Example #22
0
        protected void LearnWeaponGroup(ThingDef weapon, Pawn pawn, CompKnowledge techComp)
        {
            bool groupRanged = ModBaseHumanResources.LearnRangedWeaponsByGroup && weapon.IsRangedWeapon;
            bool groupMelee  = ModBaseHumanResources.LearnMeleeWeaponsByGroup && weapon.IsMeleeWeapon;

            if (Extension_Research.TechByWeapon.ContainsKey(weapon) && (groupRanged || groupMelee))
            {
                foreach (ThingDef sister in Extension_Research.WeaponsByTech[Extension_Research.TechByWeapon[weapon]])
                {
                    if ((groupRanged && sister.IsRangedWeapon) || (groupMelee && sister.IsMeleeWeapon))
                    {
                        techComp.LearnWeapon(sister);
                        Messages.Message("MessageTrainingComplete".Translate(pawn, sister), MessageTypeDefOf.TaskCompletion);
                    }
                }
            }
            else
            {
                techComp.LearnWeapon(weapon);
                Messages.Message("MessageTrainingComplete".Translate(pawn, weapon), MessageTypeDefOf.TaskCompletion);
            }
        }
Example #23
0
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            //Log.Message(pawn + " is looking for a study job...");
            Building_WorkTable Desk = t as Building_WorkTable;

            if (Desk != null)
            {
                var relevantBills = RelevantBills(Desk, pawn);
                if (!CheckJobOnThing(pawn, t, forced) | relevantBills.EnumerableNullOrEmpty())
                {
                    //Log.Message("...no job on desk.");
                    return(false);
                }
                List <ResearchProjectDef> studyMaterial = new List <ResearchProjectDef>();
                foreach (Bill bill in relevantBills)
                {
                    //Log.Message("...checking recipe: " + bill.recipe + ", on bill " + bill.GetType());
                    //Log.Message("...selected techs count: " + bill.SelectedTech().ToList().Count());
                    studyMaterial.AddRange(bill.SelectedTech().Where(x => x.IsFinished));
                }
                availableTechs = studyMaterial;
                //Log.Message("...studyMaterial count is " + studyMaterial.Count());
                CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                techComp.AssignHomework(studyMaterial);
                //Log.Message("...homework count is " + techComp.HomeWork.Count());
                if (techComp.HomeWork.Count() > 0)
                {
                    return(true);
                }
                if (studyMaterial.Intersect(techComp.HomeWork).Any())
                {
                    return(true);
                }
                return(false);
            }
            Log.Message("case 4");
            return(false);
        }
Example #24
0
        public override bool HasJobOnThing(Pawn pawn, Thing t, bool forced = false)
        {
            //Log.Message(pawn + " is looking for a document job...");
            Building_WorkTable Desk = t as Building_WorkTable;

            if (Desk != null && ModBaseHumanResources.unlocked.libraryFreeSpace > 0)
            {
                var relevantBills = RelevantBills(Desk, pawn);
                if (!CheckJobOnThing(pawn, t, forced) | relevantBills.EnumerableNullOrEmpty())
                {
                    //Log.Message("... no job on thing");
                    return(false);
                }
                CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                return(techComp.knownTechs.Where(x => !x.IsFinished).Intersect(techComp.homework).Any());
            }
            //Log.Message("... no free space");
            if (ModBaseHumanResources.unlocked.libraryFreeSpace <= 0)
            {
                JobFailReason.Is("NoSpaceInLibrary".Translate());
            }
            return(false);
        }
Example #25
0
        private static void ReflectKnowledge(object instance, CompKnowledge techComp, out IEnumerable <object> expertiseDisplay)
        {
            Find.WindowStack.FloatMenu?.Close(false);
            bool valid = !techComp.expertise.EnumerableNullOrEmpty();

            expertiseDisplay = new object[] { };
            if (AltRPal)
            {
                ToggleSearch(true);
                if (valid)
                {
                    expertiseDisplay = from e in ResearchNodesCache
                                       where techComp.expertise.Keys.Contains(e.Key)
                                       select e.Value;
                }
            }
            else if (valid)
            {
                foreach (ResearchProjectDef tech in techComp.expertise.Keys)
                {
                    HighlightedProxy(ResearchNodesCache[tech], true);
                }
            }
        }
Example #26
0
        public static bool DrawQueue_Prefix(object __instance, Rect canvas)
        {
            if (AltRPal)
            {
                canvas.xMax += 130f + 2 * Margin; //keep an eye on his MainTabWindow_ResearchTree.DrawTopBar method for changes to this number
                canvas       = canvas.ExpandedBy(Margin);
            }
            float   padding   = 12f;
            float   spacing   = Find.ColonistBar.SpaceBetweenColonistsHorizontal;
            float   height    = canvas.height;
            float   startPos  = canvas.xMax - height - padding;
            Vector2 size      = new Vector2(height + spacing, height - padding);
            Vector2 innerSize = new Vector2(height - padding, height - padding);
            IEnumerable <object> expertiseDisplay = new object[] { };
            bool displayActive = false;

            using (IEnumerator <Pawn> enumerator = Find.ColonistBar.GetColonistsInOrder().Where(x => x.TechBound()).AsEnumerable().Reverse().GetEnumerator())
            {
                while (enumerator.MoveNext())
                {
                    Vector2 position = new Vector2(startPos, canvas.y);
                    Rect    box      = new Rect(position, size);
                    Rect    innerBox = new Rect(position.x + spacing, position.y, size.x - spacing - 2 * padding, size.y);
                    Pawn    pawn     = enumerator.Current;
                    GUI.DrawTexture(box, PortraitsCache.Get(pawn, size, Rot4.South, cameraZoom: 1.4f));
                    CompKnowledge techComp = pawn.TryGetComp <CompKnowledge>();
                    if (Mouse.IsOver(innerBox))
                    {
                        DeInterest();
                        ReflectKnowledge(__instance, techComp, out expertiseDisplay);
                        displayActive = true;
                    }
                    if (!techComp.homework.NullOrEmpty())
                    {
                        StringBuilder homeworkSummary = new StringBuilder();
                        homeworkSummary.AppendLine("AssignedTo".Translate(pawn));
                        foreach (var tech in techComp.homework)
                        {
                            homeworkSummary.AppendLine("- " + TechStrings.GetTask(pawn, tech) + " " + tech.label);
                        }
                        TooltipHandler.TipRegionByKey(box, homeworkSummary.ToString());
                    }
                    Vector2 pos = new Vector2(box.center.x, box.yMax);
                    GenMapUI.DrawPawnLabel(pawn, pos, 1f, box.width, null, GameFont.Tiny, false, true);
                    startPos -= height;
                }
            }
            if (AltRPal)
            {
                if (displayActive)
                {
                    UpdateMatches(expertiseDisplay);
                    expertiseDisplayed = true;
                }
                else if (expertiseDisplayed)
                {
                    ToggleSearch(false);
                    expertiseDisplayed = false;
                }
            }
            return(false);
        }
Example #27
0
        protected override IEnumerable <Toil> MakeNewToils()
        {
            Bill bill = job.bill;

            AddEndCondition(delegate
            {
                Thing thing = GetActor().jobs.curJob.GetTarget(TargetIndex.A).Thing;
                if (thing is Building && !thing.Spawned)
                {
                    return(JobCondition.Incompletable);
                }
                return(JobCondition.Ongoing);
            });
            this.FailOnBurningImmobile(TargetIndex.A);
            this.FailOn(delegate()
            {
                IBillGiver billGiver = job.GetTarget(TargetIndex.A).Thing as IBillGiver;
                if (billGiver != null)
                {
                    if (job.bill.DeletedOrDereferenced)
                    {
                        return(true);
                    }
                    if (!billGiver.CurrentlyUsableForBills())
                    {
                        return(true);
                    }
                }
                return(false);
            });
            AddFinishAction(delegate()
            {
                //Log.Message("LearnWeapon: finishing");
                ThingWithComps thingWithComps = (ThingWithComps)job.targetB.Thing;
                if (pawn.equipment.Primary != null)
                {
                    pawn.equipment.TryDropEquipment(thingWithComps, out thingWithComps, pawn.Position, false);
                }
            });
            Toil gotoBillGiver = Toils_Goto.GotoThing(TargetIndex.A, PathEndMode.InteractionCell);

            yield return(Toils_Jump.JumpIf(gotoBillGiver, () => job.GetTargetQueue(TargetIndex.B).NullOrEmpty <LocalTargetInfo>()));

            Toil extract = Toils_JobTransforms.ExtractNextTargetFromQueue(TargetIndex.B, true);

            yield return(extract);

            Toil getToHaulTarget = Toils_Goto.GotoThing(TargetIndex.B, PathEndMode.ClosestTouch).FailOnDespawnedNullOrForbidden(TargetIndex.B).FailOnSomeonePhysicallyInteracting(TargetIndex.B);

            yield return(getToHaulTarget);

            //temporary equip
            yield return(new Toil
            {
                initAction = delegate()
                {
                    ThingWithComps thingWithComps = (ThingWithComps)job.targetB.Thing;
                    ThingWithComps thingWithComps2;
                    if (thingWithComps.def.stackLimit > 1 && thingWithComps.stackCount > 1)
                    {
                        thingWithComps2 = (ThingWithComps)thingWithComps.SplitOff(1);
                    }
                    else
                    {
                        thingWithComps2 = thingWithComps;
                        thingWithComps2.DeSpawn(DestroyMode.Vanish);
                    }
                    pawn.equipment.MakeRoomFor(thingWithComps2);
                    pawn.equipment.AddEquipment(thingWithComps2);
                    if (thingWithComps.def.soundInteract != null)
                    {
                        thingWithComps.def.soundInteract.PlayOneShot(new TargetInfo(pawn.Position, pawn.Map, false));
                    }
                },
                defaultCompleteMode = ToilCompleteMode.Instant
            });

            yield return(Toils_Jump.JumpIfHaveTargetInQueue(TargetIndex.B, extract));

            yield return(gotoBillGiver);

            yield return(Toils_Combat.TrySetJobToUseAttackVerb(TargetIndex.A));

            Toil train = new Toil();

            train.initAction = delegate()
            {
                Pawn     actor  = train.actor;
                Job      curJob = actor.jobs.curJob;
                ThingDef weapon = job.targetB.Thing.def;
                workLeft                  = curJob.bill.recipe.WorkAmountTotal(null);
                billStartTick             = Find.TickManager.TicksGame;
                ticksSpentDoingRecipeWork = 0;
                curJob.bill.Notify_DoBillStarted(actor);
                //sound:
                if (weapon.soundInteract != null)
                {
                    weapon.soundInteract.PlayOneShot(new TargetInfo(pawn.Position, pawn.Map, false));
                }
            };
            train.tickAction = delegate()
            {
                Pawn     actor  = train.actor;
                Job      curJob = actor.jobs.curJob;
                ThingDef weapon = job.targetB.Thing.def;
                ticksSpentDoingRecipeWork++;
                curJob.bill.Notify_PawnDidWork(actor);
                IBillGiverWithTickAction billGiverWithTickAction = train.actor.CurJob.GetTarget(TargetIndex.A).Thing as IBillGiverWithTickAction;
                if (billGiverWithTickAction != null)
                {
                    billGiverWithTickAction.UsedThisTick();
                }
                float num = (curJob.RecipeDef.workSpeedStat != null) ? actor.GetStatValue(curJob.RecipeDef.workSpeedStat, true) : 1f;
                if (curJob.RecipeDef.workTableSpeedStat != null)
                {
                    Building_WorkTable building_WorkTable = BillGiver as Building_WorkTable;
                    if (building_WorkTable != null)
                    {
                        num *= building_WorkTable.GetStatValue(curJob.RecipeDef.workTableSpeedStat, true);
                    }
                }
                if (DebugSettings.fastCrafting)
                {
                    num *= 30f;
                }
                workLeft -= num;
                actor.GainComfortFromCellIfPossible();
                if (workLeft <= 0f)
                {
                    ReadyForNextToil();
                }

                //pawn posture
                Verb            verbToUse = actor.jobs.curJob.verbToUse;
                LocalTargetInfo target    = actor.jobs.curJob.GetTarget(TargetIndex.A);
                pawn.stances.SetStance(new Stance_Warmup(1, target, verbToUse));

                //sound:
                if (verbToUse.verbProps != null && verbToUse.verbProps.warmupTime > 0)
                {
                    if ((ticksSpentDoingRecipeWork % verbToUse.verbProps.AdjustedFullCycleTime(verbToUse, actor).SecondsToTicks()) == 0)
                    {
                        if (verbToUse.verbProps.soundCast != null)
                        {
                            verbToUse.verbProps.soundCast.PlayOneShot(new TargetInfo(pawn.Position, pawn.Map, false));
                        }
                        if (verbToUse.verbProps.soundCastTail != null)
                        {
                            verbToUse.verbProps.soundCastTail.PlayOneShotOnCamera(pawn.Map);
                        }
                    }
                }
                if (job.RecipeDef.workSkill != null)
                {
                    //float xpDelta = techComp.proficientWeapons.Contains(job.targetB.Thing.def) ? 1f : 0.1f;
                    float xp = 0.1f * job.RecipeDef.workSkillLearnFactor;
                    actor.skills.GetSkill(job.RecipeDef.workSkill).Learn(xp, false);
                }
            };
            train.defaultCompleteMode = ToilCompleteMode.Never;
            train.WithEffect(() => train.actor.CurJob.bill.recipe.effectWorking, TargetIndex.A);
            train.PlaySustainerOrSound(() => train.actor.CurJob.bill.recipe.soundWorking);
            train.WithProgressBar(TargetIndex.A, delegate
            {
                Pawn actor = train.actor;
                Job curJob = actor.CurJob;
                //return 1f - ((JobDriver_DoBill)actor.jobs.curDriver).workLeft / curJob.bill.recipe.WorkAmountTotal(null);
                return(1f - (workLeft / curJob.bill.recipe.WorkAmountTotal(null)));
            }, false, -0.5f);
            train.FailOn(() => train.actor.CurJob.bill.suspended);
            train.activeSkill = () => train.actor.CurJob.bill.recipe.workSkill;
            yield return(train.FailOnDespawnedNullOrForbiddenPlacedThings().FailOnCannotTouch(TargetIndex.A, PathEndMode.InteractionCell));

            Toil finalizeTraining = new Toil();

            finalizeTraining.initAction = delegate
            {
                Pawn          actor    = finalizeTraining.actor;
                CompKnowledge techComp = actor.TryGetComp <CompKnowledge>();
                if (!techComp.proficientWeapons.Contains(job.targetB.Thing.def))
                {
                    techComp.proficientWeapons.Add(TargetThingB.def);
                }
                job.bill.Notify_IterationCompleted(actor, new List <Thing> {
                });
                actor.jobs.EndCurrentJob(JobCondition.Succeeded, false);
            };
            finalizeTraining.defaultCompleteMode = ToilCompleteMode.Instant;
            finalizeTraining.FailOnDespawnedOrNull(TargetIndex.A);
            yield return(finalizeTraining);

            //testing
            yield return(Toils_Reserve.Reserve(TargetIndex.B, 1, -1, null));

            Toil findPlaceTarget = Toils_Haul.CarryHauledThingToCell(TargetIndex.B);

            yield return(findPlaceTarget);

            yield return(Toils_Haul.PlaceHauledThingInCell(TargetIndex.B, findPlaceTarget, true, true));

            yield break;
        }