Use ObjectManager, Actor and Model.

This commit is contained in:
Ottermandias 2024-03-19 22:52:20 +01:00
parent 5b9309a311
commit c8216b0acc
22 changed files with 240 additions and 325 deletions

View file

@ -1,9 +1,9 @@
using Dalamud.Plugin.Services;
using FFXIVClientStructs.FFXIV.Client.Game.Object;
using OtterGui.Services;
using Penumbra.Collections;
using Penumbra.CrashHandler.Buffers;
using Penumbra.GameData;
using Penumbra.GameData.Interop;
using Penumbra.Interop.PathResolving;
using Penumbra.Interop.Structs;
using Penumbra.Services;
@ -16,10 +16,10 @@ public sealed unsafe class LoadCharacterVfx : FastHook<LoadCharacterVfx.Delegate
{
private readonly GameState _state;
private readonly CollectionResolver _collectionResolver;
private readonly IObjectTable _objects;
private readonly ObjectManager _objects;
private readonly CrashHandlerService _crashHandler;
public LoadCharacterVfx(HookManager hooks, GameState state, CollectionResolver collectionResolver, IObjectTable objects,
public LoadCharacterVfx(HookManager hooks, GameState state, CollectionResolver collectionResolver, ObjectManager objects,
CrashHandlerService crashHandler)
{
_state = state;
@ -39,19 +39,19 @@ public sealed unsafe class LoadCharacterVfx : FastHook<LoadCharacterVfx.Delegate
{
var obj = vfxParams->GameObjectType switch
{
0 => _objects.SearchById(vfxParams->GameObjectId),
0 => _objects.ById(vfxParams->GameObjectId),
2 => _objects[(int)vfxParams->GameObjectId],
4 => GetOwnedObject(vfxParams->GameObjectId),
_ => null,
_ => Actor.Null,
};
newData = obj != null
newData = obj.Valid
? _collectionResolver.IdentifyCollection((GameObject*)obj.Address, true)
: ResolveData.Invalid;
}
var last = _state.SetAnimationData(newData);
_crashHandler.LogAnimation(newData.AssociatedGameObject, newData.ModCollection, AnimationInvocationType.LoadCharacterVfx);
var ret = Task.Result.Original(vfxPath, vfxParams, unk1, unk2, unk3, unk4);
var ret = Task.Result.Original(vfxPath, vfxParams, unk1, unk2, unk3, unk4);
Penumbra.Log.Excessive(
$"[Load Character VFX] Invoked with {new ByteString(vfxPath)}, 0x{vfxParams->GameObjectId:X}, {vfxParams->TargetCount}, {unk1}, {unk2}, {unk3}, {unk4} -> 0x{ret:X}.");
_state.RestoreAnimationData(last);
@ -59,13 +59,11 @@ public sealed unsafe class LoadCharacterVfx : FastHook<LoadCharacterVfx.Delegate
}
/// <summary> Search an object by its id, then get its minion/mount/ornament. </summary>
private Dalamud.Game.ClientState.Objects.Types.GameObject? GetOwnedObject(uint id)
private Actor GetOwnedObject(uint id)
{
var owner = _objects.SearchById(id);
if (owner == null)
return null;
var idx = ((GameObject*)owner.Address)->ObjectIndex;
return _objects[idx + 1];
var owner = _objects.ById(id);
return !owner.Valid
? Actor.Null
: _objects[owner.Index.Index + 1];
}
}

View file

@ -3,8 +3,8 @@ using Dalamud.Plugin.Services;
using FFXIVClientStructs.FFXIV.Client.Game.Object;
using OtterGui.Services;
using Penumbra.Collections;
using Penumbra.CrashHandler;
using Penumbra.GameData;
using Penumbra.GameData.Interop;
using Penumbra.Interop.PathResolving;
using Penumbra.Services;
@ -19,11 +19,11 @@ public sealed unsafe class LoadTimelineResources : FastHook<LoadTimelineResource
private readonly GameState _state;
private readonly CollectionResolver _collectionResolver;
private readonly ICondition _conditions;
private readonly IObjectTable _objects;
private readonly ObjectManager _objects;
private readonly CrashHandlerService _crashHandler;
public LoadTimelineResources(HookManager hooks, GameState state, CollectionResolver collectionResolver, ICondition conditions,
IObjectTable objects, CrashHandlerService crashHandler)
ObjectManager objects, CrashHandlerService crashHandler)
{
_state = state;
_collectionResolver = collectionResolver;
@ -56,7 +56,7 @@ public sealed unsafe class LoadTimelineResources : FastHook<LoadTimelineResource
}
/// <summary> Use timelines vfuncs to obtain the associated game object. </summary>
public static ResolveData GetDataFromTimeline(IObjectTable objects, CollectionResolver resolver, nint timeline)
public static ResolveData GetDataFromTimeline(ObjectManager objects, CollectionResolver resolver, nint timeline)
{
try
{
@ -64,10 +64,10 @@ public sealed unsafe class LoadTimelineResources : FastHook<LoadTimelineResource
{
var getGameObjectIdx = ((delegate* unmanaged<nint, int>**)timeline)[0][Offsets.GetGameObjectIdxVfunc];
var idx = getGameObjectIdx(timeline);
if (idx >= 0 && idx < objects.Length)
if (idx >= 0 && idx < objects.Count)
{
var obj = (GameObject*)objects.GetObjectAddress(idx);
return obj != null ? resolver.IdentifyCollection(obj, true) : ResolveData.Invalid;
var obj = objects[idx];
return obj.Valid ? resolver.IdentifyCollection(obj.AsObject, true) : ResolveData.Invalid;
}
}
}

View file

@ -1,7 +1,7 @@
using Dalamud.Plugin.Services;
using OtterGui.Services;
using Penumbra.CrashHandler.Buffers;
using Penumbra.GameData;
using Penumbra.GameData.Interop;
using Penumbra.Interop.PathResolving;
using Penumbra.Interop.Structs;
using Penumbra.Services;
@ -13,10 +13,10 @@ public sealed unsafe class ScheduleClipUpdate : FastHook<ScheduleClipUpdate.Dele
{
private readonly GameState _state;
private readonly CollectionResolver _collectionResolver;
private readonly IObjectTable _objects;
private readonly ObjectManager _objects;
private readonly CrashHandlerService _crashHandler;
public ScheduleClipUpdate(HookManager hooks, GameState state, CollectionResolver collectionResolver, IObjectTable objects,
public ScheduleClipUpdate(HookManager hooks, GameState state, CollectionResolver collectionResolver, ObjectManager objects,
CrashHandlerService crashHandler)
{
_state = state;

View file

@ -1,8 +1,7 @@
using Dalamud.Plugin.Services;
using FFXIVClientStructs.FFXIV.Client.Game.Object;
using OtterGui.Services;
using Penumbra.CrashHandler.Buffers;
using Penumbra.GameData;
using Penumbra.GameData.Interop;
using Penumbra.Interop.PathResolving;
using Penumbra.Services;
@ -13,10 +12,10 @@ public sealed unsafe class SomePapLoad : FastHook<SomePapLoad.Delegate>
{
private readonly GameState _state;
private readonly CollectionResolver _collectionResolver;
private readonly IObjectTable _objects;
private readonly ObjectManager _objects;
private readonly CrashHandlerService _crashHandler;
public SomePapLoad(HookManager hooks, GameState state, CollectionResolver collectionResolver, IObjectTable objects,
public SomePapLoad(HookManager hooks, GameState state, CollectionResolver collectionResolver, ObjectManager objects,
CrashHandlerService crashHandler)
{
_state = state;
@ -36,9 +35,9 @@ public sealed unsafe class SomePapLoad : FastHook<SomePapLoad.Delegate>
if (timelinePtr != nint.Zero)
{
var actorIdx = (int)(*(*(ulong**)timelinePtr + 1) >> 3);
if (actorIdx >= 0 && actorIdx < _objects.Length)
if (actorIdx >= 0 && actorIdx < _objects.Count)
{
var newData = _collectionResolver.IdentifyCollection((GameObject*)_objects.GetObjectAddress(actorIdx), true);
var newData = _collectionResolver.IdentifyCollection(_objects[actorIdx].AsObject, true);
var last = _state.SetAnimationData(newData);
_crashHandler.LogAnimation(newData.AssociatedGameObject, newData.ModCollection, AnimationInvocationType.PapLoad);
Task.Result.Original(a1, a2, a3, a4);