Updated to component, Added faceshield hit repair, fixed Helmet repair.
This commit is contained in:
15
ASS.csproj
15
ASS.csproj
@@ -7,8 +7,8 @@
|
||||
<ProjectGuid>{967E5737-8917-4C2B-A0A4-B2B553498462}</ProjectGuid>
|
||||
<OutputType>Library</OutputType>
|
||||
<AppDesignerFolder>Properties</AppDesignerFolder>
|
||||
<RootNamespace>armorMod.ASS</RootNamespace>
|
||||
<AssemblyName>armorMod.ASS</AssemblyName>
|
||||
<RootNamespace>dvize.ASS</RootNamespace>
|
||||
<AssemblyName>dvize.ASS</AssemblyName>
|
||||
<TargetFrameworkVersion>v4.7.2</TargetFrameworkVersion>
|
||||
<FileAlignment>512</FileAlignment>
|
||||
<Deterministic>true</Deterministic>
|
||||
@@ -29,6 +29,7 @@
|
||||
<DefineConstants>TRACE</DefineConstants>
|
||||
<ErrorReport>prompt</ErrorReport>
|
||||
<WarningLevel>4</WarningLevel>
|
||||
<PlatformTarget>x64</PlatformTarget>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="0Harmony, Version=2.9.0.0, Culture=neutral, processorArchitecture=MSIL">
|
||||
@@ -94,11 +95,19 @@
|
||||
</Reference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Compile Include="Component.cs" />
|
||||
<Compile Include="Plugin.cs" />
|
||||
<Compile Include="Properties\AssemblyInfo.cs" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
|
||||
<PropertyGroup>
|
||||
<PostBuildEvent>copy "$(TargetPath)" "F:\SPT-AKI\BepInEx\plugins\dvize.ASS.dll"</PostBuildEvent>
|
||||
<PostBuildEvent>copy "$(TargetPath)" "F:\SPT-AKI-DEV\BepInEx\plugins\$(TargetName).dll"
|
||||
|
||||
if $(ConfigurationName) == Debug (
|
||||
copy "$(TargetDir)$(TargetName).pdb" "F:\SPT-AKI-DEV\BepInEx\plugins\$(TargetName).pdb"
|
||||
) else (
|
||||
del "F:\SPT-AKI-DEV\BepInEx\plugins\$(TargetName).pdb"
|
||||
)
|
||||
</PostBuildEvent>
|
||||
</PropertyGroup>
|
||||
</Project>
|
176
Component.cs
Normal file
176
Component.cs
Normal file
@@ -0,0 +1,176 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using BepInEx.Logging;
|
||||
using Comfort.Common;
|
||||
using EFT;
|
||||
using EFT.InventoryLogic;
|
||||
using HarmonyLib;
|
||||
using UnityEngine;
|
||||
|
||||
namespace armorMod
|
||||
{
|
||||
internal class AssComponent : MonoBehaviour
|
||||
{
|
||||
private static GameWorld gameWorld = new GameWorld();
|
||||
private static Player player = new Player();
|
||||
|
||||
private static float newRepairRate;
|
||||
private static float newMaxDurabilityDrainRate;
|
||||
private static RepairableComponent armor;
|
||||
private static FaceShieldComponent faceShield;
|
||||
private static float maxRepairableDurabilityBasedOnCap;
|
||||
private static float timeSinceLastHit = 0f;
|
||||
|
||||
private static Dictionary<EquipmentSlot, List<Item>> equipmentSlotDictionary = new Dictionary<EquipmentSlot, List<Item>>
|
||||
{
|
||||
{ EquipmentSlot.ArmorVest, new List<Item>() },
|
||||
{ EquipmentSlot.TacticalVest, new List<Item>() },
|
||||
{ EquipmentSlot.Eyewear, new List<Item>() },
|
||||
{ EquipmentSlot.FaceCover, new List<Item>() },
|
||||
{ EquipmentSlot.Headwear, new List<Item>() },
|
||||
};
|
||||
|
||||
protected static ManualLogSource Logger
|
||||
{
|
||||
get; private set;
|
||||
}
|
||||
private AssComponent()
|
||||
{
|
||||
if (Logger == null)
|
||||
{
|
||||
Logger = BepInEx.Logging.Logger.CreateLogSource(nameof(AssComponent));
|
||||
}
|
||||
}
|
||||
|
||||
private void Start()
|
||||
{
|
||||
player = Singleton<GameWorld>.Instance.MainPlayer;
|
||||
player.BeingHitAction += Player_BeingHitAction;
|
||||
}
|
||||
internal static void Enable()
|
||||
{
|
||||
if (Singleton<IBotGame>.Instantiated)
|
||||
{
|
||||
gameWorld = Singleton<GameWorld>.Instance;
|
||||
gameWorld.GetOrAddComponent<AssComponent>();
|
||||
|
||||
Logger.LogDebug("ASS: AssComponent enabled");
|
||||
}
|
||||
}
|
||||
|
||||
private async void Update()
|
||||
{
|
||||
if (AssPlugin.ArmorServiceMode.Value)
|
||||
{
|
||||
timeSinceLastHit += Time.deltaTime;
|
||||
|
||||
if (timeSinceLastHit >= AssPlugin.TimeDelayRepairInSec.Value)
|
||||
{
|
||||
RepairArmor();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private async Task RepairArmor()
|
||||
{
|
||||
newRepairRate = AssPlugin.ArmorRepairRateOverTime.Value * Time.deltaTime;
|
||||
newMaxDurabilityDrainRate = AssPlugin.MaxDurabilityDegradationRateOverTime.Value * Time.deltaTime;
|
||||
|
||||
foreach (EquipmentSlot slot in equipmentSlotDictionary.Keys.ToArray())
|
||||
{
|
||||
Slot tempSlot = getEquipSlot(slot);
|
||||
|
||||
if (tempSlot == null || tempSlot.ContainedItem == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
foreach (var item in tempSlot.ContainedItem.GetAllItems())
|
||||
{
|
||||
//get the armorcomponent of each item in items and check to see if all item componenets (even helmet side ears) are max durability
|
||||
|
||||
//Logger.LogDebug("Examining the item: " + item.Name.Localized() + " in slot: " + slot.ToString() + " for repairable component");
|
||||
|
||||
item.TryGetItemComponent<RepairableComponent>(out armor);
|
||||
|
||||
|
||||
if (armor == null)
|
||||
{
|
||||
//Logger.LogDebug("Item: " + item.Name.Localized() + " in slot: " + slot.ToString() + " does not have a repairable component");
|
||||
continue;
|
||||
}
|
||||
|
||||
if (slot == EquipmentSlot.Headwear)
|
||||
{
|
||||
item.TryGetItemComponent<FaceShieldComponent>(out faceShield);
|
||||
|
||||
//if has faceshield repair bullet damage hits
|
||||
if (faceShield != null)
|
||||
{
|
||||
//Logger.LogDebug("Item has a faceshield component, setting hits to 0");
|
||||
|
||||
if (faceShield.Hits > 0)
|
||||
{
|
||||
faceShield.Hits = 0;
|
||||
faceShield.HitsChanged.Invoke();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
maxRepairableDurabilityBasedOnCap = ((AssPlugin.MaxDurabilityCap.Value / 100) * armor.MaxDurability);
|
||||
|
||||
//check if it needs repair for the current item in loop of all items for the slot
|
||||
if(armor.Durability < maxRepairableDurabilityBasedOnCap)
|
||||
{
|
||||
//increase armor durability by newRepairRate until maximum then set as maximum durability
|
||||
if (armor.Durability + newRepairRate >= armor.MaxDurability)
|
||||
{
|
||||
armor.Durability = armor.MaxDurability;
|
||||
}
|
||||
else
|
||||
{
|
||||
armor.Durability += newRepairRate;
|
||||
armor.MaxDurability -= newMaxDurabilityDrainRate;
|
||||
}
|
||||
}
|
||||
|
||||
await Task.Delay(1);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
private void Player_BeingHitAction(DamageInfo dmgInfo, EBodyPart bodyPart, float hitEffectId) => timeSinceLastHit = 0f;
|
||||
|
||||
|
||||
|
||||
private static Slot slotContents;
|
||||
private static InventoryControllerClass inventoryController;
|
||||
private Slot getEquipSlot(EquipmentSlot slot)
|
||||
{
|
||||
// Use AccessTools to get the protected field _inventoryController
|
||||
inventoryController = (InventoryControllerClass)AccessTools.Field(typeof(Player), "_inventoryController").GetValue(player);
|
||||
|
||||
if (inventoryController != null)
|
||||
{
|
||||
slotContents = inventoryController.Inventory.Equipment.GetSlot(slot);
|
||||
|
||||
if (slotContents.ContainedItem == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return slotContents;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
|
200
Plugin.cs
200
Plugin.cs
@@ -1,22 +1,17 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Aki.Reflection.Patching;
|
||||
using System.Reflection;
|
||||
using BepInEx;
|
||||
using BepInEx.Configuration;
|
||||
using Comfort.Common;
|
||||
using EFT;
|
||||
using EFT.InventoryLogic;
|
||||
using HarmonyLib;
|
||||
using UnityEngine;
|
||||
|
||||
namespace armorMod
|
||||
{
|
||||
[BepInPlugin("com.armorMod.ASS", "armorMod.ASS", "1.2.0")]
|
||||
[BepInPlugin("com.armorMod.ASS", "armorMod.ASS", "1.3.0")]
|
||||
|
||||
public class ASS : BaseUnityPlugin
|
||||
public class AssPlugin : BaseUnityPlugin
|
||||
{
|
||||
private ConfigEntry<Boolean> ArmorServiceMode
|
||||
internal static ConfigEntry<Boolean> ArmorServiceMode
|
||||
{
|
||||
get; set;
|
||||
}
|
||||
@@ -24,43 +19,22 @@ namespace armorMod
|
||||
{
|
||||
get; set;
|
||||
}*/
|
||||
private static ConfigEntry<float> TimeDelayRepairInSec
|
||||
internal static ConfigEntry<float> TimeDelayRepairInSec
|
||||
{
|
||||
get; set;
|
||||
}
|
||||
private static ConfigEntry<float> ArmorRepairRateOverTime
|
||||
internal static ConfigEntry<float> ArmorRepairRateOverTime
|
||||
{
|
||||
get; set;
|
||||
}
|
||||
private static ConfigEntry<float> MaxDurabilityDegradationRateOverTime
|
||||
internal static ConfigEntry<float> MaxDurabilityDegradationRateOverTime
|
||||
{
|
||||
get; set;
|
||||
}
|
||||
private static ConfigEntry<float> MaxDurabilityCap
|
||||
internal static ConfigEntry<float> MaxDurabilityCap
|
||||
{
|
||||
get; set;
|
||||
}
|
||||
|
||||
private AbstractGame game;
|
||||
private bool runOnceAlready = false;
|
||||
private bool newGame = true;
|
||||
private float newRepairRate;
|
||||
private float newMaxDurabilityDrainRate;
|
||||
private ArmorComponent armor;
|
||||
private float currentArmorDurabilityPercentage;
|
||||
private static float timeSinceLastHit = 0f;
|
||||
/*private static InsuranceCompanyClass insurance;
|
||||
private static List<InsuredItemClass> insuranceList;*/
|
||||
|
||||
private readonly Dictionary<EquipmentSlot, List<Item>> equipmentSlotDictionary = new Dictionary<EquipmentSlot, List<Item>>
|
||||
{
|
||||
{ EquipmentSlot.ArmorVest, new List<Item>() },
|
||||
{ EquipmentSlot.TacticalVest, new List<Item>() },
|
||||
{ EquipmentSlot.Eyewear, new List<Item>() },
|
||||
{ EquipmentSlot.FaceCover, new List<Item>() },
|
||||
{ EquipmentSlot.Headwear, new List<Item>() }
|
||||
};
|
||||
|
||||
internal void Awake()
|
||||
{
|
||||
ArmorServiceMode = Config.Bind("Armor Repair Settings", "Enable/Disable Mod", true, "Enables the Armor Repairing Options Below");
|
||||
@@ -69,162 +43,20 @@ namespace armorMod
|
||||
ArmorRepairRateOverTime = Config.Bind("Armor Repair Settings", "Armor Repair Rate", 0.5f, "How much durability per second is repaired");
|
||||
MaxDurabilityDegradationRateOverTime = Config.Bind("Armor Repair Settings", "Max Durability Drain Rate", 0.025f, "How much max durability per second of repairs is drained");
|
||||
MaxDurabilityCap = Config.Bind("Armor Repair Settings", "Max Durability Cap", 100f, "Maximum durability percentage to which armor will be able to repair to. For example, setting to 80 would repair your armor to maximum of 80% of it's max durability");
|
||||
}
|
||||
private void Update()
|
||||
{
|
||||
try
|
||||
{
|
||||
game = Singleton<AbstractGame>.Instance;
|
||||
|
||||
if (game.InRaid && Camera.main.transform.position != null && newGame && ArmorServiceMode.Value)
|
||||
{
|
||||
var player = Singleton<GameWorld>.Instance.MainPlayer;
|
||||
timeSinceLastHit += Time.deltaTime;
|
||||
|
||||
if (!runOnceAlready && game.Status == GameStatus.Started)
|
||||
{
|
||||
Logger.LogDebug("ASS: Attaching events");
|
||||
player.BeingHitAction += Player_BeingHitAction;
|
||||
player.OnPlayerDeadOrUnspawn += Player_OnPlayerDeadOrUnspawn;
|
||||
runOnceAlready = true;
|
||||
/*
|
||||
//get insurance singleton
|
||||
insurance = Singleton<InsuranceCompanyClass>.Instance;*/
|
||||
}
|
||||
|
||||
RepairArmor();
|
||||
}
|
||||
}
|
||||
catch { }
|
||||
new NewGamePatch().Enable();
|
||||
}
|
||||
|
||||
private void RepairArmor()
|
||||
internal class NewGamePatch : ModulePatch
|
||||
{
|
||||
//if the time since we were last hit exceeds TimeDelayRepairInSec.Value then repair all armor
|
||||
if (timeSinceLastHit >= TimeDelayRepairInSec.Value)
|
||||
protected override MethodBase GetTargetMethod() => typeof(GameWorld).GetMethod(nameof(GameWorld.OnGameStarted));
|
||||
|
||||
[PatchPrefix]
|
||||
private static void PatchPrefix()
|
||||
{
|
||||
//Logger.LogInfo($"Repairing Armor Block Reached Because TimeSinceLastHitReached: " + timeSinceLastHit);
|
||||
//repair the armor divided by the time.unfixed rate
|
||||
newRepairRate = ArmorRepairRateOverTime.Value * Time.deltaTime;
|
||||
newMaxDurabilityDrainRate = MaxDurabilityDegradationRateOverTime.Value * Time.deltaTime;
|
||||
|
||||
foreach (EquipmentSlot slot in equipmentSlotDictionary.Keys.ToArray())
|
||||
{
|
||||
//Logger.LogInfo("ASS: Checking EquipmentSlot: " + slot);
|
||||
Slot tempSlot = getEquipSlot(slot);
|
||||
|
||||
if (tempSlot == null || tempSlot.ContainedItem == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
foreach (var item in tempSlot.ContainedItem.GetAllItems())
|
||||
{
|
||||
//get the armorcomponent of each item in items and check to see if all item componenets (even helmet side ears) are max durability
|
||||
armor = item.GetItemComponent<ArmorComponent>();
|
||||
|
||||
currentArmorDurabilityPercentage = armor.Repairable.Durability / armor.Repairable.MaxDurability * 100;
|
||||
|
||||
//check if it needs repair for the current item in loop of all items for the slot
|
||||
if (armor != null && (currentArmorDurabilityPercentage < MaxDurabilityCap.Value) && (armor.Repairable.Durability < armor.Repairable.MaxDurability))
|
||||
{
|
||||
//increase armor durability by newRepairRate until maximum then set as maximum durability
|
||||
if (armor.Repairable.Durability + newRepairRate >= armor.Repairable.MaxDurability)
|
||||
{
|
||||
armor.Repairable.Durability = armor.Repairable.MaxDurability;
|
||||
|
||||
/*//check if insuredItems class contains the item
|
||||
if (insurance != null && LoseInsuranceOnRepair.Value)
|
||||
{
|
||||
// use accesstools to get private List<InsuredItemClass> list_0;
|
||||
insuranceList = (List<InsuredItemClass>)AccessTools.Field(typeof(InsuranceCompanyClass), "list_0").GetValue(insurance);
|
||||
|
||||
//check the insuranceList for the item by id and remove it if it exists
|
||||
var x = insuranceList.Where(i => i.itemId == item.Id).FirstOrDefault();
|
||||
if (x != null)
|
||||
{
|
||||
//remove from insuranceList
|
||||
insuranceList.Remove(x);
|
||||
}
|
||||
|
||||
}*/
|
||||
|
||||
//Logger.LogInfo("ASS: Setting MaxDurability for " + item.LocalizedName());
|
||||
}
|
||||
else
|
||||
{
|
||||
armor.Repairable.Durability += newRepairRate;
|
||||
armor.Repairable.MaxDurability -= newMaxDurabilityDrainRate;
|
||||
|
||||
//check if insuredItems class contains the item
|
||||
/*if (insurance != null && LoseInsuranceOnRepair.Value)
|
||||
{
|
||||
// use accesstools to get private List<InsuredItemClass> list_0;
|
||||
insuranceList = (List<InsuredItemClass>)AccessTools.Field(typeof(InsuranceCompanyClass), "list_0").GetValue(insurance);
|
||||
|
||||
//check the insuranceList for the item by id and remove it if it exists
|
||||
var x = insuranceList.Where(i => i.itemId == item.Id).FirstOrDefault();
|
||||
if (x != null)
|
||||
{
|
||||
//remove from insuranceList
|
||||
insuranceList.Remove(x);
|
||||
}
|
||||
|
||||
}*/
|
||||
|
||||
//Logger.LogInfo("ASS: Repairing " + item.LocalizedName() + " : " + armor.Repairable.Durability + "/" + armor.Repairable.MaxDurability);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
AssComponent.Enable();
|
||||
}
|
||||
}
|
||||
|
||||
private void Player_BeingHitAction(DamageInfo dmgInfo, EBodyPart bodyPart, float hitEffectId) => timeSinceLastHit = 0f;
|
||||
|
||||
private void Player_OnPlayerDeadOrUnspawn(Player player)
|
||||
{
|
||||
Logger.LogDebug("ASS: Undo all events");
|
||||
player.BeingHitAction -= Player_BeingHitAction;
|
||||
player.OnPlayerDeadOrUnspawn -= Player_OnPlayerDeadOrUnspawn;
|
||||
runOnceAlready = false;
|
||||
newGame = false;
|
||||
|
||||
Task.Delay(TimeSpan.FromSeconds(15)).ContinueWith(_ =>
|
||||
{
|
||||
// Set newGame = true after the timer is finished so it doesn't execute the events right away
|
||||
newGame = true;
|
||||
});
|
||||
}
|
||||
|
||||
private Slot slotContents;
|
||||
private InventoryControllerClass inventoryController;
|
||||
private Slot getEquipSlot(EquipmentSlot slot)
|
||||
{
|
||||
var player = Singleton<GameWorld>.Instance.MainPlayer;
|
||||
|
||||
// Use AccessTools to get the protected field _inventoryController
|
||||
inventoryController = (InventoryControllerClass)AccessTools.Field(typeof(Player), "_inventoryController").GetValue(player);
|
||||
|
||||
|
||||
if (inventoryController != null)
|
||||
{
|
||||
slotContents = inventoryController.Inventory.Equipment.GetSlot(slot);
|
||||
|
||||
if (slotContents.ContainedItem == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return slotContents;
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
@@ -31,5 +31,5 @@ using System.Runtime.InteropServices;
|
||||
// You can specify all the values or you can default the Build and Revision Numbers
|
||||
// by using the '*' as shown below:
|
||||
// [assembly: AssemblyVersion("1.0.*")]
|
||||
[assembly: AssemblyVersion("1.2.0.0")]
|
||||
[assembly: AssemblyFileVersion("1.2.0.0")]
|
||||
[assembly: AssemblyVersion("1.3.0.0")]
|
||||
[assembly: AssemblyFileVersion("1.3.0.0")]
|
||||
|
Reference in New Issue
Block a user