Skip to content

Commit

Permalink
Merge pull request #429 from Akechi-kun/PLD
Browse files Browse the repository at this point in the history
ClassPLDUtility.cs update; ClassDRKUtility.cs implementation
  • Loading branch information
awgil authored Aug 22, 2024
2 parents 0740c0f + 6b2be33 commit cfc0090
Show file tree
Hide file tree
Showing 4 changed files with 132 additions and 15 deletions.
1 change: 1 addition & 0 deletions BossMod/ActionQueue/Tanks/DRK.cs
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ public enum TraitID : uint
public enum SID : uint
{
None = 0,
Oblation = 2682,
BloodWeapon = 742,
Grit = 743,
SaltedEarth = 749,
Expand Down
72 changes: 72 additions & 0 deletions BossMod/Autorotation/Utility/ClassDRKUtility.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
namespace BossMod.Autorotation;

public sealed class ClassDRKUtility(RotationModuleManager manager, Actor player) : RoleTankUtility(manager, player)
{
public enum Track { DarkMind = SharedTrack.Count, ShadowWall, LivingDead, TheBlackestNight, Oblation, DarkMissionary }
public enum WallOption { None, ShadowWall, ShadowedVigil }
public enum OblationStrategy { None, Force, Delay }

public static readonly ActionID IDLimitBreak3 = ActionID.MakeSpell(DRK.AID.DarkForce);
public static readonly ActionID IDStanceApply = ActionID.MakeSpell(DRK.AID.Grit);
public static readonly ActionID IDStanceRemove = ActionID.MakeSpell(DRK.AID.ReleaseGrit);

public static RotationModuleDefinition Definition()
{
var res = new RotationModuleDefinition("Utility: DRK", "Planner support for utility actions", "Akechi", RotationModuleQuality.Ok, BitMask.Build((int)Class.DRK), 100);
DefineShared(res, IDLimitBreak3, IDStanceApply, IDStanceRemove);

DefineSimpleConfig(res, Track.DarkMind, "DarkMind", "DMind", 450, DRK.AID.DarkMind, 10); //120s CD, 15s duration

res.Define(Track.ShadowWall).As<WallOption>("ShadowWall", "Wall", 550) //120s CD, 15s duration
.AddOption(WallOption.None, "None", "Do not use automatically")
.AddOption(WallOption.ShadowWall, "Use", "Use ShadowWall", 120, 15, ActionTargets.Self, 38, 91)
.AddOption(WallOption.ShadowedVigil, "UseEx", "Use ShadowedVigil", 120, 15, ActionTargets.Self, 92)
.AddAssociatedActions(DRK.AID.ShadowWall, DRK.AID.ShadowedVigil);

DefineSimpleConfig(res, Track.LivingDead, "LivingDead", "LD", 400, DRK.AID.LivingDead, 10); //300s CD, 10s duration
DefineSimpleConfig(res, Track.TheBlackestNight, "The Blackest Night", "TBN", 400, DRK.AID.TheBlackestNight, 7); //15s CD, 7s duration, 3000MP cost

res.Define(Track.Oblation).As<OblationStrategy>("Oblation", "", 550) //60s (120s total), 10s duration, 2 charges
.AddOption(OblationStrategy.None, "None", "Do not use automatically")
.AddOption(OblationStrategy.Force, "Use", "Use Oblation", 60, 10, ActionTargets.Self, 82)
.AddOption(OblationStrategy.Delay, "Don't use", "Delay Oblation")
.AddAssociatedActions(DRK.AID.Oblation);

DefineSimpleConfig(res, Track.DarkMissionary, "DarkMissionary", "Mission", 220, DRK.AID.DarkMissionary, 15); //90s CD, 15s duration

//DefineSimpleConfig(res, Track.Shadowstride, "Shadowstride", "Dash", 380, DRK.AID.Shadowstride); (TODO: Dash no longer does damage, consider how to add this)

return res;
}

public override void Execute(StrategyValues strategy, Actor? primaryTarget, float estimatedAnimLockDelay, float forceMovementIn, bool isMoving)
{
ExecuteShared(strategy, IDLimitBreak3, IDStanceApply, IDStanceRemove, (uint)DRK.SID.Grit, primaryTarget); //Execution of our shared abilities
ExecuteSimple(strategy.Option(Track.DarkMind), DRK.AID.DarkMind, Player); //Execution of DarkMind
ExecuteSimple(strategy.Option(Track.LivingDead), DRK.AID.LivingDead, Player); //Execution of LivingDead
ExecuteSimple(strategy.Option(Track.TheBlackestNight), DRK.AID.TheBlackestNight, Player); //Execution of TheBlackestNight
ExecuteSimple(strategy.Option(Track.DarkMissionary), DRK.AID.DarkMissionary, Player); //Execution of DarkMissionary

//ExecuteSimple(strategy.Option(Track.Shadowstride), DRK.AID.Shadowstride, primaryTarget); (TODO: Dash no longer does damage, consider how to add this)

var obl = strategy.Option(Track.Oblation);
var oblAction = obl.As<OblationStrategy>() switch
{
OblationStrategy.Force => DRK.AID.Oblation,
OblationStrategy.Delay => DRK.AID.None,
_ => default
};
if (oblAction != default && SelfStatusLeft(DRK.SID.Oblation) <= 3f)
Hints.ActionsToExecute.Push(ActionID.MakeSpell(oblAction), Player, obl.Priority(), obl.Value.ExpireIn); //Checking proper use of said option

var wall = strategy.Option(Track.ShadowWall);
var wallAction = wall.As<WallOption>() switch
{
WallOption.ShadowWall => DRK.AID.ShadowWall,
WallOption.ShadowedVigil => DRK.AID.ShadowedVigil,
_ => default
};
if (wallAction != default)
Hints.ActionsToExecute.Push(ActionID.MakeSpell(wallAction), Player, wall.Priority(), wall.Value.ExpireIn); //Checking proper use of said option
}
}
70 changes: 57 additions & 13 deletions BossMod/Autorotation/Utility/ClassPLDUtility.cs
Original file line number Diff line number Diff line change
@@ -1,31 +1,75 @@
namespace BossMod.Autorotation;
using static FFXIVClientStructs.FFXIV.Client.UI.AddonJobHudPLD0;

namespace BossMod.Autorotation;

public sealed class ClassPLDUtility(RotationModuleManager manager, Actor player) : RoleTankUtility(manager, player)
{
public enum Track { Sheltron = SharedTrack.Count, Sentinel, HallowedGround }
public enum BWOption { None, Bloodwhetting, RawIntuition, NascentFlash }
public enum Track { Sheltron = SharedTrack.Count, Sentinel, Cover, Bulwark, DivineVeil, PassageOfArms, HallowedGround } //What we're tracking
public enum ShelOption { None, Sheltron, HolySheltron, Intervention } //Sheltron Options
public enum SentOption { None, Sentinel, Guardian } //Sentinel enhancement

public static readonly ActionID IDLimitBreak3 = ActionID.MakeSpell(PLD.AID.LastBastion);
public static readonly ActionID IDStanceApply = ActionID.MakeSpell(PLD.AID.IronWill);
public static readonly ActionID IDStanceRemove = ActionID.MakeSpell(PLD.AID.ReleaseIronWill);
public static readonly ActionID IDLimitBreak3 = ActionID.MakeSpell(PLD.AID.LastBastion); //LB
public static readonly ActionID IDStanceApply = ActionID.MakeSpell(PLD.AID.IronWill); //StanceOn
public static readonly ActionID IDStanceRemove = ActionID.MakeSpell(PLD.AID.ReleaseIronWill); //StanceOff

public static RotationModuleDefinition Definition()
{
var res = new RotationModuleDefinition("Utility: PLD", "Planner support for utility actions", "veyn", RotationModuleQuality.WIP, BitMask.Build((int)Class.PLD), 60);
var res = new RotationModuleDefinition("Utility: PLD", "Planner support for utility actions", "veyn, Akechi", RotationModuleQuality.Good, BitMask.Build((int)Class.PLD), 100);

DefineShared(res, IDLimitBreak3, IDStanceApply, IDStanceRemove);

DefineSimpleConfig(res, Track.Sheltron, "Sheltron", "", 380, PLD.AID.Sheltron, 6);
DefineSimpleConfig(res, Track.Sentinel, "Sentinel", "", 550, PLD.AID.Sentinel, 15);
DefineSimpleConfig(res, Track.HallowedGround, "HallowedGround", "Invuln", 400, PLD.AID.HallowedGround, 10);
res.Define(Track.Sheltron).As<ShelOption>("Sheltron", "Shel", 350) //Sheltron definitions
.AddOption(ShelOption.None, "None", "Do not use automatically")
.AddOption(ShelOption.Sheltron, "Sheltron", "Use Sheltron", 0, 4, ActionTargets.Self, 35, 81) //5s CD, 6s duration, -50 OathGauge cost
.AddOption(ShelOption.HolySheltron, "HolySheltron", "Use Holy Sheltron", 0, 4, ActionTargets.Self, 82) //5s CD, 8s duration (similar to GNB/WAR we only really care about the first 4s of the mit), -50 OathGauge cost
.AddOption(ShelOption.Intervention, "Intervention", "Use Intervention", 0, 4, ActionTargets.Party, 62) //10s CD, 8s duration (similar to GNB/WAR we only really care about the first 4s of the buddy mit), -50 OathGauge cost
.AddAssociatedActions(PLD.AID.Sheltron, PLD.AID.HolySheltron, PLD.AID.Intervention);

res.Define(Track.Sentinel).As<SentOption>("Sentinel", "Sent", 550) //Sentinel definition for CD plans
.AddOption(SentOption.None, "None", "Do not use automatically")
.AddOption(SentOption.Sentinel, "Use", "Use Sentinel", 120, 15, ActionTargets.Self, 38, 91) //120s CD, 15s duration
.AddOption(SentOption.Guardian, "UseEx", "Use Guardian", 120, 15, ActionTargets.Self, 92) //120s CD, 15s duration
.AddAssociatedActions(PLD.AID.Sentinel, PLD.AID.Guardian);

DefineSimpleConfig(res, Track.Cover, "Cover", "", 320, PLD.AID.Cover, 12); //120s CD, 12s duration, -50 OathGauge cost
DefineSimpleConfig(res, Track.Bulwark, "Bulwark", "Bul", 450, PLD.AID.Bulwark, 10); //90s CD, 15s duration
DefineSimpleConfig(res, Track.DivineVeil, "DivineVeil", "Veil", 220, PLD.AID.DivineVeil, 30); //90s CD, 30s duration
DefineSimpleConfig(res, Track.PassageOfArms, "PassageOfArms", "Arms", 470, PLD.AID.PassageOfArms, 3); //120s CD, 18s max duration
DefineSimpleConfig(res, Track.HallowedGround, "HallowedGround", "Inv", 400, PLD.AID.HallowedGround, 10); //420s CD, 10s duration
//DefineSimpleConfig(res, Track.Clemency, "Clemency", "Clem", 420, PLD.AID.Clemency); (TODO: we don't really care about this, do we? maybe later)

return res;
}

public override void Execute(StrategyValues strategy, Actor? primaryTarget, float estimatedAnimLockDelay, float forceMovementIn, bool isMoving)
{
ExecuteShared(strategy, IDLimitBreak3, IDStanceApply, IDStanceRemove, (uint)PLD.SID.IronWill, primaryTarget);
ExecuteSimple(strategy.Option(Track.Sheltron), PLD.AID.Sheltron, Player);
ExecuteSimple(strategy.Option(Track.Sentinel), PLD.AID.Sentinel, Player);
ExecuteSimple(strategy.Option(Track.HallowedGround), PLD.AID.HallowedGround, Player);
ExecuteSimple(strategy.Option(Track.Cover), PLD.AID.Cover, Player); //Cover execution
ExecuteSimple(strategy.Option(Track.Bulwark), PLD.AID.Bulwark, Player); //Bulwark execution
ExecuteSimple(strategy.Option(Track.DivineVeil), PLD.AID.DivineVeil, Player); //DivineVeil execution
ExecuteSimple(strategy.Option(Track.PassageOfArms), PLD.AID.PassageOfArms, Player); //PassageOfArms execution
ExecuteSimple(strategy.Option(Track.HallowedGround), PLD.AID.HallowedGround, Player); //HallowedGround execution
//DefineSimpleConfig(res, Track.Clemency, "Clemency", "Clem", 420, PLD.AID.Clemency); (TODO: we don't really care about this, do we? maybe later)

var shel = strategy.Option(Track.Sheltron);
var shelAction = shel.As<ShelOption>() switch
{
ShelOption.HolySheltron => PLD.AID.HolySheltron,
ShelOption.Sheltron => PLD.AID.Sheltron,
ShelOption.Intervention => PLD.AID.Intervention,
_ => default
};
if (shelAction != default)
Hints.ActionsToExecute.Push(ActionID.MakeSpell(shelAction), shelAction == PLD.AID.Intervention ? ResolveTargetOverride(shel.Value) ?? CoTank() : Player, shel.Priority(), shel.Value.ExpireIn); //Sheltron & Intervention execution

var sent = strategy.Option(Track.Sentinel);
var sentAction = sent.As<SentOption>() switch
{
SentOption.Sentinel => PLD.AID.Sentinel,
SentOption.Guardian => PLD.AID.Guardian,
_ => default
};
if (sentAction != default)
Hints.ActionsToExecute.Push(ActionID.MakeSpell(sentAction), Player, sent.Priority(), sent.Value.ExpireIn); //Sentinel execution
}
}
4 changes: 2 additions & 2 deletions BossMod/Autorotation/Utility/RoleTankUtility.cs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ protected static void DefineShared(RotationModuleDefinition def, ActionID lb3, A
DefineSimpleConfig(def, SharedTrack.Rampart, "Rampart", "", 500, ClassShared.AID.Rampart, 20);
DefineSimpleConfig(def, SharedTrack.LowBlow, "LowBlow", "Stun", -100, ClassShared.AID.LowBlow, 5);
DefineSimpleConfig(def, SharedTrack.Provoke, "Provoke", "", 200, ClassShared.AID.Provoke);
DefineSimpleConfig(def, SharedTrack.Interject, "Interject", "Interrupt", -50, ClassShared.AID.Interject);
DefineSimpleConfig(def, SharedTrack.Interject, "Interject", "Interrupt", 50, ClassShared.AID.Interject);

def.Define(SharedTrack.Reprisal).As<ReprisalOption>("Reprisal", "", 250)
.AddOption(ReprisalOption.None, "None", "Do not use automatically")
Expand All @@ -29,7 +29,7 @@ protected static void DefineShared(RotationModuleDefinition def, ActionID lb3, A
DefineSimpleConfig(def, SharedTrack.Shirk, "Shirk", "", 150, ClassShared.AID.Shirk);
DefineSimpleConfig(def, SharedTrack.ArmsLength, "ArmsLength", "ArmsL", 300, ClassShared.AID.ArmsLength, 6); // note: secondary effect 15s

def.Define(SharedTrack.Stance).As<StanceOption>("Stance", "", -10)
def.Define(SharedTrack.Stance).As<StanceOption>("Stance", "", 10)
.AddOption(StanceOption.None, "None", "Do not touch stance")
.AddOption(StanceOption.Apply, "Apply", "Use stance if not already active", 2)
.AddOption(StanceOption.Remove, "Remove", "Remove stance if active", 1)
Expand Down

0 comments on commit cfc0090

Please sign in to comment.