using System;
using System.Reflection;
using System.Runtime.CompilerServices;
using BepInEx;
using HarmonyLib;
using Photon.Pun;
using UnityEngine;
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: CompilationRelaxations(8)]
[assembly: AssemblyVersion("0.0.0.0")]
namespace ThrowTeammate;
[BepInProcess("PEAK.exe")]
[BepInPlugin("com.throwthrow.throwteammate", "Throwwaway", "1.2.4")]
public class Plugin : BaseUnityPlugin
{
private Harmony harmony;
private void Awake()
{
//IL_0016: Unknown result type (might be due to invalid IL or missing references)
//IL_0020: Expected O, but got Unknown
((BaseUnityPlugin)this).Logger.LogInfo((object)"Throwwaway v1.2.4 loading...");
harmony = new Harmony("com.throwthrow.throwteammate");
harmony.PatchAll();
((BaseUnityPlugin)this).Logger.LogInfo((object)"Throwwaway loaded successfully!");
((BaseUnityPlugin)this).Logger.LogInfo((object)" Hold the game's Drop key (default Q) with empty hands to throw a carried teammate.");
((BaseUnityPlugin)this).Logger.LogInfo((object)" The top-row 4 / backpack action still drops the teammate normally.");
((BaseUnityPlugin)this).Logger.LogInfo((object)" Only the thrower needs this mod; teammates receive native PEAK network messages.");
}
private void OnDestroy()
{
if (harmony != null)
{
harmony.UnpatchSelf();
}
ThrowTeammateBehaviour[] array = Object.FindObjectsByType<ThrowTeammateBehaviour>((FindObjectsSortMode)0);
foreach (ThrowTeammateBehaviour throwTeammateBehaviour in array)
{
Object.Destroy((Object)(object)throwTeammateBehaviour);
}
((BaseUnityPlugin)this).Logger.LogInfo((object)"Throwwaway unloaded");
}
}
public static class PluginInfo
{
public const string GUID = "com.throwthrow.throwteammate";
public const string Name = "Throwwaway";
public const string Version = "1.2.4";
}
public sealed class ThrowTeammateBehaviour : MonoBehaviour
{
[HarmonyPatch(typeof(Character), "Awake")]
private static class AttachPatch
{
[HarmonyPostfix]
internal static void Postfix(Character __instance)
{
ThrowTeammateBehaviour throwTeammateBehaviour = ((Component)__instance).GetComponent<ThrowTeammateBehaviour>();
if ((Object)(object)throwTeammateBehaviour == (Object)null)
{
throwTeammateBehaviour = ((Component)__instance).gameObject.AddComponent<ThrowTeammateBehaviour>();
}
throwTeammateBehaviour.character = __instance;
}
}
[HarmonyPatch(typeof(CharacterItems), "DoDropping")]
private static class DropInputPatch
{
[HarmonyPrefix]
internal static bool Prefix(CharacterItems __instance, Character ___character, ref bool ___pressedDrop, ref float ___lastPressedDrop)
{
if (!___character.IsLocal)
{
return true;
}
ThrowTeammateBehaviour component = ((Component)___character).GetComponent<ThrowTeammateBehaviour>();
if (!((Object)(object)component == (Object)null))
{
return component.BeforeDropping(__instance, ref ___pressedDrop, ref ___lastPressedDrop);
}
return true;
}
}
private static readonly FieldInfo PressedDrop = AccessTools.Field(typeof(CharacterItems), "pressedDrop");
private static readonly Func<Vector3, Vector3, Vector3> LookToDirection = (Func<Vector3, Vector3, Vector3>)Delegate.CreateDelegate(typeof(Func<Vector3, Vector3, Vector3>), AccessTools.Method(typeof(HelperFunctions), "LookToDirection", (Type[])null, (Type[])null));
private Character character;
private Character chargeTarget;
private bool charging;
internal bool BeforeDropping(CharacterItems items, ref bool pressedDrop, ref float lastPressedDrop)
{
if (charging && (!CanCharge() || !pressedDrop))
{
CancelCharge();
}
if (character.input.dropWasPressed && CanStartCharge())
{
chargeTarget = character.data.carriedPlayer;
charging = true;
items.throwChargeLevel = 0f;
lastPressedDrop = Time.time;
pressedDrop = true;
}
if (charging && character.input.dropWasReleased)
{
Character target = chargeTarget;
float throwChargeLevel = items.throwChargeLevel;
CancelCharge();
Throw(target, throwChargeLevel);
return false;
}
return true;
}
private bool CanStartCharge()
{
if (character.IsLocal && Application.isFocused && CanThrowPair(character, character.data.carriedPlayer) && !character.refs.afflictions.isStruggling)
{
if (!((Object)(object)GUIManager.instance == (Object)null))
{
if (!GUIManager.instance.windowBlockingInput)
{
return !GUIManager.instance.wheelActive;
}
return false;
}
return true;
}
return false;
}
private bool CanCharge()
{
if (CanStartCharge() && (Object)(object)chargeTarget != (Object)null)
{
return (Object)(object)character.data.carriedPlayer == (Object)(object)chargeTarget;
}
return false;
}
private static bool CanThrowPair(Character carrier, Character target)
{
if ((Object)(object)carrier != (Object)null && (Object)(object)target != (Object)null && (Object)(object)carrier != (Object)(object)target && !carrier.data.isCarried && !carrier.data.dead && !carrier.data.passedOut && !carrier.data.fullyPassedOut && (Object)(object)carrier.data.currentItem == (Object)null && (Object)(object)carrier.data.carriedPlayer == (Object)(object)target && target.data.isCarried && (Object)(object)target.data.carrier == (Object)(object)carrier && target.data.fullyPassedOut)
{
return !target.data.dead;
}
return false;
}
private void LateUpdate()
{
if (charging && (!CanCharge() || !character.input.dropIsPressed))
{
CancelCharge();
}
}
private void OnApplicationFocus(bool focused)
{
if (!focused)
{
CancelCharge();
}
}
private void OnDisable()
{
CancelCharge();
}
private void CancelCharge()
{
if (charging)
{
charging = false;
chargeTarget = null;
if (!((Object)(object)character == (Object)null) && !((Object)(object)character.refs.items == (Object)null))
{
CharacterItems items = character.refs.items;
PressedDrop.SetValue(items, false);
items.throwChargeLevel = 0f;
items.isChargingThrow = false;
}
}
}
internal void Throw(Character target, float charge)
{
//IL_009f: Unknown result type (might be due to invalid IL or missing references)
//IL_00a4: Unknown result type (might be due to invalid IL or missing references)
//IL_00a9: Unknown result type (might be due to invalid IL or missing references)
//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
//IL_00b3: Unknown result type (might be due to invalid IL or missing references)
//IL_00b7: Unknown result type (might be due to invalid IL or missing references)
//IL_00bc: Unknown result type (might be due to invalid IL or missing references)
//IL_00bd: Unknown result type (might be due to invalid IL or missing references)
//IL_00c5: Unknown result type (might be due to invalid IL or missing references)
//IL_00ca: Unknown result type (might be due to invalid IL or missing references)
//IL_0151: Unknown result type (might be due to invalid IL or missing references)
//IL_0156: Unknown result type (might be due to invalid IL or missing references)
if ((Object)(object)character == (Object)null || !character.IsLocal || !((MonoBehaviourPun)character).photonView.IsMine || !CanThrowPair(character, target) || !(charge > 0f) || !(charge <= 1f))
{
return;
}
CharacterItems items = character.refs.items;
float num = (items.minThrowForce + (items.maxThrowForce - items.minThrowForce) * charge) * 0.5f;
if (!(num > 0f) || !(Time.fixedDeltaTime > 0f))
{
return;
}
Vector3 val = LookToDirection(Vector2.op_Implicit(character.data.lookValues), Vector3.forward);
Vector3 normalized = ((Vector3)(ref val)).normalized;
Vector3 val2 = normalized * (num / Time.fixedDeltaTime);
if (!(((Vector3)(ref val2)).sqrMagnitude > 0f) || float.IsInfinity(((Vector3)(ref val2)).sqrMagnitude) || !target.refs.ragdoll.partDict.TryGetValue((BodypartType)2, out var value) || (Object)(object)value == (Object)null || (Object)(object)value.Rig == (Object)null)
{
return;
}
character.BreakCharacterCarrying(true);
if (!target.data.isCarried && !((Object)(object)target.data.carrier != (Object)null))
{
target.AddForceToBodyPart(value.Rig, Vector3.zero, val2);
if (charge > 0.1f && (Object)(object)character.refs.animations != (Object)null)
{
character.refs.animations.throwTime = 0.125f;
}
}
}
}