diff --git a/Libraries/Core/Controllers/QuestController.cs b/Libraries/Core/Controllers/QuestController.cs
index 3d3b2a92..592ddad9 100644
--- a/Libraries/Core/Controllers/QuestController.cs
+++ b/Libraries/Core/Controllers/QuestController.cs
@@ -1,3 +1,4 @@
+using System.Text.Json;
using SptCommon.Annotations;
using Core.Helpers;
using Core.Models.Eft.Common;
@@ -12,6 +13,7 @@ using Core.Servers;
using Core.Services;
using Core.Utils;
using Core.Utils.Cloners;
+using SptCommon.Extensions;
namespace Core.Controllers;
@@ -217,7 +219,7 @@ public class QuestController(
{
if (condition.Id == handoverQuestRequest.ConditionId && handoverQuestTypes.Contains(condition.ConditionType))
{
- handedInCount = int.Parse((string)condition.Value);
+ handedInCount = int.Parse(condition.Value.ToString());
isItemHandoverQuest = condition.ConditionType == handoverQuestTypes.FirstOrDefault();
handoverRequirements = condition;
diff --git a/Libraries/Core/Helpers/QuestHelper.cs b/Libraries/Core/Helpers/QuestHelper.cs
index 6f6e7469..c0447587 100644
--- a/Libraries/Core/Helpers/QuestHelper.cs
+++ b/Libraries/Core/Helpers/QuestHelper.cs
@@ -96,7 +96,18 @@ public class QuestHelper(
/// Reduction of cartesian product between two quest lists
public List GetDeltaQuests(List before, List after)
{
- throw new System.NotImplementedException();
+ List knownQuestsIds = [];
+ foreach (var quest in before) {
+ knownQuestsIds.Add(quest.Id);
+ }
+
+ if (knownQuestsIds.Count != 0) {
+ return after.Where((q) => {
+ return knownQuestsIds.IndexOf(q.Id) == -1;
+ }).ToList();
+ }
+
+ return after;
}
///
@@ -107,7 +118,43 @@ public class QuestHelper(
/// the adjusted skill progress gain
public int AdjustSkillExpForLowLevels(Common profileSkill, int progressAmount)
{
- throw new System.NotImplementedException();
+ var currentLevel = Math.Floor((double)(profileSkill.Progress / 100));
+
+ // Only run this if the current level is under 9
+ if (currentLevel >= 9) {
+ return progressAmount;
+ }
+
+ // This calculates how much progress we have in the skill's starting level
+ var startingLevelProgress = (profileSkill.Progress % 100) * ((currentLevel + 1) / 10);
+
+ // The code below assumes a 1/10th progress skill amount
+ var remainingProgress = progressAmount / 10;
+
+ // We have to do this loop to handle edge cases where the provided XP bumps your level up
+ // See "CalculateExpOnFirstLevels" in client for original logic
+ var adjustedSkillProgress = 0;
+ while (remainingProgress > 0 && currentLevel < 9) {
+ // Calculate how much progress to add, limiting it to the current level max progress
+ var currentLevelRemainingProgress = (currentLevel + 1) * 10 - startingLevelProgress;
+ _logger.Debug($"currentLevelRemainingProgress: {currentLevelRemainingProgress}");
+ var progressToAdd = Math.Min(remainingProgress, currentLevelRemainingProgress ?? 0);
+ var adjustedProgressToAdd = (10 / (currentLevel + 1)) * progressToAdd;
+ _logger.Debug($"Progress To Add: {progressToAdd} Adjusted for level: {adjustedProgressToAdd}");
+
+ // Add the progress amount adjusted by level
+ adjustedSkillProgress += (int)adjustedProgressToAdd;
+ remainingProgress -= (int)progressToAdd;
+ startingLevelProgress = 0;
+ currentLevel++;
+ }
+
+ // If there's any remaining progress, add it. This handles if you go from level 8 -> 9
+ if (remainingProgress > 0) {
+ adjustedSkillProgress += remainingProgress;
+ }
+
+ return adjustedSkillProgress;
}
///
@@ -1174,7 +1221,7 @@ public class QuestHelper(
return false;
}
- return quest.Conditions.Fail.Any(condition => (condition.Target.List?.Contains(completedQuestId) ?? false));
+ return quest.Conditions.Fail.Any(condition => (condition.Target?.List?.Contains(completedQuestId) ?? false));
}
)
.ToList();
diff --git a/Libraries/Core/Helpers/RewardHelper.cs b/Libraries/Core/Helpers/RewardHelper.cs
index ac4bda66..8521a070 100644
--- a/Libraries/Core/Helpers/RewardHelper.cs
+++ b/Libraries/Core/Helpers/RewardHelper.cs
@@ -100,14 +100,14 @@ namespace Core.Helpers
case RewardType.Experience:
_profileHelper.AddExperienceToPmc(
sessionId,
- (int)reward.Value
+ int.Parse(reward.Value.ToString())
); // this must occur first as the output object needs to take the modified profile exp value
break;
case RewardType.TraderStanding:
_traderHelper.AddStandingToTrader(
sessionId,
reward.Target,
- (double)reward.Value
+ double.Parse(reward.Value.ToString())
);
break;
case RewardType.TraderUnlock: