qstbak/QuestionableCompanion/QuestionableCompanion.Services/MultiClientIPC.cs
2025-12-04 04:39:08 +10:00

230 lines
6.9 KiB
C#

using System;
using Dalamud.Plugin;
using Dalamud.Plugin.Ipc;
using Dalamud.Plugin.Services;
namespace QuestionableCompanion.Services;
public class MultiClientIPC : IDisposable
{
private readonly IDalamudPluginInterface pluginInterface;
private readonly IPluginLog log;
private readonly ICallGateProvider<string, ushort, object?> requestHelperProvider;
private readonly ICallGateProvider<object?> dismissHelperProvider;
private readonly ICallGateProvider<string, ushort, object?> helperAvailableProvider;
private readonly ICallGateProvider<string, object?> chatMessageProvider;
private readonly ICallGateProvider<string, ushort, object?> passengerMountedProvider;
private readonly ICallGateSubscriber<string, ushort, object?> requestHelperSubscriber;
private readonly ICallGateSubscriber<object?> dismissHelperSubscriber;
private readonly ICallGateSubscriber<string, ushort, object?> helperAvailableSubscriber;
private readonly ICallGateSubscriber<string, object?> chatMessageSubscriber;
private readonly ICallGateSubscriber<string, ushort, object?> passengerMountedSubscriber;
public event Action<string, ushort>? OnHelperRequested;
public event Action? OnHelperDismissed;
public event Action<string, ushort>? OnHelperAvailable;
public event Action<string>? OnChatMessageReceived;
public event Action<string, ushort>? OnPassengerMounted;
public MultiClientIPC(IDalamudPluginInterface pluginInterface, IPluginLog log)
{
this.pluginInterface = pluginInterface;
this.log = log;
requestHelperProvider = pluginInterface.GetIpcProvider<string, ushort, object>("QSTCompanion.RequestHelper");
dismissHelperProvider = pluginInterface.GetIpcProvider<object>("QSTCompanion.DismissHelper");
helperAvailableProvider = pluginInterface.GetIpcProvider<string, ushort, object>("QSTCompanion.HelperAvailable");
chatMessageProvider = pluginInterface.GetIpcProvider<string, object>("QSTCompanion.ChatMessage");
passengerMountedProvider = pluginInterface.GetIpcProvider<string, ushort, object>("QSTCompanion.PassengerMounted");
requestHelperSubscriber = pluginInterface.GetIpcSubscriber<string, ushort, object>("QSTCompanion.RequestHelper");
dismissHelperSubscriber = pluginInterface.GetIpcSubscriber<object>("QSTCompanion.DismissHelper");
helperAvailableSubscriber = pluginInterface.GetIpcSubscriber<string, ushort, object>("QSTCompanion.HelperAvailable");
chatMessageSubscriber = pluginInterface.GetIpcSubscriber<string, object>("QSTCompanion.ChatMessage");
passengerMountedSubscriber = pluginInterface.GetIpcSubscriber<string, ushort, object>("QSTCompanion.PassengerMounted");
requestHelperProvider.RegisterFunc(delegate(string name, ushort worldId)
{
OnRequestHelperReceived(name, worldId);
return (object?)null;
});
dismissHelperProvider.RegisterFunc(delegate
{
OnDismissHelperReceived();
return (object?)null;
});
helperAvailableProvider.RegisterFunc(delegate(string name, ushort worldId)
{
OnHelperAvailableReceived(name, worldId);
return (object?)null;
});
chatMessageProvider.RegisterFunc(delegate(string message)
{
OnChatMessageReceivedInternal(message);
return (object?)null;
});
passengerMountedProvider.RegisterFunc(delegate(string questerName, ushort questerWorld)
{
OnPassengerMountedReceived(questerName, questerWorld);
return (object?)null;
});
log.Information("[MultiClientIPC] ✅ IPC initialized successfully");
}
public void RequestHelper(string characterName, ushort worldId)
{
try
{
log.Information($"[MultiClientIPC] Broadcasting helper request: {characterName}@{worldId}");
requestHelperSubscriber.InvokeFunc(characterName, worldId);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Failed to send helper request: " + ex.Message);
}
}
public void DismissHelper()
{
try
{
log.Information("[MultiClientIPC] Broadcasting helper dismiss");
dismissHelperSubscriber.InvokeFunc();
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Failed to send helper dismiss: " + ex.Message);
}
}
private void OnRequestHelperReceived(string characterName, ushort worldId)
{
try
{
log.Information($"[MultiClientIPC] Received helper request: {characterName}@{worldId}");
this.OnHelperRequested?.Invoke(characterName, worldId);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Error handling helper request: " + ex.Message);
}
}
private void OnDismissHelperReceived()
{
try
{
log.Information("[MultiClientIPC] Received helper dismiss");
this.OnHelperDismissed?.Invoke();
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Error handling helper dismiss: " + ex.Message);
}
}
public void AnnounceHelperAvailable(string characterName, ushort worldId)
{
try
{
log.Information($"[MultiClientIPC] Broadcasting helper availability: {characterName}@{worldId}");
helperAvailableSubscriber.InvokeFunc(characterName, worldId);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Failed to announce helper: " + ex.Message);
}
}
private void OnHelperAvailableReceived(string characterName, ushort worldId)
{
try
{
log.Information($"[MultiClientIPC] Received helper available: {characterName}@{worldId}");
this.OnHelperAvailable?.Invoke(characterName, worldId);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Error handling helper available: " + ex.Message);
}
}
public void SendChatMessage(string message)
{
try
{
log.Information("[MultiClientIPC] Broadcasting chat message: " + message);
chatMessageSubscriber.InvokeFunc(message);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Failed to send chat message: " + ex.Message);
}
}
private void OnChatMessageReceivedInternal(string message)
{
try
{
log.Information("[MultiClientIPC] Received chat message: " + message);
this.OnChatMessageReceived?.Invoke(message);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Error handling chat message: " + ex.Message);
}
}
public void SendPassengerMounted(string questerName, ushort questerWorld)
{
try
{
log.Information($"[MultiClientIPC] Broadcasting passenger mounted: {questerName}@{questerWorld}");
passengerMountedSubscriber.InvokeFunc(questerName, questerWorld);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Failed to send passenger mounted: " + ex.Message);
}
}
private void OnPassengerMountedReceived(string questerName, ushort questerWorld)
{
try
{
log.Information($"[MultiClientIPC] Received passenger mounted: {questerName}@{questerWorld}");
this.OnPassengerMounted?.Invoke(questerName, questerWorld);
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Error handling passenger mounted: " + ex.Message);
}
}
public void Dispose()
{
try
{
requestHelperProvider.UnregisterFunc();
dismissHelperProvider.UnregisterFunc();
helperAvailableProvider.UnregisterFunc();
chatMessageProvider.UnregisterFunc();
}
catch (Exception ex)
{
log.Error("[MultiClientIPC] Error during dispose: " + ex.Message);
}
}
}