fix minions/mounts for 6.2, todo: remove penumbra redraw once glamourer is available
This commit is contained in:
2
MareAPI
2
MareAPI
Submodule MareAPI updated: 374cc31bab...37d4eb5b1d
@@ -31,14 +31,14 @@ public class CharacterDataFactory
|
|||||||
_ipcManager = ipcManager;
|
_ipcManager = ipcManager;
|
||||||
}
|
}
|
||||||
|
|
||||||
public CharacterData BuildCharacterData(CharacterData previousData, ObjectKind objectKind, IntPtr playerPointer, CancellationToken token)
|
public unsafe CharacterData BuildCharacterData(CharacterData previousData, ObjectKind objectKind, IntPtr playerPointer, CancellationToken token)
|
||||||
{
|
{
|
||||||
if (!_ipcManager.Initialized)
|
if (!_ipcManager.Initialized)
|
||||||
{
|
{
|
||||||
throw new ArgumentException("Penumbra is not connected");
|
throw new ArgumentException("Penumbra is not connected");
|
||||||
}
|
}
|
||||||
|
|
||||||
if (playerPointer == IntPtr.Zero)
|
if (playerPointer == IntPtr.Zero || ((Character*)playerPointer)->GameObject.GetDrawObject() == null)
|
||||||
{
|
{
|
||||||
Logger.Verbose("Pointer was zero for " + objectKind);
|
Logger.Verbose("Pointer was zero for " + objectKind);
|
||||||
previousData.FileReplacements.Remove(objectKind);
|
previousData.FileReplacements.Remove(objectKind);
|
||||||
@@ -198,6 +198,11 @@ public class CharacterDataFactory
|
|||||||
|
|
||||||
private unsafe CharacterData CreateCharacterData(CharacterData previousData, ObjectKind objectKind, IntPtr charaPointer, CancellationToken token)
|
private unsafe CharacterData CreateCharacterData(CharacterData previousData, ObjectKind objectKind, IntPtr charaPointer, CancellationToken token)
|
||||||
{
|
{
|
||||||
|
if (previousData.FileReplacements.ContainsKey(objectKind))
|
||||||
|
{
|
||||||
|
previousData.FileReplacements[objectKind].Clear();
|
||||||
|
}
|
||||||
|
|
||||||
Stopwatch st = Stopwatch.StartNew();
|
Stopwatch st = Stopwatch.StartNew();
|
||||||
var chara = _dalamudUtil.CreateGameObject(charaPointer)!;
|
var chara = _dalamudUtil.CreateGameObject(charaPointer)!;
|
||||||
while (!_dalamudUtil.IsObjectPresent(chara))
|
while (!_dalamudUtil.IsObjectPresent(chara))
|
||||||
@@ -207,17 +212,9 @@ public class CharacterDataFactory
|
|||||||
}
|
}
|
||||||
_dalamudUtil.WaitWhileCharacterIsDrawing(charaPointer);
|
_dalamudUtil.WaitWhileCharacterIsDrawing(charaPointer);
|
||||||
|
|
||||||
if (previousData.FileReplacements.ContainsKey(objectKind))
|
|
||||||
{
|
|
||||||
previousData.FileReplacements[objectKind].Clear();
|
|
||||||
}
|
|
||||||
|
|
||||||
previousData.ManipulationString = _ipcManager.PenumbraGetMetaManipulations();
|
previousData.ManipulationString = _ipcManager.PenumbraGetMetaManipulations();
|
||||||
|
|
||||||
if (objectKind is not ObjectKind.Mount)
|
|
||||||
{
|
|
||||||
previousData.GlamourerString[objectKind] = _ipcManager.GlamourerGetCharacterCustomization(chara);
|
previousData.GlamourerString[objectKind] = _ipcManager.GlamourerGetCharacterCustomization(chara);
|
||||||
}
|
|
||||||
|
|
||||||
var human = (Human*)((Character*)charaPointer)->GameObject.GetDrawObject();
|
var human = (Human*)((Character*)charaPointer)->GameObject.GetDrawObject();
|
||||||
for (var mdlIdx = 0; mdlIdx < human->CharacterBase.SlotCount; ++mdlIdx)
|
for (var mdlIdx = 0; mdlIdx < human->CharacterBase.SlotCount; ++mdlIdx)
|
||||||
|
|||||||
@@ -236,14 +236,18 @@ public class CachedPlayer
|
|||||||
Logger.Debug(
|
Logger.Debug(
|
||||||
$"Request Redraw for {PlayerName}");
|
$"Request Redraw for {PlayerName}");
|
||||||
_ipcManager.GlamourerApplyAll(glamourerData, PlayerCharacter.Address);
|
_ipcManager.GlamourerApplyAll(glamourerData, PlayerCharacter.Address);
|
||||||
|
// todo: remove
|
||||||
|
_ipcManager.PenumbraRedraw(PlayerCharacter.Address);
|
||||||
}
|
}
|
||||||
else if (objectKind == ObjectKind.Minion)
|
else if (objectKind == ObjectKind.MinionOrMount)
|
||||||
{
|
{
|
||||||
var minion = ((Character*)PlayerCharacter.Address)->CompanionObject;
|
var minionOrMount = ((Character*)PlayerCharacter.Address)->CompanionObject;
|
||||||
if (minion != null)
|
if (minionOrMount != null)
|
||||||
{
|
{
|
||||||
Logger.Debug($"Request Redraw for Minion");
|
Logger.Debug($"Request Redraw for Minion/Mount");
|
||||||
_ipcManager.GlamourerApplyAll(glamourerData, obj: (IntPtr)minion);
|
_ipcManager.GlamourerApplyAll(glamourerData, obj: (IntPtr)minionOrMount);
|
||||||
|
// todo: remove
|
||||||
|
_ipcManager.PenumbraRedraw((IntPtr)minionOrMount);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (objectKind == ObjectKind.Pet)
|
else if (objectKind == ObjectKind.Pet)
|
||||||
@@ -253,6 +257,8 @@ public class CachedPlayer
|
|||||||
{
|
{
|
||||||
Logger.Debug("Request Redraw for Pet");
|
Logger.Debug("Request Redraw for Pet");
|
||||||
_ipcManager.GlamourerApplyAll(glamourerData, pet);
|
_ipcManager.GlamourerApplyAll(glamourerData, pet);
|
||||||
|
// todo: remove
|
||||||
|
_ipcManager.PenumbraRedraw(pet);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (objectKind == ObjectKind.Companion)
|
else if (objectKind == ObjectKind.Companion)
|
||||||
@@ -262,15 +268,8 @@ public class CachedPlayer
|
|||||||
{
|
{
|
||||||
Logger.Debug("Request Redraw for Companion");
|
Logger.Debug("Request Redraw for Companion");
|
||||||
_ipcManager.GlamourerApplyAll(glamourerData, companion);
|
_ipcManager.GlamourerApplyAll(glamourerData, companion);
|
||||||
}
|
// todo: remove
|
||||||
}
|
_ipcManager.PenumbraRedraw(companion);
|
||||||
else if (objectKind == ObjectKind.Mount)
|
|
||||||
{
|
|
||||||
var mount = ((CharaExt*)PlayerCharacter.Address)->Mount;
|
|
||||||
if (mount != null)
|
|
||||||
{
|
|
||||||
Logger.Debug($"Request Redraw for Mount");
|
|
||||||
_ipcManager.PenumbraRedraw((IntPtr)mount);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -283,13 +282,15 @@ public class CachedPlayer
|
|||||||
{
|
{
|
||||||
_ipcManager.GlamourerApplyOnlyCustomization(_originalGlamourerData, PlayerCharacter);
|
_ipcManager.GlamourerApplyOnlyCustomization(_originalGlamourerData, PlayerCharacter);
|
||||||
_ipcManager.GlamourerApplyOnlyEquipment(_lastGlamourerData, PlayerCharacter);
|
_ipcManager.GlamourerApplyOnlyEquipment(_lastGlamourerData, PlayerCharacter);
|
||||||
|
// todo: remove
|
||||||
|
_ipcManager.PenumbraRedraw(PlayerCharacter.Address);
|
||||||
}
|
}
|
||||||
else if (objectKind == ObjectKind.Minion)
|
else if (objectKind == ObjectKind.MinionOrMount)
|
||||||
{
|
{
|
||||||
var minion = ((Character*)PlayerCharacter.Address)->CompanionObject;
|
var minionOrMount = ((Character*)PlayerCharacter.Address)->CompanionObject;
|
||||||
if (minion != null)
|
if (minionOrMount != null)
|
||||||
{
|
{
|
||||||
_ipcManager.PenumbraRedraw((IntPtr)minion);
|
_ipcManager.PenumbraRedraw((IntPtr)minionOrMount);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (objectKind == ObjectKind.Pet)
|
else if (objectKind == ObjectKind.Pet)
|
||||||
@@ -308,14 +309,6 @@ public class CachedPlayer
|
|||||||
_ipcManager.PenumbraRedraw(companion);
|
_ipcManager.PenumbraRedraw(companion);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (objectKind == ObjectKind.Mount)
|
|
||||||
{
|
|
||||||
var mount = ((CharaExt*)PlayerCharacter.Address)->Mount;
|
|
||||||
if (mount != null)
|
|
||||||
{
|
|
||||||
_ipcManager.PenumbraRedraw((IntPtr)mount);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public void DisposePlayer()
|
public void DisposePlayer()
|
||||||
@@ -429,6 +422,7 @@ public class CachedPlayer
|
|||||||
Logger.Debug($"Player {PlayerName} changed, PenumbraRedraw is {RequestedPenumbraRedraw}");
|
Logger.Debug($"Player {PlayerName} changed, PenumbraRedraw is {RequestedPenumbraRedraw}");
|
||||||
if (!RequestedPenumbraRedraw && PlayerCharacter is not null)
|
if (!RequestedPenumbraRedraw && PlayerCharacter is not null)
|
||||||
{
|
{
|
||||||
|
_currentCharacterEquipment.HasUnprocessedUpdate = false;
|
||||||
Logger.Debug($"Saving new Glamourer data");
|
Logger.Debug($"Saving new Glamourer data");
|
||||||
_lastGlamourerData = _ipcManager.GlamourerGetCharacterCustomization(PlayerCharacter!);
|
_lastGlamourerData = _ipcManager.GlamourerGetCharacterCustomization(PlayerCharacter!);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -5,12 +5,10 @@ using System;
|
|||||||
using System.Threading;
|
using System.Threading;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
using MareSynchronos.API;
|
using MareSynchronos.API;
|
||||||
using Penumbra.GameData.Structs;
|
|
||||||
using FFXIVClientStructs.FFXIV.Client.Game.Character;
|
using FFXIVClientStructs.FFXIV.Client.Game.Character;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using MareSynchronos.Models;
|
using MareSynchronos.Models;
|
||||||
using MareSynchronos.Interop;
|
|
||||||
|
|
||||||
namespace MareSynchronos.Managers
|
namespace MareSynchronos.Managers
|
||||||
{
|
{
|
||||||
@@ -55,10 +53,9 @@ namespace MareSynchronos.Managers
|
|||||||
playerRelatedObjects = new List<PlayerRelatedObject>()
|
playerRelatedObjects = new List<PlayerRelatedObject>()
|
||||||
{
|
{
|
||||||
new PlayerRelatedObject(ObjectKind.Player, IntPtr.Zero, IntPtr.Zero, () => _dalamudUtil.PlayerPointer),
|
new PlayerRelatedObject(ObjectKind.Player, IntPtr.Zero, IntPtr.Zero, () => _dalamudUtil.PlayerPointer),
|
||||||
new PlayerRelatedObject(ObjectKind.Minion, IntPtr.Zero, IntPtr.Zero, () => (IntPtr)((Character*)_dalamudUtil.PlayerPointer)->CompanionObject),
|
new PlayerRelatedObject(ObjectKind.MinionOrMount, IntPtr.Zero, IntPtr.Zero, () => (IntPtr)((Character*)_dalamudUtil.PlayerPointer)->CompanionObject),
|
||||||
new PlayerRelatedObject(ObjectKind.Pet, IntPtr.Zero, IntPtr.Zero, () => _dalamudUtil.GetPet()),
|
new PlayerRelatedObject(ObjectKind.Pet, IntPtr.Zero, IntPtr.Zero, () => _dalamudUtil.GetPet()),
|
||||||
new PlayerRelatedObject(ObjectKind.Companion, IntPtr.Zero, IntPtr.Zero, () => _dalamudUtil.GetCompanion()),
|
new PlayerRelatedObject(ObjectKind.Companion, IntPtr.Zero, IntPtr.Zero, () => _dalamudUtil.GetCompanion()),
|
||||||
new PlayerRelatedObject(ObjectKind.Mount, IntPtr.Zero, IntPtr.Zero, () => (IntPtr)((CharaExt*)_dalamudUtil.PlayerPointer)->Mount),
|
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -21,7 +21,7 @@
|
|||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<DalamudLibPath>$(appdata)\XIVLauncher\addon\Hooks\6692d56\</DalamudLibPath>
|
<DalamudLibPath>$(appdata)\XIVLauncher\addon\Hooks\Dev\</DalamudLibPath>
|
||||||
<AssemblyVersion></AssemblyVersion>
|
<AssemblyVersion></AssemblyVersion>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
|
|||||||
@@ -47,7 +47,7 @@ namespace MareSynchronos.Models
|
|||||||
var chara = (Character*)curPtr;
|
var chara = (Character*)curPtr;
|
||||||
bool addr = Address == IntPtr.Zero || Address != curPtr;
|
bool addr = Address == IntPtr.Zero || Address != curPtr;
|
||||||
bool equip = CompareAndUpdateByteData(chara->EquipSlotData, chara->CustomizeData);
|
bool equip = CompareAndUpdateByteData(chara->EquipSlotData, chara->CustomizeData);
|
||||||
bool drawObj = (chara->GameObject.DrawObject != null && (IntPtr)chara->GameObject.DrawObject != DrawObjectAddress);
|
bool drawObj = (IntPtr)chara->GameObject.DrawObject != DrawObjectAddress;
|
||||||
var name = new Utf8String(chara->GameObject.Name).ToString();
|
var name = new Utf8String(chara->GameObject.Name).ToString();
|
||||||
bool nameChange = (name != _name);
|
bool nameChange = (name != _name);
|
||||||
if (addr || equip || drawObj || nameChange)
|
if (addr || equip || drawObj || nameChange)
|
||||||
@@ -98,8 +98,6 @@ namespace MareSynchronos.Models
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ObjectKind is not ObjectKind.Mount)
|
|
||||||
{
|
|
||||||
var newHatState = Marshal.ReadByte((IntPtr)customizeData + 30, 0);
|
var newHatState = Marshal.ReadByte((IntPtr)customizeData + 30, 0);
|
||||||
var newWeaponOrVisorState = Marshal.ReadByte((IntPtr)customizeData + 31, 0);
|
var newWeaponOrVisorState = Marshal.ReadByte((IntPtr)customizeData + 31, 0);
|
||||||
if (newHatState != HatState)
|
if (newHatState != HatState)
|
||||||
@@ -125,7 +123,6 @@ namespace MareSynchronos.Models
|
|||||||
VisorWeaponState = newWeaponOrVisorState;
|
VisorWeaponState = newWeaponOrVisorState;
|
||||||
hasChanges = true;
|
hasChanges = true;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
return hasChanges;
|
return hasChanges;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -124,12 +124,24 @@ namespace MareSynchronos.WebAPI
|
|||||||
private string ApiUri => _pluginConfiguration.ApiUri;
|
private string ApiUri => _pluginConfiguration.ApiUri;
|
||||||
public int OnlineUsers => SystemInfoDto.OnlineUsers;
|
public int OnlineUsers => SystemInfoDto.OnlineUsers;
|
||||||
|
|
||||||
public ServerState ServerState { get; private set; }
|
private ServerState _serverState;
|
||||||
|
public ServerState ServerState
|
||||||
|
{
|
||||||
|
get => _serverState;
|
||||||
|
private set
|
||||||
|
{
|
||||||
|
Logger.Debug($"New ServerState: {value}, prev ServerState: {_serverState}");
|
||||||
|
_serverState = value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public async Task CreateConnections()
|
public async Task CreateConnections()
|
||||||
{
|
{
|
||||||
|
await StopConnection(_connectionCancellationTokenSource.Token);
|
||||||
|
|
||||||
if (_pluginConfiguration.FullPause)
|
if (_pluginConfiguration.FullPause)
|
||||||
{
|
{
|
||||||
|
Logger.Info("Not recreating Connection, paused");
|
||||||
ServerState = ServerState.Disconnected;
|
ServerState = ServerState.Disconnected;
|
||||||
_connectionDto = null;
|
_connectionDto = null;
|
||||||
return;
|
return;
|
||||||
@@ -137,8 +149,6 @@ namespace MareSynchronos.WebAPI
|
|||||||
|
|
||||||
Logger.Info("Recreating Connection");
|
Logger.Info("Recreating Connection");
|
||||||
|
|
||||||
await StopConnection(_connectionCancellationTokenSource.Token);
|
|
||||||
|
|
||||||
_connectionCancellationTokenSource.Cancel();
|
_connectionCancellationTokenSource.Cancel();
|
||||||
_connectionCancellationTokenSource = new CancellationTokenSource();
|
_connectionCancellationTokenSource = new CancellationTokenSource();
|
||||||
var token = _connectionCancellationTokenSource.Token;
|
var token = _connectionCancellationTokenSource.Token;
|
||||||
@@ -298,9 +308,9 @@ namespace MareSynchronos.WebAPI
|
|||||||
CurrentUploads.Clear();
|
CurrentUploads.Clear();
|
||||||
CurrentDownloads.Clear();
|
CurrentDownloads.Clear();
|
||||||
_uploadCancellationTokenSource?.Cancel();
|
_uploadCancellationTokenSource?.Cancel();
|
||||||
Logger.Info("Connection closed");
|
|
||||||
Disconnected?.Invoke();
|
Disconnected?.Invoke();
|
||||||
ServerState = ServerState.Offline;
|
ServerState = ServerState.Offline;
|
||||||
|
Logger.Info("Connection closed");
|
||||||
return Task.CompletedTask;
|
return Task.CompletedTask;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -337,6 +347,14 @@ namespace MareSynchronos.WebAPI
|
|||||||
await _mareHub.DisposeAsync();
|
await _mareHub.DisposeAsync();
|
||||||
_mareHub = null;
|
_mareHub = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (ServerState != ServerState.Disconnected)
|
||||||
|
{
|
||||||
|
while (ServerState != ServerState.Offline)
|
||||||
|
{
|
||||||
|
await Task.Delay(16);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
2
Penumbra
2
Penumbra
Submodule Penumbra updated: cfeb20a18e...e66ca7c580
Reference in New Issue
Block a user