feat: add Auto Fishing Stool plugin
This commit is contained in:
152
AutoFishingStool/Plugin.cs
Normal file
152
AutoFishingStool/Plugin.cs
Normal file
@@ -0,0 +1,152 @@
|
||||
using System;
|
||||
using Dalamud.Game.ClientState.Conditions;
|
||||
using Dalamud.IoC;
|
||||
using Dalamud.Plugin;
|
||||
using Dalamud.Plugin.Services;
|
||||
using FFXIVClientStructs.FFXIV.Client.System.String;
|
||||
using FFXIVClientStructs.FFXIV.Client.UI;
|
||||
|
||||
namespace AutoFishingStool;
|
||||
|
||||
public sealed unsafe class Plugin : IDalamudPlugin
|
||||
{
|
||||
private const int SitDelayMilliseconds = 2500;
|
||||
private const int ActionSettleMilliseconds = 500;
|
||||
private const uint FisherClassJobId = 18;
|
||||
|
||||
[PluginService]
|
||||
internal static ICondition Condition { get; private set; } = null!;
|
||||
|
||||
[PluginService]
|
||||
internal static IFramework Framework { get; private set; } = null!;
|
||||
|
||||
[PluginService]
|
||||
internal static IPlayerState PlayerState { get; private set; } = null!;
|
||||
|
||||
[PluginService]
|
||||
internal static IPluginLog Log { get; private set; } = null!;
|
||||
|
||||
private DateTime? sitAt;
|
||||
private bool satThisSession;
|
||||
private bool waitingForActionToFinish;
|
||||
|
||||
public Plugin()
|
||||
{
|
||||
Condition.ConditionChange += OnConditionChange;
|
||||
Framework.Update += OnFrameworkUpdate;
|
||||
Log.Information("Auto Fishing Stool loaded");
|
||||
}
|
||||
|
||||
private void OnConditionChange(ConditionFlag flag, bool value)
|
||||
{
|
||||
if (flag == ConditionFlag.Fishing)
|
||||
{
|
||||
Log.Information("Fishing condition changed to {Value}", value);
|
||||
|
||||
if (value && Condition[ConditionFlag.Gathering] && IsFisher() && !satThisSession)
|
||||
{
|
||||
sitAt = DateTime.UtcNow.AddMilliseconds(SitDelayMilliseconds);
|
||||
waitingForActionToFinish = false;
|
||||
Log.Information("Fishing became active; stable Sit timer started");
|
||||
}
|
||||
else if (!value && !satThisSession)
|
||||
{
|
||||
sitAt = null;
|
||||
waitingForActionToFinish = false;
|
||||
Log.Information("Fishing became inactive; stable Sit timer reset");
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (flag != ConditionFlag.Gathering)
|
||||
return;
|
||||
|
||||
Log.Information("Gathering condition changed to {Value}", value);
|
||||
|
||||
if (value)
|
||||
{
|
||||
if (!IsFisher())
|
||||
return;
|
||||
|
||||
satThisSession = false;
|
||||
sitAt = null;
|
||||
waitingForActionToFinish = false;
|
||||
Log.Information("Fisher gathering session started");
|
||||
return;
|
||||
}
|
||||
|
||||
sitAt = null;
|
||||
satThisSession = false;
|
||||
waitingForActionToFinish = false;
|
||||
}
|
||||
|
||||
private void OnFrameworkUpdate(IFramework framework)
|
||||
{
|
||||
if (satThisSession || sitAt is null)
|
||||
return;
|
||||
|
||||
if (!Condition[ConditionFlag.Gathering] || !Condition[ConditionFlag.Fishing] || !IsFisher())
|
||||
{
|
||||
sitAt = null;
|
||||
satThisSession = false;
|
||||
waitingForActionToFinish = false;
|
||||
return;
|
||||
}
|
||||
|
||||
if (DateTime.UtcNow < sitAt.Value)
|
||||
return;
|
||||
|
||||
if (Condition[ConditionFlag.ExecutingGatheringAction])
|
||||
{
|
||||
if (!waitingForActionToFinish)
|
||||
{
|
||||
waitingForActionToFinish = true;
|
||||
Log.Information("Sit timer elapsed during a fishing action; waiting for it to finish");
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (waitingForActionToFinish)
|
||||
{
|
||||
waitingForActionToFinish = false;
|
||||
sitAt = DateTime.UtcNow.AddMilliseconds(ActionSettleMilliseconds);
|
||||
Log.Information("Fishing action finished; Sit command scheduled after settling");
|
||||
return;
|
||||
}
|
||||
|
||||
var uiModule = UIModule.Instance();
|
||||
if (uiModule is null)
|
||||
{
|
||||
Log.Warning("Could not access the game's UI module");
|
||||
sitAt = null;
|
||||
return;
|
||||
}
|
||||
|
||||
var command = Utf8String.FromString("/sit");
|
||||
try
|
||||
{
|
||||
uiModule->ProcessChatBoxEntry(command);
|
||||
Log.Information("Submitted /sit after fishing started");
|
||||
}
|
||||
finally
|
||||
{
|
||||
command->Dtor(true);
|
||||
}
|
||||
satThisSession = true;
|
||||
sitAt = null;
|
||||
waitingForActionToFinish = false;
|
||||
}
|
||||
|
||||
private static bool IsFisher()
|
||||
{
|
||||
return PlayerState.IsLoaded && PlayerState.ClassJob.RowId == FisherClassJobId;
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Condition.ConditionChange -= OnConditionChange;
|
||||
Framework.Update -= OnFrameworkUpdate;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user