using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using Photon.Pun;
using UnityEngine;
using UnityEngine.UI;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: AssemblyTitle("canFart")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("canFart")]
[assembly: AssemblyCopyright("Copyright © 2025")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("093a27fc-e347-4e2d-b831-458af2e3a8f1")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")]
[assembly: AssemblyVersion("1.0.0.0")]
namespace canFart;
[BepInPlugin("CanFart_SlimeYuri", "CanFart", "1.1.0")]
public class CanFart : BaseUnityPlugin
{
public static class PluginInfo
{
public const string PLUGIN_GUID = "CanFart_SlimeYuri";
public const string PLUGIN_NAME = "CanFart";
public const string PLUGIN_VERSION = "1.1.0";
}
[CompilerGenerated]
private sealed class <FartCoolDownCoroutine>d__37 : IEnumerator<object>, IDisposable, IEnumerator
{
private int <>1__state;
private object <>2__current;
public float cdDuration;
public CanFart <>4__this;
object IEnumerator<object>.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
object IEnumerator.Current
{
[DebuggerHidden]
get
{
return <>2__current;
}
}
[DebuggerHidden]
public <FartCoolDownCoroutine>d__37(int <>1__state)
{
this.<>1__state = <>1__state;
}
[DebuggerHidden]
void IDisposable.Dispose()
{
<>1__state = -2;
}
private bool MoveNext()
{
//IL_0033: Unknown result type (might be due to invalid IL or missing references)
//IL_003d: Expected O, but got Unknown
switch (<>1__state)
{
default:
return false;
case 0:
<>1__state = -1;
<>4__this.isInCoolDown = true;
<>2__current = (object)new WaitForSeconds(cdDuration);
<>1__state = 1;
return true;
case 1:
<>1__state = -1;
<>4__this.isInCoolDown = false;
return false;
}
}
bool IEnumerator.MoveNext()
{
//ILSpy generated this explicit interface implementation from .override directive in MoveNext
return this.MoveNext();
}
[DebuggerHidden]
void IEnumerator.Reset()
{
throw new NotSupportedException();
}
}
public static CanFart instance;
private static float _currentJumpMult = 2f;
private ConfigEntry<bool> enableCd;
private ConfigEntry<float> cdDurationConfig;
private ConfigEntry<float> FartingForce;
private bool isInCoolDown;
public ConfigEntry<KeyCode> hotkey;
private ConfigEntry<bool> enableChargeFart;
private ConfigEntry<float> minChargeTime;
private ConfigEntry<float> maxChargeTime;
private ConfigEntry<float> chargeLevel1Force;
private ConfigEntry<float> chargeLevel2Force;
private ConfigEntry<float> chargeLevel3Force;
private ConfigEntry<float> chargeLevel4Force;
private ConfigEntry<float> chargeLevel5Force;
private bool isChargingFart = false;
private float chargeStartTime = 0f;
private float currentChargeLevel = 0f;
private AudioSource chargeAudioSource;
private GameObject _customThrowUI;
private Image _customThrowBar;
private Gradient _throwGradient;
private ItemAudioManager _itemAudioManager;
internal static float CurrentJumpMult
{
get
{
return _currentJumpMult;
}
set
{
_currentJumpMult = value;
}
}
public void Start()
{
//IL_01bd: Unknown result type (might be due to invalid IL or missing references)
//IL_01c3: Expected O, but got Unknown
instance = this;
enableCd = ((BaseUnityPlugin)this).Config.Bind<bool>("放屁设置", "EnableCoolDown", true, "是否启用CD");
cdDurationConfig = ((BaseUnityPlugin)this).Config.Bind<float>("放屁设置", "CoolDownDuration", 2f, "CD时长(秒)");
FartingForce = ((BaseUnityPlugin)this).Config.Bind<float>("升空力度", "lift_off Force", 2000f, "float浮点数,Default:2000f,Recommnad:0f~8000f");
hotkey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("快捷键", "hotkey", (KeyCode)102, "默认键位键盘F,改键位时复制上述支持的键位即可");
enableChargeFart = ((BaseUnityPlugin)this).Config.Bind<bool>("蓄力放屁", "EnableChargeFart", true, "是否启用蓄力放屁");
minChargeTime = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "MinChargeTime", 0.3f, "最小蓄力时间(秒)");
maxChargeTime = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "MaxChargeTime", 5f, "最大蓄力时间(秒)");
chargeLevel1Force = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "ChargeLevel1Force", 2f, "等级1跳跃倍率(默认不蓄力)");
chargeLevel2Force = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "ChargeLevel2Force", 3f, "等级2跳跃倍率");
chargeLevel3Force = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "ChargeLevel3Force", 4f, "等级3跳跃倍率");
chargeLevel4Force = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "ChargeLevel4Force", 5f, "等级4跳跃倍率");
chargeLevel5Force = ((BaseUnityPlugin)this).Config.Bind<float>("蓄力放屁", "ChargeLevel5Force", 6f, "等级5跳跃倍率");
Harmony val = new Harmony("CanFart_SlimeYuri");
val.PatchAll();
((BaseUnityPlugin)this).Logger.LogInfo((object)"CanFart 已启动!");
InitializeCustomThrowUI();
}
public void Update()
{
//IL_0022: Unknown result type (might be due to invalid IL or missing references)
if (enableChargeFart.Value)
{
HandleChargeFart();
}
else if (Input.GetKeyDown(hotkey.Value) && !isInCoolDown)
{
Fart(chargeLevel1Force.Value);
if (enableCd.Value)
{
((MonoBehaviour)this).StartCoroutine(FartCoolDownCoroutine(cdDurationConfig.Value));
}
}
}
private void HandleChargeFart()
{
//IL_0007: Unknown result type (might be due to invalid IL or missing references)
//IL_006a: Unknown result type (might be due to invalid IL or missing references)
//IL_0127: Unknown result type (might be due to invalid IL or missing references)
if (Input.GetKeyDown(hotkey.Value))
{
if (isInCoolDown)
{
return;
}
isChargingFart = true;
chargeStartTime = Time.time;
currentChargeLevel = 0f;
PlayChargeSound();
((BaseUnityPlugin)this).Logger.LogInfo((object)"开始蓄力放屁");
}
if (isChargingFart && Input.GetKey(hotkey.Value))
{
float num = Time.time - chargeStartTime;
float value = minChargeTime.Value;
float num2 = maxChargeTime.Value;
if (num2 <= value)
{
num2 = value + 1f;
}
currentChargeLevel = Mathf.Clamp01(num / num2);
((BaseUnityPlugin)this).Logger.LogInfo((object)$"当前蓄力进度:{currentChargeLevel:F2},蓄力时间:{num:F2}秒,最大时间:{num2:F2}秒");
UpdateThrowUI(currentChargeLevel);
UpdateChargeSound(currentChargeLevel);
}
if (isChargingFart && Input.GetKeyUp(hotkey.Value))
{
float num3 = Time.time - chargeStartTime;
StopChargeSound();
float num4 = CalculateJumpMult(num3);
Fart(num4);
isChargingFart = false;
currentChargeLevel = 0f;
ResetThrowUI();
if (enableCd.Value)
{
((MonoBehaviour)this).StartCoroutine(FartCoolDownCoroutine(cdDurationConfig.Value));
}
((BaseUnityPlugin)this).Logger.LogInfo((object)$"蓄力放屁完成,蓄力时间:{num3:F2}秒,跳跃倍率:{num4:F1}f");
}
}
private float CalculateJumpMult(float chargeDuration)
{
if (chargeDuration < minChargeTime.Value)
{
return chargeLevel1Force.Value;
}
float value = minChargeTime.Value;
float num = maxChargeTime.Value;
if (num <= value)
{
num = value + 1f;
}
float num2 = Mathf.Clamp01((chargeDuration - value) / (num - value));
return Mathf.CeilToInt(num2 * 5f) switch
{
1 => chargeLevel1Force.Value,
2 => chargeLevel2Force.Value,
3 => chargeLevel3Force.Value,
4 => chargeLevel4Force.Value,
5 => chargeLevel5Force.Value,
_ => chargeLevel1Force.Value,
};
}
private void UpdateThrowUI(float chargeLevel)
{
//IL_0112: Unknown result type (might be due to invalid IL or missing references)
try
{
if ((Object)(object)_customThrowUI == (Object)null || (Object)(object)_customThrowBar == (Object)null)
{
InitializeCustomThrowUI();
if ((Object)(object)_customThrowUI == (Object)null || (Object)(object)_customThrowBar == (Object)null)
{
((BaseUnityPlugin)this).Logger.LogWarning((object)"UI组件仍未初始化,跳过更新");
return;
}
}
_customThrowUI.SetActive(true);
((BaseUnityPlugin)this).Logger.LogInfo((object)$"UI激活状态:{_customThrowUI.activeSelf}, Bar组件:{((Object)((Component)_customThrowBar).gameObject).name}");
float num = Mathf.Lerp(0.692f, 0.808f, chargeLevel);
_customThrowBar.fillAmount = num;
((BaseUnityPlugin)this).Logger.LogInfo((object)$"UI更新:chargeLevel={chargeLevel:F2},mappedFillAmount={num:F3},当前fillAmount={_customThrowBar.fillAmount:F3}");
if (_throwGradient != null)
{
((Graphic)_customThrowBar).color = _throwGradient.Evaluate(chargeLevel);
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("更新投掷UI失败:" + ex.Message + "\n" + ex.StackTrace));
}
}
private void ResetThrowUI()
{
try
{
if ((Object)(object)_customThrowUI != (Object)null)
{
_customThrowUI.SetActive(false);
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("重置投掷UI失败:" + ex.Message));
}
}
private void InitializeCustomThrowUI()
{
//IL_00e9: Unknown result type (might be due to invalid IL or missing references)
//IL_010c: Unknown result type (might be due to invalid IL or missing references)
//IL_0112: Invalid comparison between Unknown and I4
//IL_01ea: Unknown result type (might be due to invalid IL or missing references)
//IL_01f4: Expected O, but got Unknown
try
{
if ((Object)(object)GUIManager.instance == (Object)null)
{
((BaseUnityPlugin)this).Logger.LogWarning((object)"GUIManager实例为空,延迟初始化UI...");
return;
}
GameObject throwGO = GUIManager.instance.throwGO;
if ((Object)(object)throwGO == (Object)null)
{
((BaseUnityPlugin)this).Logger.LogWarning((object)"原始投掷UI为空");
return;
}
_customThrowUI = Object.Instantiate<GameObject>(throwGO);
_customThrowUI.transform.SetParent(throwGO.transform.parent, false);
((Object)_customThrowUI).name = "CustomFartChargeUI";
Image[] componentsInChildren = _customThrowUI.GetComponentsInChildren<Image>(true);
((BaseUnityPlugin)this).Logger.LogInfo((object)$"找到{componentsInChildren.Length}个Image组件");
Image[] array = componentsInChildren;
foreach (Image val in array)
{
((BaseUnityPlugin)this).Logger.LogInfo((object)$"Image名称: {((Object)((Component)val).gameObject).name}, 类型: {val.type}, 当前fillAmount: {val.fillAmount}");
if ((int)val.type == 3)
{
_customThrowBar = val;
((BaseUnityPlugin)this).Logger.LogInfo((object)("选中的蓄力条:" + ((Object)((Component)val).gameObject).name));
break;
}
}
if ((Object)(object)_customThrowBar == (Object)null)
{
if (componentsInChildren.Length != 0)
{
_customThrowBar = componentsInChildren[0];
((BaseUnityPlugin)this).Logger.LogInfo((object)("使用第一个Image作为蓄力条:" + ((Object)((Component)componentsInChildren[0]).gameObject).name));
}
else
{
((BaseUnityPlugin)this).Logger.LogWarning((object)"没有找到任何Image组件");
}
}
FieldInfo fieldInfo = AccessTools.Field(typeof(GUIManager), "throwGradient");
if (fieldInfo != null)
{
_throwGradient = (Gradient)fieldInfo.GetValue(GUIManager.instance);
}
_customThrowUI.SetActive(false);
((BaseUnityPlugin)this).Logger.LogInfo((object)"自定义蓄力UI初始化完成");
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("初始化自定义UI失败:" + ex.Message + "\n" + ex.StackTrace));
}
}
private void PlayChargeSound()
{
//IL_00ae: Unknown result type (might be due to invalid IL or missing references)
//IL_00b4: Expected O, but got Unknown
try
{
InitializeAudioManager();
if ((Object)(object)_itemAudioManager != (Object)null && (Object)(object)_itemAudioManager.throwCharge != (Object)null)
{
_itemAudioManager.throwCharge.loop = true;
_itemAudioManager.throwCharge.volume = 0.5f;
_itemAudioManager.throwCharge.pitch = 0.8f;
_itemAudioManager.throwCharge.Play();
((BaseUnityPlugin)this).Logger.LogInfo((object)"播放原生蓄力音效");
return;
}
Character localCharacter = Character.localCharacter;
if ((Object)(object)localCharacter != (Object)null)
{
GameObject val = new GameObject("ChargeFartAudio");
val.transform.SetParent(((Component)localCharacter).transform);
chargeAudioSource = val.AddComponent<AudioSource>();
chargeAudioSource.loop = true;
chargeAudioSource.volume = 0.5f;
chargeAudioSource.pitch = 1f;
chargeAudioSource.Play();
((BaseUnityPlugin)this).Logger.LogInfo((object)"使用备份方案播放蓄力音效");
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("播放蓄力音效失败:" + ex.Message));
}
}
private void InitializeAudioManager()
{
if ((Object)(object)_itemAudioManager != (Object)null)
{
return;
}
try
{
Character localCharacter = Character.localCharacter;
if ((Object)(object)localCharacter != (Object)null)
{
_itemAudioManager = ((Component)localCharacter).GetComponent<ItemAudioManager>();
if ((Object)(object)_itemAudioManager == (Object)null)
{
_itemAudioManager = ((Component)((Component)localCharacter).transform.root).GetComponentInChildren<ItemAudioManager>();
}
if ((Object)(object)_itemAudioManager != (Object)null)
{
((BaseUnityPlugin)this).Logger.LogInfo((object)"获取ItemAudioManager成功");
}
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("初始化音效管理器失败:" + ex.Message));
}
}
private void UpdateChargeSound(float chargeLevel)
{
try
{
if ((Object)(object)_itemAudioManager != (Object)null && (Object)(object)_itemAudioManager.throwCharge != (Object)null && _itemAudioManager.throwCharge.isPlaying)
{
_itemAudioManager.throwCharge.volume = Mathf.Lerp(0.3f, 1.4f, chargeLevel);
_itemAudioManager.throwCharge.pitch = Mathf.Lerp(0.8f, 1.4f, chargeLevel);
}
else if ((Object)(object)chargeAudioSource != (Object)null && chargeAudioSource.isPlaying)
{
chargeAudioSource.volume = Mathf.Lerp(0.5f, 1f, chargeLevel);
chargeAudioSource.pitch = Mathf.Lerp(1f, 2f, chargeLevel);
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("更新蓄力音效失败:" + ex.Message));
}
}
private void StopChargeSound()
{
try
{
if ((Object)(object)_itemAudioManager != (Object)null && (Object)(object)_itemAudioManager.throwCharge != (Object)null)
{
_itemAudioManager.throwCharge.Stop();
}
if ((Object)(object)chargeAudioSource != (Object)null)
{
chargeAudioSource.Stop();
if ((Object)(object)((Component)chargeAudioSource).gameObject != (Object)null)
{
Object.Destroy((Object)(object)((Component)chargeAudioSource).gameObject);
}
chargeAudioSource = null;
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("停止蓄力音效失败:" + ex.Message));
}
}
[IteratorStateMachine(typeof(<FartCoolDownCoroutine>d__37))]
private IEnumerator FartCoolDownCoroutine(float cdDuration)
{
//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
return new <FartCoolDownCoroutine>d__37(0)
{
<>4__this = this,
cdDuration = cdDuration
};
}
public void Fart(float jumpMult)
{
Character localCharacter = Character.localCharacter;
if ((Object)(object)localCharacter != (Object)null)
{
TryFart(localCharacter, jumpMult);
}
}
public void TryFart(Character character, float jumpMult)
{
//IL_0094: Unknown result type (might be due to invalid IL or missing references)
//IL_0154: Unknown result type (might be due to invalid IL or missing references)
//IL_00d3: Unknown result type (might be due to invalid IL or missing references)
//IL_018a: Unknown result type (might be due to invalid IL or missing references)
try
{
if ((Object)(object)character == (Object)null)
{
((BaseUnityPlugin)this).Logger.LogError((object)"TryFart: Character实例为空!");
return;
}
CurrentJumpMult = jumpMult;
((BaseUnityPlugin)this).Logger.LogInfo((object)"使用反射调用SpawnResourceAtPositionNetworked");
GameUtils val = GameUtils.instance;
if ((Object)(object)val != (Object)null)
{
MethodInfo methodInfo = AccessTools.Method(typeof(GameUtils), "SpawnResourceAtPositionNetworked", (Type[])null, (Type[])null);
ParameterInfo[] parameters = methodInfo.GetParameters();
if (parameters.Length == 3)
{
methodInfo.Invoke(val, new object[3]
{
"VFX_SporeExploExploEdibleSpawn",
character.Center,
(object)(RpcTarget)1
});
}
else if (parameters.Length == 4)
{
methodInfo.Invoke(val, new object[4]
{
"VFX_SporeExploExploEdibleSpawn",
character.Center,
(object)(RpcTarget)1,
null
});
}
}
((BaseUnityPlugin)this).Logger.LogInfo((object)"使用反射调用RPC_SpawnResourceAtPosition");
if ((Object)(object)val != (Object)null)
{
MethodInfo methodInfo2 = AccessTools.Method(typeof(GameUtils), "RPC_SpawnResourceAtPosition", (Type[])null, (Type[])null);
ParameterInfo[] parameters2 = methodInfo2.GetParameters();
if (parameters2.Length == 2)
{
methodInfo2.Invoke(val, new object[2] { "VFX_SporeExploExploEdibleSpawn_NoKnockback", character.Center });
}
else if (parameters2.Length == 3)
{
methodInfo2.Invoke(val, new object[3] { "VFX_SporeExploExploEdibleSpawn_NoKnockback", character.Center, null });
}
}
((BaseUnityPlugin)this).Logger.LogInfo((object)"使用反射调用JumpRpc");
CharacterMovement component = ((Component)character).GetComponent<CharacterMovement>();
if ((Object)(object)component != (Object)null)
{
MethodInfo methodInfo3 = AccessTools.Method(typeof(CharacterMovement), "JumpRpc", (Type[])null, (Type[])null);
ParameterInfo[] parameters3 = methodInfo3.GetParameters();
if (parameters3.Length == 1)
{
methodInfo3.Invoke(component, new object[1] { true });
}
else if (parameters3.Length == 2)
{
methodInfo3.Invoke(component, new object[2] { true, null });
}
}
}
catch (Exception ex)
{
((BaseUnityPlugin)this).Logger.LogError((object)("放屁逻辑执行失败:" + ex.Message + "\n" + ex.StackTrace));
}
}
public void LogInfo(string message)
{
((BaseUnityPlugin)this).Logger.LogInfo((object)message);
}
public void LogWarning(string message)
{
((BaseUnityPlugin)this).Logger.LogWarning((object)message);
}
public void LogError(string message)
{
((BaseUnityPlugin)this).Logger.LogError((object)message);
}
}
[HarmonyPatch(typeof(CharacterMovement), "JumpRpc")]
[HarmonyPriority(200)]
public class JumpRpcPatch
{
private static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions)
{
//IL_00d6: Unknown result type (might be due to invalid IL or missing references)
//IL_00e0: Expected O, but got Unknown
List<CodeInstruction> list = new List<CodeInstruction>(instructions);
for (int i = 0; i < list.Count; i++)
{
if (list[i].opcode == OpCodes.Ldc_R4 && Math.Abs((float)list[i].operand - 2f) < 0.001f && i + 1 < list.Count && list[i + 1].opcode == OpCodes.Stfld)
{
FieldInfo fieldInfo = list[i + 1].operand as FieldInfo;
if (fieldInfo != null && fieldInfo.Name.Contains("jumpMult"))
{
list[i] = new CodeInstruction(OpCodes.Call, (object)AccessTools.PropertyGetter(typeof(CanFart), "CurrentJumpMult"));
Debug.Log((object)"成功替换jumpMult赋值");
}
}
}
return list;
}
}