M Local/NosSmooth.LocalBinding/ExternalNosBrowser.cs => Local/NosSmooth.LocalBinding/ExternalNosBrowser.cs +26 -1
@@ 21,8 21,10 @@ public class ExternalNosBrowser
{
private readonly PlayerManagerOptions _playerManagerOptions;
private readonly SceneManagerOptions _sceneManagerOptions;
+ private readonly PetManagerOptions _petManagerOptions;
private PlayerManager? _playerManager;
private SceneManager? _sceneManager;
+ private PetManagerList? _petManagerList;
/// <summary>
/// Initializes a new instance of the <see cref="ExternalNosBrowser"/> class.
@@ 30,15 32,18 @@ public class ExternalNosBrowser
/// <param name="process">The process to browse.</param>
/// <param name="playerManagerOptions">The options for obtaining player manager.</param>
/// <param name="sceneManagerOptions">The scene manager options.</param>
+ /// <param name="petManagerOptions">The pet manager options.</param>
public ExternalNosBrowser
(
Process process,
PlayerManagerOptions playerManagerOptions,
- SceneManagerOptions sceneManagerOptions
+ SceneManagerOptions sceneManagerOptions,
+ PetManagerOptions petManagerOptions
)
{
_playerManagerOptions = playerManagerOptions;
_sceneManagerOptions = sceneManagerOptions;
+ _petManagerOptions = petManagerOptions;
Process = process;
Memory = new ExternalMemory(process);
Scanner = new Scanner(process, process.MainModule);
@@ 98,4 103,24 @@ public class ExternalNosBrowser
return _sceneManager;
}
+
+ /// <summary>
+ /// Get the pet manager list.
+ /// </summary>
+ /// <returns>The player manager or an error.</returns>
+ public Result<PetManagerList> GetPetManagerList()
+ {
+ if (_petManagerList is null)
+ {
+ var petManagerResult = PetManagerList.Create(this, _petManagerOptions);
+ if (!petManagerResult.IsSuccess)
+ {
+ return petManagerResult;
+ }
+
+ _petManagerList = petManagerResult.Entity;
+ }
+
+ return _petManagerList;
+ }
}=
\ No newline at end of file
M Local/NosSmooth.LocalBinding/NosBindingManager.cs => Local/NosSmooth.LocalBinding/NosBindingManager.cs +9 -2
@@ 38,13 38,15 @@ public class NosBindingManager : IDisposable
/// <param name="sceneManagerBindingOptions">The scene manager binding options.</param>
/// <param name="playerManagerOptions">The player manager options.</param>
/// <param name="sceneManagerOptions">The scene manager options.</param>
+ /// <param name="petManagerOptions">The pet manager options.</param>
public NosBindingManager
(
IOptions<CharacterBindingOptions> characterBindingOptions,
IOptions<NetworkBindingOptions> networkBindingOptions,
IOptions<SceneManagerBindingOptions> sceneManagerBindingOptions,
IOptions<PlayerManagerOptions> playerManagerOptions,
- IOptions<SceneManagerOptions> sceneManagerOptions
+ IOptions<SceneManagerOptions> sceneManagerOptions,
+ IOptions<PetManagerOptions> petManagerOptions
)
{
Hooks = new ReloadedHooks();
@@ 54,7 56,12 @@ public class NosBindingManager : IDisposable
_networkBindingOptions = networkBindingOptions.Value;
_sceneManagerBindingOptions = sceneManagerBindingOptions.Value;
_nosBrowser = new ExternalNosBrowser
- (Process.GetCurrentProcess(), playerManagerOptions.Value, sceneManagerOptions.Value);
+ (
+ Process.GetCurrentProcess(),
+ playerManagerOptions.Value,
+ sceneManagerOptions.Value,
+ petManagerOptions.Value
+ );
}
/// <summary>
A Local/NosSmooth.LocalBinding/Options/PetManagerOptions.cs => Local/NosSmooth.LocalBinding/Options/PetManagerOptions.cs +27 -0
@@ 0,0 1,27 @@
+//
+// PetManagerOptions.cs
+//
+// Copyright (c) František Boháček. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+
+using NosSmooth.LocalBinding.Objects;
+
+namespace NosSmooth.LocalBinding.Options;
+
+/// <summary>
+/// Options for <see cref="PetManagerBinding"/>.
+/// </summary>
+public class PetManagerOptions
+{
+ /// <summary>
+ /// Gets or sets the pattern to find static pet manager list address at.
+ /// </summary>
+ public string PetManagerListPattern { get; set; }
+ = "00 ff 70 00 ?? ?? ?? ?? 10 90";
+
+ /// <summary>
+ /// Gets or sets the offsets to find the pet manager list at from the static address.
+ /// </summary>
+ public int[] PetManagerListOffsets { get; set; }
+ = { 4, 8, 0x180, 0x18, 0x1C, 0x54 };
+}<
\ No newline at end of file
A Local/NosSmooth.LocalBinding/Structs/MapNpcObj.cs => Local/NosSmooth.LocalBinding/Structs/MapNpcObj.cs +25 -0
@@ 0,0 1,25 @@
+//
+// MapNpcObj.cs
+//
+// Copyright (c) František Boháček. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+
+using Reloaded.Memory.Sources;
+
+namespace NosSmooth.LocalBinding.Structs;
+
+/// <summary>
+/// Npc NosTale object.
+/// </summary>
+public class MapNpcObj : MapBaseObj
+{
+ /// <summary>
+ /// Initializes a new instance of the <see cref="MapNpcObj"/> class.
+ /// </summary>
+ /// <param name="memory">The memory.</param>
+ /// <param name="mapObjPointer">The pointer to the object.</param>
+ public MapNpcObj(IMemory memory, IntPtr mapObjPointer)
+ : base(memory, mapObjPointer)
+ {
+ }
+}<
\ No newline at end of file
A Local/NosSmooth.LocalBinding/Structs/PetManager.cs => Local/NosSmooth.LocalBinding/Structs/PetManager.cs +49 -0
@@ 0,0 1,49 @@
+//
+// PetManager.cs
+//
+// Copyright (c) František Boháček. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+
+using NosSmooth.LocalBinding.Errors;
+using NosSmooth.LocalBinding.Options;
+using Reloaded.Memory.Sources;
+using Remora.Results;
+
+namespace NosSmooth.LocalBinding.Structs;
+
+/// <summary>
+/// NosTale pet manager.
+/// </summary>
+public class PetManager : ControlManager
+{
+ private readonly IMemory _memory;
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="PetManager"/> class.
+ /// </summary>
+ /// <param name="memory">The memory.</param>
+ /// <param name="petManagerAddress">The pet manager address.</param>
+ public PetManager(IMemory memory, IntPtr petManagerAddress)
+ : base(memory)
+ {
+ _memory = memory;
+ Address = petManagerAddress;
+ }
+
+ /// <summary>
+ /// Gets the address of the pet manager.
+ /// </summary>
+ public override IntPtr Address { get; }
+
+ /// <summary>
+ /// Gets the player object.
+ /// </summary>
+ public MapNpcObj Pet
+ {
+ get
+ {
+ _memory.SafeRead(Address + 0x20, out int playerAddress);
+ return new MapNpcObj(_memory, (IntPtr)playerAddress);
+ }
+ }
+}<
\ No newline at end of file
A Local/NosSmooth.LocalBinding/Structs/PetManagerList.cs => Local/NosSmooth.LocalBinding/Structs/PetManagerList.cs +116 -0
@@ 0,0 1,116 @@
+//
+// PetManagerList.cs
+//
+// Copyright (c) František Boháček. All rights reserved.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
+
+using NosSmooth.LocalBinding.Errors;
+using NosSmooth.LocalBinding.Extensions;
+using NosSmooth.LocalBinding.Options;
+using Reloaded.Memory.Sources;
+using Remora.Results;
+
+namespace NosSmooth.LocalBinding.Structs;
+
+/// <summary>
+/// NosTale list of <see cref="PetManager"/>.
+/// </summary>
+public class PetManagerList
+{
+ /// <summary>
+ /// Create <see cref="PlayerManager"/> instance.
+ /// </summary>
+ /// <param name="nosBrowser">The NosTale process browser.</param>
+ /// <param name="options">The options.</param>
+ /// <returns>The player manager or an error.</returns>
+ public static Result<PetManagerList> Create(ExternalNosBrowser nosBrowser, PetManagerOptions options)
+ {
+ var characterObjectAddress = nosBrowser.Scanner.CompiledFindPattern(options.PetManagerListPattern);
+ if (!characterObjectAddress.Found)
+ {
+ return new BindingNotFoundError(options.PetManagerListPattern, "PetManagerList");
+ }
+
+ if (nosBrowser.Process.MainModule is null)
+ {
+ return new NotFoundError("Cannot find the main module of the target process.");
+ }
+
+ int staticManagerAddress = (int)nosBrowser.Process.MainModule.BaseAddress + characterObjectAddress.Offset;
+ return new PetManagerList(nosBrowser.Memory, staticManagerAddress, options.PetManagerListOffsets);
+ }
+
+ private readonly IMemory _memory;
+ private readonly int _staticPetManagerListAddress;
+ private readonly int[] _staticPetManagerOffsets;
+
+ /// <summary>
+ /// Initializes a new instance of the <see cref="PetManagerList"/> class.
+ /// </summary>
+ /// <param name="memory">The memory.</param>
+ /// <param name="staticPetManagerListAddress">The static pet manager address.</param>
+ /// <param name="staticPetManagerOffsets">The offsets to follow to the pet manager list address.</param>
+ public PetManagerList(IMemory memory, int staticPetManagerListAddress, int[] staticPetManagerOffsets)
+ {
+ _memory = memory;
+ _staticPetManagerListAddress = staticPetManagerListAddress;
+ _staticPetManagerOffsets = staticPetManagerOffsets;
+ }
+
+ /// <summary>
+ /// Gets the address of the pet manager.
+ /// </summary>
+ /// <returns>An address to the pet manager list.</returns>
+ public IntPtr Address => _memory.FollowStaticAddressOffsets(_staticPetManagerListAddress, _staticPetManagerOffsets);
+
+ /// <summary>
+ /// Gets the length of the array.
+ /// </summary>
+ public int Length
+ {
+ get
+ {
+ _memory.SafeRead(Address + 0x08, out int length);
+ return length;
+ }
+ }
+
+ private IntPtr List
+ {
+ get
+ {
+ _memory.SafeRead(Address + 0x04, out int listPointer);
+ return (IntPtr)listPointer;
+ }
+ }
+
+ /// <summary>
+ /// Get the first pet.
+ /// </summary>
+ /// <returns>First pet, if exists.</returns>
+ public MapNpcObj? GetFirst()
+ {
+ if (Length == 0)
+ {
+ return null;
+ }
+
+ _memory.SafeRead(List, out int firstAddress);
+ return new MapNpcObj(_memory, (IntPtr)firstAddress);
+ }
+
+ /// <summary>
+ /// Get the second pet.
+ /// </summary>
+ /// <returns>Second pet, if exists.</returns>
+ public MapNpcObj? GetSecond()
+ {
+ if (Length < 2)
+ {
+ return null;
+ }
+
+ _memory.SafeRead(List + 0x04, out int secondAddress);
+ return new MapNpcObj(_memory, (IntPtr)secondAddress);
+ }
+}<
\ No newline at end of file
M Local/NosSmooth.LocalBinding/Structs/SceneManager.cs => Local/NosSmooth.LocalBinding/Structs/SceneManager.cs +1 -1
@@ 36,7 36,7 @@ public class SceneManager
return new NotFoundError("Cannot find the main module of the target process.");
}
- int staticManagerAddress = (int)nosBrowser.Process.MainModule.BaseAddress + characterObjectAddress.Offset + 1;
+ int staticManagerAddress = (int)nosBrowser.Process.MainModule.BaseAddress + characterObjectAddress.Offset;
return new SceneManager(nosBrowser.Memory, staticManagerAddress, options.SceneManagerOffsets);
}