Fix and add features #3

Merged
Terkoiz merged 3 commits from CWX/Freecam:master into master 2023-02-21 12:04:57 -05:00
10 changed files with 172 additions and 258 deletions

4
.gitignore vendored

@ -241,6 +241,10 @@ ClientBin/
*.pfx
*.publishsettings
orleans.codegen.cs
.idea
Freecam.sln.DotSettings.user
Project/.idea/
Project/Shared/*
# Including strong name files can present a security risk
# (https://github.com/github/gitignore/pull/2483#issue-259490424)

@ -0,0 +1,16 @@

Microsoft Visual Studio Solution File, Format Version 12.00
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Terkoiz.Freecam", "Terkoiz.Freecam\Terkoiz.Freecam.csproj", "{BC26F21D-2987-4504-BBE6-0867001DFEB3}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{BC26F21D-2987-4504-BBE6-0867001DFEB3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{BC26F21D-2987-4504-BBE6-0867001DFEB3}.Debug|Any CPU.Build.0 = Debug|Any CPU
{BC26F21D-2987-4504-BBE6-0867001DFEB3}.Release|Any CPU.ActiveCfg = Release|Any CPU
{BC26F21D-2987-4504-BBE6-0867001DFEB3}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
EndGlobal

@ -1,4 +1,4 @@
using JetBrains.Annotations;
using JetBrains.Annotations;
using UnityEngine;
namespace Terkoiz.Freecam
@ -13,7 +13,7 @@ namespace Terkoiz.Freecam
public class Freecam : MonoBehaviour
{
public bool IsActive = false;
[UsedImplicitly]
public void Update()
{
@ -27,44 +27,44 @@ namespace Terkoiz.Freecam
if (Input.GetKey(KeyCode.A) || Input.GetKey(KeyCode.LeftArrow))
{
transform.position += (-transform.right * movementSpeed * Time.deltaTime);
transform.position += (-transform.right * (movementSpeed * Time.deltaTime));
}
if (Input.GetKey(KeyCode.D) || Input.GetKey(KeyCode.RightArrow))
{
transform.position += (transform.right * movementSpeed * Time.deltaTime);
transform.position += (transform.right * (movementSpeed * Time.deltaTime));
}
if (Input.GetKey(KeyCode.W) || Input.GetKey(KeyCode.UpArrow))
{
transform.position += (transform.forward * movementSpeed * Time.deltaTime);
transform.position += (transform.forward * (movementSpeed * Time.deltaTime));
}
if (Input.GetKey(KeyCode.S) || Input.GetKey(KeyCode.DownArrow))
{
transform.position += (-transform.forward * movementSpeed * Time.deltaTime);
transform.position += (-transform.forward * (movementSpeed * Time.deltaTime));
}
if (FreecamPlugin.CameraHeightMovement.Value)
{
if (Input.GetKey(KeyCode.Q))
{
transform.position += (transform.up * movementSpeed * Time.deltaTime);
transform.position += (transform.up * (movementSpeed * Time.deltaTime));
}
if (Input.GetKey(KeyCode.E))
{
transform.position += (-transform.up * movementSpeed * Time.deltaTime);
transform.position += (-transform.up * (movementSpeed * Time.deltaTime));
}
if (Input.GetKey(KeyCode.R) || Input.GetKey(KeyCode.PageUp))
{
transform.position += (Vector3.up * movementSpeed * Time.deltaTime);
transform.position += (Vector3.up * (movementSpeed * Time.deltaTime));
}
if (Input.GetKey(KeyCode.F) || Input.GetKey(KeyCode.PageDown))
{
transform.position += (-Vector3.up * movementSpeed * Time.deltaTime);
transform.position += (-Vector3.up * (movementSpeed * Time.deltaTime));
}
}
@ -78,9 +78,15 @@ namespace Terkoiz.Freecam
if (axis != 0)
{
var zoomSensitivity = fastMode ? FreecamPlugin.CameraFastZoomSpeed.Value : FreecamPlugin.CameraZoomSpeed.Value;
transform.position += transform.forward * axis * zoomSensitivity;
transform.position += transform.forward * (axis * zoomSensitivity);
}
}
}
[UsedImplicitly]
private void OnDestroy()
{
Destroy(this);
}
}
}

@ -1,11 +1,9 @@
using System.Reflection;
using Comfort.Common;
using EFT;
using EFT.CameraControl;
using EFT.UI;
using HarmonyLib;
using JetBrains.Annotations;
using MonoMod.RuntimeDetour;
using UnityEngine;
namespace Terkoiz.Freecam
@ -17,11 +15,9 @@ namespace Terkoiz.Freecam
private BattleUIScreen _playerUi;
private bool _uiHidden;
private bool _fallDamageToggle = false;
private MethodInfo _playerMoveMethod;
private MethodInfo _playerRotateMethod;
private Detour _moveDetour;
private Detour _rotateDetour;
private GamePlayerOwner _gamePlayerOwner;
private Vector3? _lastPosition;
private Quaternion? _lastRotation;
@ -34,21 +30,22 @@ namespace Terkoiz.Freecam
[UsedImplicitly]
public void Start()
{
// We locate and get the MethodInfo for the Move method that we will later detour to prevent the player from moving during Freecam
_playerMoveMethod = typeof(Player).GetMethod("Move");
if (_playerMoveMethod == null)
{
FreecamPlugin.Logger.LogError("Failed to locate the Player.Move method!");
}
// Find Main Camera
_mainCamera = GameObject.Find("FPS Camera");
if (_mainCamera == null)
FreecamPlugin.Logger.LogError("Failed to locate main camera");
// Same deal here, but for player rotation
_playerRotateMethod = typeof(Player).GetMethod("Rotate");
if (_playerRotateMethod == null)
{
FreecamPlugin.Logger.LogError("Failed to locate the Player.Rotate method!");
}
// Add Freecam script to main camera in scene
_freeCamScript = _mainCamera.AddComponent<Freecam>();
if (_freeCamScript == null)
FreecamPlugin.Logger.LogError("Failed to add Freecam script to Camera");
// Get GamePlayerOwner component
_gamePlayerOwner = GetLocalPlayerFromWorld().GetComponentInChildren<GamePlayerOwner>();
if (_gamePlayerOwner == null)
FreecamPlugin.Logger.LogError("Failed to locate GamePlayerOwner");
}
[UsedImplicitly]
public void Update()
{
@ -66,6 +63,29 @@ namespace Terkoiz.Freecam
{
MovePlayerToCamera();
}
if (_fallDamageToggle != FreecamPlugin.FallDamageToggle.Value)
{
_fallDamageToggle = ToggleFallDamage(FreecamPlugin.FallDamageToggle.Value);
}
}
private bool ToggleFallDamage(bool config)
{
var localPlayer = GetLocalPlayerFromWorld();
if (localPlayer == null)
return false;
// Set Safe fall height to 99999
if (config)
{
localPlayer.ActiveHealthController.FallSafeHeight = 99999;
return true;
}
// Set Safe fall height to 3
localPlayer.ActiveHealthController.FallSafeHeight = 3;
return false;
}
/// <summary>
@ -76,29 +96,7 @@ namespace Terkoiz.Freecam
// Get our own Player instance. Null means we're not in a raid
var localPlayer = GetLocalPlayerFromWorld();
if (localPlayer == null)
{
return;
}
// If we don't have the main camera object cached, go look for it in the scene
if (_mainCamera == null)
{
// Finding a GameObject by name directly is apparently better than searching for objects of a type.
// 'FPS Camera' is our main camera instance - so we just grab that
_mainCamera = GameObject.Find("FPS Camera");
if (_mainCamera == null)
{
FreecamPlugin.Logger.LogError("Failed to locate main camera");
return;
}
}
// Create the Freecam script and attach it to the main camera
if (_freeCamScript == null)
{
ClearDetours();
_freeCamScript = _mainCamera.AddComponent<Freecam>();
}
if (!_freeCamScript.IsActive)
{
@ -117,15 +115,7 @@ namespace Terkoiz.Freecam
{
var localPlayer = GetLocalPlayerFromWorld();
if (localPlayer == null)
{
return;
}
// If we don't have the main camera cached, it means we have yet to enter Freecam mode and there is nowhere to teleport to
if (_mainCamera == null)
{
return;
}
// Move the player to the camera's current position and switch to First Person mode
if (_freeCamScript.IsActive)
@ -133,6 +123,7 @@ namespace Terkoiz.Freecam
// We grab the camera's position, but we subtract a bit off the Y axis, because the players coordinate origin is at the feet
var position = new Vector3(_mainCamera.transform.position.x, _mainCamera.transform.position.y - 1.8f, _mainCamera.transform.position.z);
localPlayer.gameObject.transform.SetPositionAndRotation(position, Quaternion.Euler(0, _mainCamera.transform.rotation.y, 0));
// localPlayer.gameObject.transform.SetPositionAndRotation(position, _mainCamera.transform.rotation);
SetPlayerToFirstPersonMode(localPlayer);
}
@ -145,9 +136,7 @@ namespace Terkoiz.Freecam
{
// Check if we're currently in a raid
if (GetLocalPlayerFromWorld() == null)
{
return;
}
// If we don't have the UI Component cached, go look for it in the scene
if (_playerUi == null)
@ -194,17 +183,8 @@ namespace Terkoiz.Freecam
FreecamPlugin.Logger.LogError("Failed to get the PlayerBody field");
}
// Detour the Player.Move method into an empty one, preventing the character from moving during Freecam mode
if (_playerMoveMethod != null)
{
_moveDetour = new Detour(_playerMoveMethod, typeof(FreecamController).GetMethod(nameof(DisabledMove)));
}
// Same deal here, but for player rotation
if (_playerRotateMethod != null)
{
_rotateDetour = new Detour(_playerRotateMethod, typeof(FreecamController).GetMethod(nameof(DisabledRotate)));
}
// Instead of Detouring, just turn off _gamePlayerOwner which takes the input
_gamePlayerOwner.enabled = false;
if (FreecamPlugin.CameraRememberLastPosition.Value && _lastPosition != null && _lastRotation != null)
{
@ -228,8 +208,9 @@ namespace Terkoiz.Freecam
_lastPosition = _mainCamera.transform.position;
_lastRotation = _mainCamera.transform.rotation;
}
ClearDetours();
// re-enable _gamePlayerOwner
_gamePlayerOwner.enabled = true;
localPlayer.PointOfView = EPointOfView.FirstPerson;
}
@ -242,56 +223,19 @@ namespace Terkoiz.Freecam
{
// If the GameWorld instance is null or has no RegisteredPlayers, it most likely means we're not in a raid
var gameWorld = Singleton<GameWorld>.Instance;
if (gameWorld == null || gameWorld.RegisteredPlayers == null)
{
if (gameWorld == null || gameWorld.MainPlayer == null)
Terkoiz marked this conversation as resolved Outdated

Same comment as above

Same comment as above
Outdated
Review

removed as i didnt think it was needed

removed as i didnt think it was needed
return null;
}
// One of the RegisteredPlayers will have the IsYourPlayer flag set, which will be our own Player instance
return gameWorld.RegisteredPlayers.Find(p => p.IsYourPlayer);
return gameWorld.MainPlayer;
}
[UsedImplicitly]
public void OnDestroy()
{
_freeCamScript.IsActive = false;
// Making sure no stray Detours are left
ClearDetours();
_lastPosition = null;
_lastRotation = null;
}
public void ClearDetours()
{
if (_moveDetour != null)
{
_moveDetour.Dispose();
_moveDetour = null;
}
if (_rotateDetour != null)
{
_rotateDetour.Dispose();
_rotateDetour = null;
}
}
/// <summary>
/// An empty method that's used to detour the player Move method, preventing movement during Freecam mode
/// </summary>
[UsedImplicitly]
public static void DisabledMove(Player self, Vector2 direction)
{
}
/// <summary>
/// An empty method that's used to detour the player Rotate method, preventing rotation during Freecam mode
/// </summary>
[UsedImplicitly]
public static void DisabledRotate(Player self, Vector2 deltaRotation, bool ignoreClamp = false)
private void OnDestroy()
{
// Destroy FreeCamScript before FreeCamController if exists
Destroy(_freeCamScript);
Destroy(this);
}
}
}

@ -0,0 +1,27 @@
using System.Reflection;
using Aki.Reflection.Patching;
using Comfort.Common;
using EFT;
namespace Terkoiz.Freecam
{
public class FreecamPatch : ModulePatch
{
protected override MethodBase GetTargetMethod()
{
return typeof(GameWorld).GetMethod("OnGameStarted", BindingFlags.Public | BindingFlags.Instance);
}
[PatchPostfix]
public static void PatchPostFix()
{
var gameworld = Singleton<GameWorld>.Instance;
if (gameworld == null)
return;
// Add FreeCamController to GameWorld GameObject
gameworld.gameObject.AddComponent<FreecamController>();
Terkoiz marked this conversation as resolved Outdated

Sam says:

If you want multiversion compatibility, you shouldn't use GetOrAddComponent as this is eft GClassXX extension method, which means compiler will transfer it into GClass call that will change at some point and the mod will need to be recompiled with changed assembly-csharp in references

Sam says: > If you want multiversion compatibility, you shouldn't use GetOrAddComponent as this is eft GClassXX extension method, which means compiler will transfer it into GClass call that will change at some point and the mod will need to be recompiled with changed assembly-csharp in references
Outdated
Review

changed to gameworld.GameObject.AddComponent instead

changed to gameworld.GameObject.AddComponent instead
}
}
}

@ -3,22 +3,22 @@ using BepInEx.Configuration;
using BepInEx.Logging;
using JetBrains.Annotations;
using UnityEngine;
using KeyboardShortcut = BepInEx.Configuration.KeyboardShortcut;
namespace Terkoiz.Freecam
{
[BepInPlugin("com.terkoiz.freecam", "Terkoiz.Freecam", "1.2.0")]
[BepInPlugin("com.terkoiz.freecam", "Terkoiz.Freecam", "1.3.0")]
public class FreecamPlugin : BaseUnityPlugin
{
internal new static ManualLogSource Logger { get; private set; }
private static GameObject HookObject;
// Keyboard shortcut config entries
private const string KeybindSectionName = "Keybinds";
internal static ConfigEntry<KeyboardShortcut> ToggleFreecamMode;
internal static ConfigEntry<KeyboardShortcut> TeleportToCamera;
internal static ConfigEntry<KeyboardShortcut> ToggleUi;
// Camera settings config entries
private const string CameraSettingsSectionName = "CameraSettings";
internal static ConfigEntry<float> CameraMoveSpeed;
@ -31,19 +31,15 @@ namespace Terkoiz.Freecam
internal static ConfigEntry<bool> CameraHeightMovement;
internal static ConfigEntry<bool> CameraMousewheelZoom;
internal static ConfigEntry<bool> CameraRememberLastPosition;
// TODO: Hook into camera OnDestroy to run the OnDestroy from FreecamController
public static ConfigEntry<bool> FallDamageToggle;
[UsedImplicitly]
internal void Start()
{
new FreecamPatch().Enable();
Logger = base.Logger;
InitConfiguration();
HookObject = new GameObject();
HookObject.AddComponent<FreecamController>();
DontDestroyOnLoad(HookObject);
}
private void InitConfiguration()
@ -124,6 +120,12 @@ namespace Terkoiz.Freecam
"CameraRememberLastPosition",
false,
"If enabled, returning to Freecam mode will put the camera to it's last position which was saved when exiting Freecam mode.");
FallDamageToggle = Config.Bind(
TogglesSectionName,
"FallHeightToggle",
Terkoiz marked this conversation as resolved
Review

Change the description to be more consistent with others, ex: If enabled, will disable all fall damage for the player.

Change the description to be more consistent with others, ex: `If enabled, will disable all fall damage for the player.`
Review

done

done
true,
"If enabled, will disable all fall damage for the player.");
}
}
}

@ -1,4 +1,4 @@
using System.Reflection;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
@ -33,4 +33,4 @@ using System.Runtime.InteropServices;
// by using the '*' as shown below:
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

@ -1,109 +1,44 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{BE2DE623-48FF-4807-9696-167A17787718}</ProjectGuid>
<OutputType>Library</OutputType>
<AppDesignerFolder>Properties</AppDesignerFolder>
<RootNamespace>Terkoiz.Freecam</RootNamespace>
<AssemblyName>Terkoiz.Freecam</AssemblyName>
<TargetFrameworkVersion>v4.7.2</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<Deterministic>true</Deterministic>
<TargetFrameworkProfile />
<NuGetPackageImportStamp>
</NuGetPackageImportStamp>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup>
<SignAssembly>false</SignAssembly>
</PropertyGroup>
<PropertyGroup>
<AssemblyOriginatorKeyFile>
</AssemblyOriginatorKeyFile>
</PropertyGroup>
<ItemGroup>
<Reference Include="0Harmony, Version=2.7.0.0, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\HarmonyX.2.7.0\lib\net45\0Harmony.dll</HintPath>
</Reference>
<Reference Include="Assembly-CSharp">
<HintPath>..\Shared\Hollowed\Assembly-CSharp.dll</HintPath>
</Reference>
<Reference Include="BepInEx, Version=5.4.19.0, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\BepInEx.BaseLib.5.4.19\lib\net35\BepInEx.dll</HintPath>
</Reference>
<Reference Include="Comfort">
<HintPath>..\Shared\Managed\Comfort.dll</HintPath>
</Reference>
<Reference Include="ItemComponent.Types">
<HintPath>..\Shared\Managed\ItemComponent.Types.dll</HintPath>
</Reference>
<Reference Include="Mono.Cecil, Version=0.11.4.0, Culture=neutral, PublicKeyToken=50cebf1cceb9d05e, processorArchitecture=MSIL">
<HintPath>..\packages\Mono.Cecil.0.11.4\lib\net40\Mono.Cecil.dll</HintPath>
</Reference>
<Reference Include="Mono.Cecil.Mdb, Version=0.11.4.0, Culture=neutral, PublicKeyToken=50cebf1cceb9d05e, processorArchitecture=MSIL">
<HintPath>..\packages\Mono.Cecil.0.11.4\lib\net40\Mono.Cecil.Mdb.dll</HintPath>
</Reference>
<Reference Include="Mono.Cecil.Pdb, Version=0.11.4.0, Culture=neutral, PublicKeyToken=50cebf1cceb9d05e, processorArchitecture=MSIL">
<HintPath>..\packages\Mono.Cecil.0.11.4\lib\net40\Mono.Cecil.Pdb.dll</HintPath>
</Reference>
<Reference Include="Mono.Cecil.Rocks, Version=0.11.4.0, Culture=neutral, PublicKeyToken=50cebf1cceb9d05e, processorArchitecture=MSIL">
<HintPath>..\packages\Mono.Cecil.0.11.4\lib\net40\Mono.Cecil.Rocks.dll</HintPath>
</Reference>
<Reference Include="MonoMod.RuntimeDetour, Version=21.12.13.1, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\MonoMod.RuntimeDetour.21.12.13.1\lib\net452\MonoMod.RuntimeDetour.dll</HintPath>
</Reference>
<Reference Include="MonoMod.Utils, Version=21.12.13.1, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\MonoMod.Utils.21.12.13.1\lib\net452\MonoMod.Utils.dll</HintPath>
</Reference>
<Reference Include="System" />
<Reference Include="UnityEngine">
<HintPath>..\Shared\Managed\UnityEngine.dll</HintPath>
</Reference>
<Reference Include="UnityEngine.CoreModule">
<HintPath>..\Shared\Managed\UnityEngine.CoreModule.dll</HintPath>
</Reference>
<Reference Include="UnityEngine.InputLegacyModule">
<HintPath>..\Shared\Managed\UnityEngine.InputLegacyModule.dll</HintPath>
</Reference>
<Reference Include="UnityEngine.UIModule">
<HintPath>..\Shared\Managed\UnityEngine.UIModule.dll</HintPath>
</Reference>
</ItemGroup>
<ItemGroup>
<Compile Include="Freecam.cs" />
<Compile Include="FreecamController.cs" />
<Compile Include="FreecamPlugin.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
</ItemGroup>
<ItemGroup>
<None Include="app.config" />
<None Include="packages.config" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="..\packages\BepInEx.Core.5.4.19\build\BepInEx.Core.targets" Condition="Exists('..\packages\BepInEx.Core.5.4.19\build\BepInEx.Core.targets')" />
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<ErrorText>This project references NuGet package(s) that are missing on this computer. Use NuGet Package Restore to download them. For more information, see http://go.microsoft.com/fwlink/?LinkID=322105. The missing file is {0}.</ErrorText>
<TargetFramework>net472</TargetFramework>
<EnableDefaultCompileItems>False</EnableDefaultCompileItems>
</PropertyGroup>
<Error Condition="!Exists('..\packages\BepInEx.Core.5.4.19\build\BepInEx.Core.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\BepInEx.Core.5.4.19\build\BepInEx.Core.targets'))" />
</Target>
</Project>
<ItemGroup>
<Reference Include="0Harmony">
<HintPath>..\Shared\0Harmony.dll</HintPath>
</Reference>
<Reference Include="Aki.Reflection">
<HintPath>..\Shared\Aki.Reflection.dll</HintPath>
</Reference>
<Reference Include="Assembly-CSharp">
<HintPath>..\Shared\Assembly-CSharp.dll</HintPath>
</Reference>
<Reference Include="BepInEx">
<HintPath>..\Shared\BepInEx.dll</HintPath>
</Reference>
<Reference Include="Comfort">
<HintPath>..\Shared\Comfort.dll</HintPath>
</Reference>
<Reference Include="ConfigurationManager">
<HintPath>..\Shared\ConfigurationManager.dll</HintPath>
</Reference>
<Reference Include="ItemComponent.Types">
<HintPath>..\Shared\ItemComponent.Types.dll</HintPath>
</Reference>
<Reference Include="UnityEngine">
<HintPath>..\Shared\UnityEngine.dll</HintPath>
</Reference>
<Reference Include="UnityEngine.CoreModule">
<HintPath>..\Shared\UnityEngine.CoreModule.dll</HintPath>
</Reference>
<Reference Include="UnityEngine.InputLegacyModule">
<HintPath>..\Shared\UnityEngine.InputLegacyModule.dll</HintPath>
</Reference>
<Reference Include="UnityEngine.UIModule">
<HintPath>..\Shared\UnityEngine.UIModule.dll</HintPath>
</Reference>
</ItemGroup>
</Project>

@ -1,11 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<runtime>
<assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
<dependentAssembly>
<assemblyIdentity name="Mono.Cecil" publicKeyToken="50cebf1cceb9d05e" culture="neutral" />
<bindingRedirect oldVersion="0.0.0.0-0.11.4.0" newVersion="0.11.4.0" />
</dependentAssembly>
</assemblyBinding>
</runtime>
</configuration>

@ -1,9 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="BepInEx.BaseLib" version="5.4.19" targetFramework="net472" />
<package id="BepInEx.Core" version="5.4.19" targetFramework="net472" />
<package id="HarmonyX" version="2.7.0" targetFramework="net472" />
<package id="Mono.Cecil" version="0.11.4" targetFramework="net472" />
<package id="MonoMod.RuntimeDetour" version="21.12.13.1" targetFramework="net472" />
<package id="MonoMod.Utils" version="21.12.13.1" targetFramework="net472" />
</packages>