Update CutsceneService and ObjectManager from upstream

This commit is contained in:
RisaDev
2024-09-30 22:44:47 +03:00
parent 80d0ed4f07
commit 021f4c8724
2 changed files with 20 additions and 19 deletions

View File

@@ -1,4 +1,5 @@
using CustomizePlus.GameData.Hooks.Objects; using CustomizePlus.GameData.Hooks.Objects;
using Dalamud.Game.ClientState.Objects.Types;
using Dalamud.Plugin.Services; using Dalamud.Plugin.Services;
using FFXIVClientStructs.FFXIV.Client.Game.Character; using FFXIVClientStructs.FFXIV.Client.Game.Character;
using FFXIVClientStructs.FFXIV.Client.Game.Object; using FFXIVClientStructs.FFXIV.Client.Game.Object;
@@ -9,23 +10,23 @@ using System.Diagnostics;
namespace CustomizePlus.GameData.Services; namespace CustomizePlus.GameData.Services;
public class CutsceneService : IService, IDisposable public sealed class CutsceneService : IRequiredService, IDisposable
{ {
public const int CutsceneStartIdx = (int)ScreenActor.CutsceneStart; public const int CutsceneStartIdx = (int)ScreenActor.CutsceneStart;
public const int CutsceneEndIdx = (int)ScreenActor.CutsceneEnd; public const int CutsceneEndIdx = (int)ScreenActor.CutsceneEnd;
public const int CutsceneSlots = CutsceneEndIdx - CutsceneStartIdx; public const int CutsceneSlots = CutsceneEndIdx - CutsceneStartIdx;
private readonly IObjectTable _objects; private readonly ObjectManager _objects;
private readonly CopyCharacter _copyCharacter; private readonly CopyCharacter _copyCharacter;
private readonly CharacterDestructor _characterDestructor; private readonly CharacterDestructor _characterDestructor;
private readonly short[] _copiedCharacters = Enumerable.Repeat((short)-1, CutsceneSlots).ToArray(); private readonly short[] _copiedCharacters = Enumerable.Repeat((short)-1, CutsceneSlots).ToArray();
public IEnumerable<KeyValuePair<int, Dalamud.Game.ClientState.Objects.Types.IGameObject>> Actors public IEnumerable<KeyValuePair<int, IGameObject>> Actors
=> Enumerable.Range(CutsceneStartIdx, CutsceneSlots) => Enumerable.Range(CutsceneStartIdx, CutsceneSlots)
.Where(i => _objects[i] != null) .Where(i => _objects[i].Valid)
.Select(i => KeyValuePair.Create(i, this[i] ?? _objects[i]!)); .Select(i => KeyValuePair.Create(i, this[i] ?? _objects.GetDalamudObject(i)!));
public unsafe CutsceneService(IObjectTable objects, CopyCharacter copyCharacter, CharacterDestructor characterDestructor, public unsafe CutsceneService(ObjectManager objects, CopyCharacter copyCharacter, CharacterDestructor characterDestructor,
IClientState clientState) IClientState clientState)
{ {
_objects = objects; _objects = objects;
@@ -43,13 +44,13 @@ public class CutsceneService : IService, IDisposable
/// Does not check for valid input index. /// Does not check for valid input index.
/// Returns null if no connected actor is set or the actor does not exist anymore. /// Returns null if no connected actor is set or the actor does not exist anymore.
/// </summary> /// </summary>
public Dalamud.Game.ClientState.Objects.Types.IGameObject? this[int idx] private IGameObject? this[int idx]
{ {
get get
{ {
Debug.Assert(idx is >= CutsceneStartIdx and < CutsceneEndIdx); Debug.Assert(idx is >= CutsceneStartIdx and < CutsceneEndIdx);
idx = _copiedCharacters[idx - CutsceneStartIdx]; idx = _copiedCharacters[idx - CutsceneStartIdx];
return idx < 0 ? null : _objects[idx]; return idx < 0 ? null : _objects.GetDalamudObject(idx);
} }
} }
@@ -65,10 +66,10 @@ public class CutsceneService : IService, IDisposable
if (parentIdx is < -1 or >= CutsceneEndIdx) if (parentIdx is < -1 or >= CutsceneEndIdx)
return false; return false;
if (_objects.GetObjectAddress(copyIdx) == nint.Zero) if (!_objects[copyIdx].Valid)
return false; return false;
if (parentIdx != -1 && _objects.GetObjectAddress(parentIdx) == nint.Zero) if (parentIdx != -1 && !_objects[parentIdx].Valid)
return false; return false;
_copiedCharacters[copyIdx - CutsceneStartIdx] = (short)parentIdx; _copiedCharacters[copyIdx - CutsceneStartIdx] = (short)parentIdx;
@@ -100,9 +101,9 @@ public class CutsceneService : IService, IDisposable
{ {
// A hack to deal with GPose actors leaving and thus losing the link, we just set the home world instead. // A hack to deal with GPose actors leaving and thus losing the link, we just set the home world instead.
// I do not think this breaks anything? // I do not think this breaks anything?
var address = (GameObject*)_objects.GetObjectAddress(i + CutsceneStartIdx); var address = _objects[i + CutsceneStartIdx];
if (address != null && address->GetObjectKind() is ObjectKind.Pc) if (address.IsPlayer)
((Character*)address)->HomeWorld = character->HomeWorld; address.AsCharacter->HomeWorld = character->HomeWorld;
_copiedCharacters[i] = -1; _copiedCharacters[i] = -1;
} }
@@ -126,7 +127,7 @@ public class CutsceneService : IService, IDisposable
/// <summary> Try to recover GPose actors on reloads into a running game. </summary> /// <summary> Try to recover GPose actors on reloads into a running game. </summary>
/// <remarks> This is not 100% accurate due to world IDs, minions etc., but will be mostly sane. </remarks> /// <remarks> This is not 100% accurate due to world IDs, minions etc., but will be mostly sane. </remarks>
private unsafe void RecoverGPoseActors() private void RecoverGPoseActors()
{ {
Dictionary<ByteString, short>? actors = null; Dictionary<ByteString, short>? actors = null;
@@ -144,11 +145,11 @@ public class CutsceneService : IService, IDisposable
bool TryGetName(int idx, out ByteString name) bool TryGetName(int idx, out ByteString name)
{ {
name = ByteString.Empty; name = ByteString.Empty;
var address = (GameObject*)_objects.GetObjectAddress(idx); var address = _objects[idx];
if (address == null) if (!address.Valid)
return false; return false;
name = new ByteString(address->Name); name = address.Utf8Name;
return !name.IsEmpty; return !name.IsEmpty;
} }

View File

@@ -44,7 +44,7 @@ public class ObjectManager(
return false; return false;
_identifierUpdate = LastUpdate; _identifierUpdate = LastUpdate;
World = (ushort)(this[0].Valid ? this[0].HomeWorld : 0); World = (ushort)(Player.Valid ? Player.HomeWorld : 0);
_identifiers.Clear(); _identifiers.Clear();
_allWorldIdentifiers.Clear(); _allWorldIdentifiers.Clear();
_nonOwnedIdentifiers.Clear(); _nonOwnedIdentifiers.Clear();