if (_clientState.LocalPlayer!.Level < quest.Info.Level)
{
- _logger.LogInformation("Stopping automation, player level ({PlayerLevel}) < quest level ({QuestLevel}",
+ _logger.LogInformation(
+ "Stopping automation, player level ({PlayerLevel}) < quest level ({QuestLevel}",
_clientState.LocalPlayer!.Level, quest.Info.Level);
Stop("Quest level too high");
}
if (questToRun.Sequence != currentSequence)
{
questToRun.SetSequence(currentSequence);
- CheckNextTasks($"New sequence {questToRun == _startedQuest}/{_questFunctions.GetCurrentQuestInternal()}");
+ CheckNextTasks(
+ $"New sequence {questToRun == _startedQuest}/{_questFunctions.GetCurrentQuestInternal()}");
}
var q = questToRun.Quest;
];
EClassJob classJob = (EClassJob?)_clientState.LocalPlayer?.ClassJob.Id ?? EClassJob.Adventurer;
+ ushort[] shadowbringersRoleQuestChapters = QuestData.AllRoleQuestChapters.Select(x => x[0]).ToArray();
if (classJob != EClassJob.Adventurer)
{
priorityQuests.AddRange(_questRegistry.GetKnownClassJobQuests(classJob)
- .Where(x => _questRegistry.TryGetQuest(x.QuestId, out Quest? quest) && quest.Info is QuestInfo
+ .Where(x =>
{
- // ignore Endwalker/Dawntrail, as the class quests are optional
- Expansion: EExpansionVersion.ARealmReborn or EExpansionVersion.Heavensward or EExpansionVersion.Stormblood or EExpansionVersion.Shadowbringers
+ if (!_questRegistry.TryGetQuest(x.QuestId, out Quest? quest) ||
+ quest.Info is not QuestInfo questInfo)
+ return false;
+
+ // if no shadowbringers role quest is complete, (at least one) is required
+ if (shadowbringersRoleQuestChapters.Contains(questInfo.NewGamePlusChapter))
+ return !QuestData.FinalShadowbringersRoleQuests.Any(_questFunctions.IsQuestComplete);
+
+ // ignore all other role quests
+ if (QuestData.AllRoleQuestChapters.Any(y => y.Contains(questInfo.NewGamePlusChapter)))
+ return false;
+
+ // even job quests for the later expacs (after role quests were introduced) might have skills locked
+ // behind them, e.g. reaper and sage
+
+ return true;
})
.Select(x => x.QuestId));
}
{
public static readonly IReadOnlyList<QuestId> CrystalTowerQuests =
[new(1709), new(1200), new(1201), new(1202), new(1203), new(1474), new(494), new(495)];
+
+ public static readonly IReadOnlyList<ushort> TankRoleQuests = [136, 154, 178];
+ public static readonly IReadOnlyList<ushort> HealerRoleQuests = [137, 155, 179];
+ public static readonly IReadOnlyList<ushort> MeleeRoleQuests = [138, 156, 180];
+ public static readonly IReadOnlyList<ushort> PhysicalRangedRoleQuests = [138, 157, 181];
+ public static readonly IReadOnlyList<ushort> CasterRoleQuests = [139, 158, 182];
+ public static readonly IReadOnlyList<IReadOnlyList<ushort>> AllRoleQuestChapters =
+ [
+ TankRoleQuests,
+ HealerRoleQuests,
+ MeleeRoleQuests,
+ PhysicalRangedRoleQuests,
+ CasterRoleQuests
+ ];
+
+ public static readonly IReadOnlyList<QuestId> FinalShadowbringersRoleQuests =
+ [new(3248), new(3272), new(3278), new(3628)];
+
private readonly Dictionary<ElementId, IQuestInfo> _quests;
public QuestData(IDataManager dataManager)
chapterIds.AddRange(classJob switch
{
- _ when classJob.IsTank() => [136, 154, 178],
- _ when classJob.IsHealer() => [137, 155, 179],
- _ when classJob.IsMelee() => [138, 156, 180],
- _ when classJob.IsPhysicalRanged() => [138, 157, 181],
- _ when classJob.IsCaster() && classJob != EClassJob.BlueMage => [139, 158, 182],
+ _ when classJob.IsTank() => TankRoleQuests,
+ _ when classJob.IsHealer() => HealerRoleQuests,
+ _ when classJob.IsMelee() => MeleeRoleQuests,
+ _ when classJob.IsPhysicalRanged() => PhysicalRangedRoleQuests,
+ _ when classJob.IsCaster() && classJob != EClassJob.BlueMage => CasterRoleQuests,
_ => []
});