0
0
mirror of https://github.com/sp-tarkov/modules.git synced 2025-02-13 09:50:43 -05:00

Fixed BTR exceptions introduced by previous commit (!107)

Todo:

- Fix BTR spawning in and driving around at a weird angle
  - Perhaps because the serverside BTR is missing an instance of `VehicleSuspension`
- Randomise BTR spawn time instead of always spawning at raid start
- Add spawn chance for BTR instead of guaranteed spawn in raid
- Test BTR trader services

Reviewed-on: SPT-AKI/Modules#107
Co-authored-by: Arys <arys@noreply.dev.sp-tarkov.com>
Co-committed-by: Arys <arys@noreply.dev.sp-tarkov.com>
This commit is contained in:
Arys 2024-04-07 08:05:07 +00:00 committed by chomp
parent b6a86e0edb
commit c5a0c6998d
6 changed files with 105 additions and 59 deletions

View File

@ -57,7 +57,7 @@ namespace Aki.Custom
new RagfairFeePatch().Enable(); new RagfairFeePatch().Enable();
new ScavQuestPatch().Enable(); new ScavQuestPatch().Enable();
new FixBrokenSpawnOnSandboxPatch().Enable(); new FixBrokenSpawnOnSandboxPatch().Enable();
new BTRControllerConstructorPatch().Enable(); new BTRControllerInitPatch().Enable();
new BTRPathLoadPatch().Enable(); new BTRPathLoadPatch().Enable();
new BTRActivateTraderDialogPatch().Enable(); new BTRActivateTraderDialogPatch().Enable();
new BTRInteractionPatch().Enable(); new BTRInteractionPatch().Enable();

View File

@ -6,11 +6,9 @@ using EFT.InventoryLogic;
using EFT.UI; using EFT.UI;
using EFT.Vehicle; using EFT.Vehicle;
using HarmonyLib; using HarmonyLib;
using System;
using System.Collections; using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
using System.Reflection;
using System.Threading.Tasks; using System.Threading.Tasks;
using UnityEngine; using UnityEngine;
using Random = UnityEngine.Random; using Random = UnityEngine.Random;
@ -50,20 +48,8 @@ namespace Aki.Custom.BTR
private Player.FirearmController firearmController; private Player.FirearmController firearmController;
private WeaponSoundPlayer weaponSoundPlayer; private WeaponSoundPlayer weaponSoundPlayer;
private MethodInfo _updateTaxiPriceMethod;
private MethodInfo _playWeaponSoundMethod;
private float originalDamageCoeff; private float originalDamageCoeff;
BTRManager()
{
Type btrControllerType = typeof(BTRControllerClass);
_updateTaxiPriceMethod = AccessTools.GetDeclaredMethods(btrControllerType).Single(IsUpdateTaxiPriceMethod);
Type firearmControllerType = typeof(Player.FirearmController);
_playWeaponSoundMethod = AccessTools.GetDeclaredMethods(firearmControllerType).Single(IsPlayWeaponSoundMethod);
}
private async void Awake() private async void Awake()
{ {
try try
@ -139,26 +125,6 @@ namespace Aki.Custom.BTR
} }
} }
// Find `BTRControllerClass.method_9(PathDestination currentDestinationPoint, bool lastRoutePoint)`
private bool IsUpdateTaxiPriceMethod(MethodInfo method)
{
ParameterInfo[] parameters = method.GetParameters();
return parameters.Length == 2 && parameters[0].ParameterType == typeof(PathDestination);
}
private bool IsPlayWeaponSoundMethod(MethodInfo method)
{
ParameterInfo[] parameters = method.GetParameters();
return parameters.Length == 5
&& parameters[0].ParameterType == typeof(WeaponSoundPlayer)
&& parameters[1].ParameterType == typeof(BulletClass)
&& parameters[2].ParameterType == typeof(Vector3)
&& parameters[3].ParameterType == typeof(Vector3)
&& parameters[4].ParameterType == typeof(bool);
}
private void Update() private void Update()
{ {
if (!btrInitialized) return; if (!btrInitialized) return;
@ -194,7 +160,7 @@ namespace Aki.Custom.BTR
private async Task InitBtr() private async Task InitBtr()
{ {
// Initial setup // Initial setup
await btrController.method_1(); await btrController.InitBtrController();
botEventHandler = Singleton<BotEventHandler>.Instance; botEventHandler = Singleton<BotEventHandler>.Instance;
var botsController = Singleton<IBotGame>.Instance.BotsController; var botsController = Singleton<IBotGame>.Instance.BotsController;
@ -280,7 +246,7 @@ namespace Aki.Custom.BTR
TraderServicesManager.Instance.RemovePurchasedService(ETraderServiceType.PlayerTaxi, BTRUtil.BTRTraderId); TraderServicesManager.Instance.RemovePurchasedService(ETraderServiceType.PlayerTaxi, BTRUtil.BTRTraderId);
// Update the prices for the taxi service // Update the prices for the taxi service
_updateTaxiPriceMethod.Invoke(btrController, new object[] { destinationPoint, isFinal }); btrController.UpdateTaxiPrice(destinationPoint, isFinal);
// Update the UI // Update the UI
TraderServicesManager.Instance.GetTraderServicesDataFromServer(BTRUtil.BTRTraderId); TraderServicesManager.Instance.GetTraderServicesDataFromServer(BTRUtil.BTRTraderId);
@ -488,7 +454,7 @@ namespace Aki.Custom.BTR
Vector3 aimDirection = Vector3.Normalize(targetHeadPos - machineGunMuzzle.position); Vector3 aimDirection = Vector3.Normalize(targetHeadPos - machineGunMuzzle.position);
ballisticCalculator.Shoot(btrMachineGunAmmo, machineGunMuzzle.position, aimDirection, btrBotShooter.ProfileId, btrMachineGunWeapon, 1f, 0); ballisticCalculator.Shoot(btrMachineGunAmmo, machineGunMuzzle.position, aimDirection, btrBotShooter.ProfileId, btrMachineGunWeapon, 1f, 0);
_playWeaponSoundMethod.Invoke(firearmController, new object[] { weaponSoundPlayer, btrMachineGunAmmo, machineGunMuzzle.position, aimDirection, false }); firearmController.PlayWeaponSound(weaponSoundPlayer, btrMachineGunAmmo, machineGunMuzzle.position, aimDirection, false);
burstCount--; burstCount--;
yield return new WaitForSecondsRealtime(0.092308f); // 650 RPM yield return new WaitForSecondsRealtime(0.092308f); // 650 RPM

View File

@ -1,20 +0,0 @@
using Aki.Reflection.Patching;
using HarmonyLib;
using System.Reflection;
namespace Aki.Custom.BTR.Patches
{
public class BTRControllerConstructorPatch : ModulePatch
{
protected override MethodBase GetTargetMethod()
{
return AccessTools.GetDeclaredConstructors(typeof(BTRControllerClass))[0];
}
[PatchPrefix]
private static bool PatchPrefix()
{
return false; // We don't want the original constructor to run
}
}
}

View File

@ -0,0 +1,34 @@
using Aki.Reflection.Patching;
using HarmonyLib;
using System.Reflection;
using System.Threading;
using System.Threading.Tasks;
namespace Aki.Custom.BTR.Patches
{
public class BTRControllerInitPatch : ModulePatch
{
protected override MethodBase GetTargetMethod()
{
return AccessTools.FirstMethod(typeof(BTRControllerClass), IsTargetMethod);
}
private bool IsTargetMethod(MethodInfo method)
{
ParameterInfo[] parameters = method.GetParameters();
return method.ReturnType == typeof(Task)
&& parameters.Length == 1
&& parameters[0].ParameterType == typeof(CancellationToken);
}
[PatchPrefix]
private static bool PatchPrefix(ref Task __result)
{
// The BTRControllerClass constructor expects the original method to return a Task,
// as it calls another method on said Task.
__result = Task.CompletedTask;
return false;
}
}
}

View File

@ -36,7 +36,7 @@ namespace Aki.Custom.BTR.Patches
return; return;
} }
var shotBy = (Player)damageInfo.Player; var shotBy = (Player)damageInfo.Player.iPlayer;
if (shotBy != null) if (shotBy != null)
{ {
botEventHandler.InterruptTraderServiceBtrSupportByBetrayer(shotBy); botEventHandler.InterruptTraderServiceBtrSupportByBetrayer(shotBy);

View File

@ -0,0 +1,66 @@
using EFT;
using EFT.Vehicle;
using HarmonyLib;
using System;
using System.Linq;
using System.Reflection;
using System.Threading.Tasks;
using UnityEngine;
namespace Aki.Custom.BTR.Utils
{
public static class BTRReflectionHelper
{
private static Type _btrControllerType = typeof(BTRControllerClass);
private static Type _firearmControllerType = typeof(Player.FirearmController);
private static MethodInfo _initBtrControllerMethod = AccessTools.GetDeclaredMethods(_btrControllerType).Single(IsInitBtrControllerMethod);
private static MethodInfo _updateTaxiPriceMethod = AccessTools.GetDeclaredMethods(_btrControllerType).Single(IsUpdateTaxiPriceMethod);
private static MethodInfo _playWeaponSoundMethod = AccessTools.GetDeclaredMethods(_firearmControllerType).Single(IsPlayWeaponSoundMethod);
public static Task InitBtrController(this BTRControllerClass controller)
{
return (Task)_initBtrControllerMethod.Invoke(controller, null);
}
public static void UpdateTaxiPrice(this BTRControllerClass controller, PathDestination destinationPoint, bool isFinal)
{
_updateTaxiPriceMethod.Invoke(controller, new object[] { destinationPoint, isFinal });
}
public static void PlayWeaponSound(this Player.FirearmController controller, WeaponSoundPlayer weaponSoundPlayer, BulletClass ammo, Vector3 shotPosition, Vector3 shotDirection, bool multiShot)
{
_playWeaponSoundMethod.Invoke(controller, new object[] { weaponSoundPlayer, ammo, shotPosition, shotDirection, multiShot });
}
// Find `BTRControllerClass.method_1()`
private static bool IsInitBtrControllerMethod(MethodInfo method)
{
return method.ReturnType == typeof(Task)
&& method.GetParameters().Length == 0;
}
// Find `BTRControllerClass.method_9(PathDestination currentDestinationPoint, bool lastRoutePoint)`
private static bool IsUpdateTaxiPriceMethod(MethodInfo method)
{
ParameterInfo[] parameters = method.GetParameters();
return parameters.Length == 2
&& parameters[0].ParameterType == typeof(PathDestination);
}
// Find `Player.FirearmController.method_54(WeaponSoundPlayer weaponSoundPlayer, BulletClass ammo, Vector3 shotPosition, Vector3 shotDirection, bool multiShot)`
private static bool IsPlayWeaponSoundMethod(MethodInfo method)
{
ParameterInfo[] parameters = method.GetParameters();
return parameters.Length == 5
&& parameters[0].ParameterType == typeof(WeaponSoundPlayer)
&& parameters[1].ParameterType == typeof(BulletClass)
&& parameters[2].ParameterType == typeof(Vector3)
&& parameters[3].ParameterType == typeof(Vector3)
&& parameters[4].ParameterType == typeof(bool);
}
}
}