using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.IO.Compression;
using System.Reflection;
using System.Reflection.Emit;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Threading;
using System.Threading.Tasks;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using Buttplug.Client;
using Buttplug.Client.Connectors.WebsocketConnector;
using Buttplug.Core;
using Costura;
using GameNetcodeStuff;
using HarmonyLib;
using LethalVibrations.Buttplug;
using LethalVibrations.Patches;
using Microsoft.CodeAnalysis;
using Unity.Netcode;
using UnityEngine;
[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)]
[assembly: TargetFramework(".NETFramework,Version=v4.7", FrameworkDisplayName = ".NET Framework 4.7")]
[assembly: AssemblyCompany("LethalVibrations")]
[assembly: AssemblyConfiguration("Release")]
[assembly: AssemblyDescription("Lethal Company mod that makes your sex toys vibrate.")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("LethalVibrations")]
[assembly: AssemblyTitle("LethalVibrations")]
[assembly: AssemblyVersion("1.0.0.0")]
[module: RefSafetyRules(11)]
internal class <Module>
{
static <Module>()
{
AssemblyLoader.Attach();
}
}
namespace Microsoft.CodeAnalysis
{
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
internal sealed class EmbeddedAttribute : Attribute
{
}
}
namespace System.Runtime.CompilerServices
{
[CompilerGenerated]
[Microsoft.CodeAnalysis.Embedded]
[AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)]
internal sealed class RefSafetyRulesAttribute : Attribute
{
public readonly int Version;
public RefSafetyRulesAttribute(int P_0)
{
Version = P_0;
}
}
}
namespace LethalVibrations
{
[BepInPlugin("LethalVibrations", "LethalVibrations", "1.0.0")]
public class Plugin : BaseUnityPlugin
{
internal static DeviceManager DeviceManager { get; private set; }
internal static ManualLogSource Mls { get; private set; }
private void Awake()
{
//IL_0029: Unknown result type (might be due to invalid IL or missing references)
//IL_002e: Unknown result type (might be due to invalid IL or missing references)
//IL_003e: Unknown result type (might be due to invalid IL or missing references)
//IL_004e: Unknown result type (might be due to invalid IL or missing references)
//IL_005e: Unknown result type (might be due to invalid IL or missing references)
//IL_006e: Unknown result type (might be due to invalid IL or missing references)
//IL_007e: Unknown result type (might be due to invalid IL or missing references)
//IL_008e: Unknown result type (might be due to invalid IL or missing references)
//IL_009e: Unknown result type (might be due to invalid IL or missing references)
Mls = ((BaseUnityPlugin)this).Logger;
DeviceManager = new DeviceManager("LethalVibrations");
DeviceManager.ConnectDevices();
Harmony val = new Harmony("LethalVibrations");
val.PatchAll(typeof(PlayerControllerBPatches));
val.PatchAll(typeof(ItemChargerPatches));
val.PatchAll(typeof(EnemyAIPatches));
val.PatchAll(typeof(HUDManagerPatches));
val.PatchAll(typeof(GrabbableObjectPatches));
val.PatchAll(typeof(RoundManagerPatches));
val.PatchAll(typeof(NoisemakerPropPatches));
val.PatchAll(typeof(ShipAlarmCordPatches));
val.PatchAll(typeof(StunGrenadeItemPatches));
((BaseUnityPlugin)this).Logger.LogInfo((object)"Plugin LethalVibrations (1.0.0) is loaded!");
}
}
public static class PluginInfo
{
public const string PLUGIN_GUID = "LethalVibrations";
public const string PLUGIN_NAME = "LethalVibrations";
public const string PLUGIN_VERSION = "1.0.0";
}
}
namespace LethalVibrations.Patches
{
internal class EnemyAIPatches
{
[HarmonyPatch(typeof(EnemyAI), "HitEnemy")]
[HarmonyPostfix]
private static void HitEnemyPatch(int force, PlayerControllerB playerWhoHit)
{
if (playerWhoHit.playerClientId == GameNetworkManager.Instance.localPlayerController.playerClientId)
{
Plugin.Mls.LogDebug((object)"HitEnemy got called");
if (Plugin.DeviceManager.IsConnected() && Config.VibrateDamageDealtEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.VibrateDamageDealtStrength.Value, Config.VibrateDamageDealtDuration.Value);
}
}
}
}
internal class GrabbableObjectPatches
{
[HarmonyPatch(typeof(GrabbableObject), "GrabItemOnClient")]
[HarmonyPostfix]
private static void GrabItemOnClientPatch(GrabbableObject __instance)
{
if (__instance.itemProperties.isScrap && !__instance.isInShipRoom)
{
Plugin.Mls.LogDebug((object)"GrabItemOnClient called");
if (Plugin.DeviceManager.IsConnected() && Config.Rewarding.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.VibrateKilledStrength.Value, Config.VibrateKilledDuration.Value);
}
}
}
}
internal class HUDManagerPatches
{
[HarmonyPatch(typeof(HUDManager), "ShakeCamera")]
[HarmonyPostfix]
private static void ShakeCameraPatch(ScreenShakeType shakeType)
{
//IL_000a: Unknown result type (might be due to invalid IL or missing references)
//IL_0033: Unknown result type (might be due to invalid IL or missing references)
//IL_0049: Expected I4, but got Unknown
Plugin.Mls.LogDebug((object)$"ShakeCamera {shakeType} got called");
if (Plugin.DeviceManager.IsConnected() && Config.VibrateScreenShakeEnabled.Value)
{
switch ((int)shakeType)
{
case 0:
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(0.3f + Config.VibrateScreenShakeAmplifier.Value, Config.VibrateScreenShakeDuration.Value);
break;
case 1:
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(0.6f + Config.VibrateScreenShakeAmplifier.Value, Config.VibrateScreenShakeDuration.Value);
break;
case 2:
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(0.5f + Config.VibrateScreenShakeAmplifier.Value, Config.VibrateScreenShakeDuration.Value + 0.6f);
break;
case 3:
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(0.9f + Config.VibrateScreenShakeAmplifier.Value, Config.VibrateScreenShakeDuration.Value + 0.3f);
break;
}
}
}
[HarmonyPatch(typeof(HUDManager), "DisplayNewDeadline")]
[HarmonyPostfix]
private static void DisplayNewDeadlinePatch()
{
Plugin.Mls.LogDebug((object)"DisplayNewDeadline got called");
if (Plugin.DeviceManager.IsConnected() && Config.QuotaReachedEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.QuotaReachedStrength.Value, Config.QuotaReachedDuration.Value);
}
}
[HarmonyPatch(typeof(HUDManager), "PingScan_performed")]
[HarmonyPostfix]
private static void PingScan_performedPatch()
{
Plugin.Mls.LogDebug((object)"PingScan_performed got called");
if (Plugin.DeviceManager.IsConnected() && Config.PingScanEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.PingScanStrength.Value, Config.PingScanDuration.Value);
}
}
}
internal class ItemChargerPatches
{
[HarmonyPatch(typeof(ItemCharger), "ChargeItem")]
[HarmonyPostfix]
private static void ChargeItemPatch()
{
Plugin.Mls.LogDebug((object)"ChargeItem got called");
if (Plugin.DeviceManager.IsConnected() && Config.VibrateItemChargerChargeEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.VibrateItemChargerChargeStrength.Value, Config.VibrateItemChargerChargeDuration.Value);
}
}
}
internal class NoisemakerPropPatches
{
[HarmonyPatch(typeof(NoisemakerProp), "ItemActivate")]
[HarmonyPostfix]
private static void ItemActivatePatch(NoisemakerProp __instance)
{
Plugin.Mls.LogDebug((object)("NoisemakerProp.ItemActivate got called: " + ((GrabbableObject)__instance).itemProperties.itemName));
if (!(((GrabbableObject)__instance).itemProperties.itemName != "Airhorn") && Plugin.DeviceManager.IsConnected() && Config.AirhornEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.AirhornStrength.Value, Config.AirhornDuration.Value);
}
}
}
internal class PlayerControllerBPatches
{
[HarmonyPatch(typeof(PlayerControllerB), "DamagePlayer")]
[HarmonyPostfix]
private static void DamagePlayerPatch(PlayerControllerB __instance, int damageNumber)
{
if (((NetworkBehaviour)__instance).IsOwner)
{
float num = damageNumber;
Plugin.Mls.LogDebug((object)$"DamagePlayer got called: {num} ({num / 100f})");
if (Plugin.DeviceManager.IsConnected() && Config.VibrateDamageReceivedEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(num / 100f + Config.VibrateDamageReceivedAmplifier.Value, Config.VibrateDamageReceivedDuration.Value);
}
}
}
[HarmonyPatch(typeof(PlayerControllerB), "KillPlayer")]
[HarmonyPostfix]
private static void KillPlayerPatch(PlayerControllerB __instance)
{
if (((NetworkBehaviour)__instance).IsOwner)
{
Plugin.Mls.LogDebug((object)"KillPlayer got called");
if (Plugin.DeviceManager.IsConnected() && Config.VibrateKilledEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.VibrateKilledStrength.Value, Config.VibrateKilledDuration.Value);
}
}
}
}
public class RoundManagerPatches
{
[HarmonyPatch(typeof(RoundManager), "DespawnPropsAtEndOfRound")]
[HarmonyPostfix]
private static void GrabItemOnClientPatch(RoundManager __instance)
{
Plugin.Mls.LogDebug((object)"DespawnPropsAtEndOfRound called");
if (Plugin.DeviceManager.IsConnected() && Config.RoundSurvivalEnabled.Value && !GameNetworkManager.Instance.localPlayerController.isPlayerDead)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.RoundSurvivalStrength.Value, Config.RoundSurvivalDuration.Value);
}
}
}
public class ShipAlarmCordPatches
{
[HarmonyPatch(typeof(ShipAlarmCord), "PullCordClientRpc")]
[HarmonyTranspiler]
private static IEnumerable<CodeInstruction> PullCordClientRpcTranspiler(IEnumerable<CodeInstruction> instructions)
{
List<CodeInstruction> list = new List<CodeInstruction>(instructions);
int index = list.FindLastIndex((CodeInstruction i) => i.opcode == OpCodes.Nop) + 1;
list.InsertRange(index, (IEnumerable<CodeInstruction>)(object)new CodeInstruction[1]
{
new CodeInstruction(OpCodes.Call, (object)AccessTools.Method(typeof(ShipAlarmCordPatches), "StartVibrating", (Type[])null, (Type[])null))
});
foreach (CodeInstruction item in list)
{
yield return item;
}
}
[HarmonyPatch(typeof(ShipAlarmCord), "StopPullingCordClientRpc")]
[HarmonyTranspiler]
private static IEnumerable<CodeInstruction> StopPullingCordClientRpcTranspiler(IEnumerable<CodeInstruction> instructions)
{
List<CodeInstruction> list = new List<CodeInstruction>(instructions);
int index = list.FindLastIndex((CodeInstruction i) => i.opcode == OpCodes.Nop) + 1;
list.InsertRange(index, (IEnumerable<CodeInstruction>)(object)new CodeInstruction[1]
{
new CodeInstruction(OpCodes.Call, (object)AccessTools.Method(typeof(ShipAlarmCordPatches), "StopVibrating", (Type[])null, (Type[])null))
});
foreach (CodeInstruction item in list)
{
yield return item;
}
}
[HarmonyPatch(typeof(ShipAlarmCord), "HoldCordDown")]
[HarmonyPostfix]
private static void HoldCordDownPatch()
{
Plugin.Mls.LogDebug((object)"ShipAlarmCord.HoldCordDown got called");
StartVibrating();
}
[HarmonyPatch(typeof(ShipAlarmCord), "StopHorn")]
[HarmonyPostfix]
private static void StopHornPatch()
{
Plugin.Mls.LogDebug((object)"ShipAlarmCord.StopHorn got called");
StopVibrating();
}
private static void StartVibrating()
{
if (Plugin.DeviceManager.IsConnected() && Config.ShipHornEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevices(Config.ShipHornStrength.Value);
}
}
private static void StopVibrating()
{
if (Plugin.DeviceManager.IsConnected() && Config.ShipHornEnabled.Value)
{
Plugin.DeviceManager.StopConnectedDevices();
}
}
}
public class StunGrenadeItemPatches
{
[HarmonyPatch(typeof(StunGrenadeItem), "StunExplosion")]
[HarmonyPostfix]
private static void StunExplosionPatch(StunGrenadeItem __instance)
{
Plugin.Mls.LogDebug((object)"StunExplosion got called");
if (Plugin.DeviceManager.IsConnected() && Config.FlashbangEnabled.Value)
{
Plugin.DeviceManager.VibrateConnectedDevicesWithDuration(Config.FlashbangStrength.Value, 0.3f);
}
}
}
}
namespace LethalVibrations.Buttplug
{
internal class Config
{
private static ConfigFile ConfigFile { get; set; }
internal static ConfigEntry<string> ServerUri { get; set; }
internal static ConfigEntry<float> VibrateAmplifier { get; set; }
internal static ConfigEntry<bool> Rewarding { get; set; }
internal static ConfigEntry<bool> VibrateDamageReceivedEnabled { get; set; }
internal static ConfigEntry<float> VibrateDamageReceivedDuration { get; set; }
internal static ConfigEntry<float> VibrateDamageReceivedAmplifier { get; set; }
internal static ConfigEntry<bool> VibrateDamageDealtEnabled { get; set; }
internal static ConfigEntry<float> VibrateDamageDealtDuration { get; set; }
internal static ConfigEntry<float> VibrateDamageDealtStrength { get; set; }
internal static ConfigEntry<bool> VibrateKilledEnabled { get; set; }
internal static ConfigEntry<float> VibrateKilledDuration { get; set; }
internal static ConfigEntry<float> VibrateKilledStrength { get; set; }
internal static ConfigEntry<bool> VibrateItemChargerChargeEnabled { get; set; }
internal static ConfigEntry<float> VibrateItemChargerChargeDuration { get; set; }
internal static ConfigEntry<float> VibrateItemChargerChargeStrength { get; set; }
internal static ConfigEntry<bool> VibrateScreenShakeEnabled { get; set; }
internal static ConfigEntry<float> VibrateScreenShakeDuration { get; set; }
internal static ConfigEntry<float> VibrateScreenShakeAmplifier { get; set; }
internal static ConfigEntry<bool> PingScanEnabled { get; set; }
internal static ConfigEntry<float> PingScanDuration { get; set; }
internal static ConfigEntry<float> PingScanStrength { get; set; }
internal static ConfigEntry<bool> QuotaReachedEnabled { get; set; }
internal static ConfigEntry<float> QuotaReachedDuration { get; set; }
internal static ConfigEntry<float> QuotaReachedStrength { get; set; }
internal static ConfigEntry<bool> RoundSurvivalEnabled { get; set; }
internal static ConfigEntry<float> RoundSurvivalDuration { get; set; }
internal static ConfigEntry<float> RoundSurvivalStrength { get; set; }
internal static ConfigEntry<bool> AirhornEnabled { get; set; }
internal static ConfigEntry<float> AirhornDuration { get; set; }
internal static ConfigEntry<float> AirhornStrength { get; set; }
internal static ConfigEntry<bool> ShipHornEnabled { get; set; }
internal static ConfigEntry<float> ShipHornStrength { get; set; }
internal static ConfigEntry<bool> FlashbangEnabled { get; set; }
internal static ConfigEntry<float> FlashbangStrength { get; set; }
static Config()
{
//IL_0010: Unknown result type (might be due to invalid IL or missing references)
//IL_001a: Expected O, but got Unknown
ConfigFile = new ConfigFile(Paths.ConfigPath + "\\LethalVibrations.cfg", true);
ServerUri = ConfigFile.Bind<string>("Devices", "Server Uri", "ws://localhost:12345", "URI of the Intiface server.");
VibrateAmplifier = ConfigFile.Bind<float>("Vibrations", "Amplifier", 0f, "Change the amplification of vibration");
Rewarding = ConfigFile.Bind<bool>("Vibrations", "Rewarding", true, "Enable rewarding");
VibrateDamageDealtEnabled = ConfigFile.Bind<bool>("Vibrations.DamageDealt", "Enabled", true, "Vibrate when you deal damage");
VibrateDamageDealtDuration = ConfigFile.Bind<float>("Vibrations.DamageDealt", "Duration", 1f, "Length of time to vibrate for");
VibrateDamageDealtStrength = ConfigFile.Bind<float>("Vibrations.DamageDealt", "Strength", 0.5f, "Change the strength of vibration");
QuotaReachedEnabled = ConfigFile.Bind<bool>("Vibrations.QuotaReached", "Enabled", true, "Vibrate when you reach the quota");
QuotaReachedDuration = ConfigFile.Bind<float>("Vibrations.QuotaReached", "Duration", 1f, "Length of time to vibrate for");
QuotaReachedStrength = ConfigFile.Bind<float>("Vibrations.QuotaReached", "Strength", 0.5f, "Change the strength of vibration");
RoundSurvivalEnabled = ConfigFile.Bind<bool>("Vibrations.RoundSurvival", "Enabled", true, "Vibrate when you survive the round");
RoundSurvivalDuration = ConfigFile.Bind<float>("Vibrations.RoundSurvival", "Duration", 1f, "Length of time to vibrate for");
RoundSurvivalStrength = ConfigFile.Bind<float>("Vibrations.RoundSurvival", "Strength", 0.3f, "Change the strength of vibration");
VibrateDamageReceivedEnabled = ConfigFile.Bind<bool>("Vibrations.DamageReceived", "Enabled", true, "Vibrate when you receive damage");
VibrateDamageReceivedDuration = ConfigFile.Bind<float>("Vibrations.DamageReceived", "Duration", 1f, "Length of time to vibrate for");
VibrateDamageReceivedAmplifier = ConfigFile.Bind<float>("Vibrations.DamageReceived", "Amplifier", 0f, "Change the amplification of vibration");
VibrateKilledEnabled = ConfigFile.Bind<bool>("Vibrations.PlayerKilled", "Enabled", false, "Vibrate when you die");
VibrateKilledDuration = ConfigFile.Bind<float>("Vibrations.PlayerKilled", "Duration", 1f, "Length of time to vibrate for");
VibrateKilledStrength = ConfigFile.Bind<float>("Vibrations.PlayerKilled", "Strength", 1f, "Change the strength of vibration");
PingScanEnabled = ConfigFile.Bind<bool>("Vibrations.PingScan", "Enabled", false, "Vibrate when you press right click");
PingScanDuration = ConfigFile.Bind<float>("Vibrations.PingScan", "Duration", 0.3f, "Length of time to vibrate for");
PingScanStrength = ConfigFile.Bind<float>("Vibrations.PingScan", "Strength", 0.3f, "Change the strength of vibration");
VibrateItemChargerChargeEnabled = ConfigFile.Bind<bool>("Vibrations.ItemCharge", "Enabled", true, "Vibrate when you charge an item");
VibrateItemChargerChargeDuration = ConfigFile.Bind<float>("Vibrations.ItemCharge", "Duration", 1f, "Length of time to vibrate for");
VibrateItemChargerChargeStrength = ConfigFile.Bind<float>("Vibrations.ItemCharge", "Strength", 0.4f, "Change the strength of vibration");
VibrateScreenShakeEnabled = ConfigFile.Bind<bool>("Vibrations.ShakeScreen", "Enabled", true, "Vibrate when your screen shakes");
VibrateScreenShakeDuration = ConfigFile.Bind<float>("Vibrations.ShakeScreen", "Duration", 1f, "Length of time to vibrate for");
VibrateScreenShakeAmplifier = ConfigFile.Bind<float>("Vibrations.ShakeScreen", "Amplifier", 0f, "Change the amplification of vibration");
AirhornEnabled = ConfigFile.Bind<bool>("Vibrations.Airhorn", "Enabled", false, "Vibrate when someone uses the airhorn");
AirhornDuration = ConfigFile.Bind<float>("Vibrations.Airhorn", "Duration", 1f, "Length of time to vibrate for");
AirhornStrength = ConfigFile.Bind<float>("Vibrations.Airhorn", "Strength", 0.1f, "Change the intensity of vibration");
ShipHornEnabled = ConfigFile.Bind<bool>("Vibrations.ShipHorn", "Enabled", true, "Vibrate when someone airs the ships horn");
ShipHornStrength = ConfigFile.Bind<float>("Vibrations.ShipHorn", "Strength", 0.5f, "Change the intensity of vibration");
FlashbangEnabled = ConfigFile.Bind<bool>("Vibrations.Flashbang", "Enabled", true, "Vibrate when a flashbang goes off");
FlashbangStrength = ConfigFile.Bind<float>("Vibrations.Flashbang", "Strength", 0.5f, "Change the intensity of vibration");
}
}
public class DeviceManager
{
private List<ButtplugClientDevice> ConnectedDevices { get; set; }
private ButtplugClient ButtplugClient { get; set; }
public DeviceManager(string clientName)
{
//IL_0013: Unknown result type (might be due to invalid IL or missing references)
//IL_001d: Expected O, but got Unknown
ConnectedDevices = new List<ButtplugClientDevice>();
ButtplugClient = new ButtplugClient(clientName);
Plugin.Mls.LogInfo((object)("BP client created for " + clientName));
ButtplugClient.DeviceAdded += HandleDeviceAdded;
ButtplugClient.DeviceRemoved += HandleDeviceRemoved;
}
public bool IsConnected()
{
return ButtplugClient.Connected;
}
public async void ConnectDevices()
{
if (ButtplugClient.Connected)
{
return;
}
try
{
Plugin.Mls.LogInfo((object)("Attempting to connect to Intiface server at " + Config.ServerUri.Value));
await ButtplugClient.ConnectAsync((IButtplugClientConnector)new ButtplugWebsocketConnector(new Uri(Config.ServerUri.Value)), default(CancellationToken));
Plugin.Mls.LogInfo((object)"Connection successful. Beginning scan for devices");
await ButtplugClient.StartScanningAsync(default(CancellationToken));
}
catch (ButtplugException val)
{
ButtplugException arg = val;
Plugin.Mls.LogError((object)"Attempt to connect to devices failed. Ensure Intiface is running and attempt to reconnect from the 'Devices' section in the mod's in-game settings.");
Plugin.Mls.LogDebug((object)$"ButtplugIO error occured while connecting devices: {arg}");
}
}
public void VibrateConnectedDevicesWithDuration(double intensity, float time)
{
intensity += Config.VibrateAmplifier.Value;
ConnectedDevices.ForEach(Action);
async void Action(ButtplugClientDevice device)
{
await device.VibrateAsync((double)Mathf.Clamp((float)intensity, 0f, 1f));
await Task.Delay((int)(time * 1000f));
await device.VibrateAsync(0.0);
}
}
public void VibrateConnectedDevices(double intensity)
{
intensity += Config.VibrateAmplifier.Value;
ConnectedDevices.ForEach(Action);
async void Action(ButtplugClientDevice device)
{
await device.VibrateAsync((double)Mathf.Clamp((float)intensity, 0f, 1f));
}
}
public void StopConnectedDevices()
{
ConnectedDevices.ForEach(async delegate(ButtplugClientDevice device)
{
await device.Stop();
});
}
internal void CleanUp()
{
StopConnectedDevices();
}
private void HandleDeviceAdded(object sender, DeviceAddedEventArgs args)
{
if (!IsVibratableDevice(args.Device))
{
Plugin.Mls.LogInfo((object)(args.Device.Name + " was detected but ignored due to it not being vibratable."));
return;
}
Plugin.Mls.LogInfo((object)(args.Device.Name + " connected to client " + ButtplugClient.Name));
ConnectedDevices.Add(args.Device);
}
private void HandleDeviceRemoved(object sender, DeviceRemovedEventArgs args)
{
if (IsVibratableDevice(args.Device))
{
Plugin.Mls.LogInfo((object)(args.Device.Name + " disconnected from client " + ButtplugClient.Name));
ConnectedDevices.Remove(args.Device);
}
}
private bool IsVibratableDevice(ButtplugClientDevice device)
{
return device.VibrateAttributes.Count > 0;
}
}
}
namespace Costura
{
[CompilerGenerated]
internal static class AssemblyLoader
{
private static object nullCacheLock = new object();
private static Dictionary<string, bool> nullCache = new Dictionary<string, bool>();
private static Dictionary<string, string> assemblyNames = new Dictionary<string, string>();
private static Dictionary<string, string> symbolNames = new Dictionary<string, string>();
private static int isAttached;
private static string CultureToString(CultureInfo culture)
{
if (culture == null)
{
return "";
}
return culture.Name;
}
private static Assembly ReadExistingAssembly(AssemblyName name)
{
AppDomain currentDomain = AppDomain.CurrentDomain;
Assembly[] assemblies = currentDomain.GetAssemblies();
Assembly[] array = assemblies;
foreach (Assembly assembly in array)
{
AssemblyName name2 = assembly.GetName();
if (string.Equals(name2.Name, name.Name, StringComparison.InvariantCultureIgnoreCase) && string.Equals(CultureToString(name2.CultureInfo), CultureToString(name.CultureInfo), StringComparison.InvariantCultureIgnoreCase))
{
return assembly;
}
}
return null;
}
private static void CopyTo(Stream source, Stream destination)
{
byte[] array = new byte[81920];
int count;
while ((count = source.Read(array, 0, array.Length)) != 0)
{
destination.Write(array, 0, count);
}
}
private static Stream LoadStream(string fullName)
{
Assembly executingAssembly = Assembly.GetExecutingAssembly();
if (fullName.EndsWith(".compressed"))
{
using (Stream stream = executingAssembly.GetManifestResourceStream(fullName))
{
using DeflateStream source = new DeflateStream(stream, CompressionMode.Decompress);
MemoryStream memoryStream = new MemoryStream();
CopyTo(source, memoryStream);
memoryStream.Position = 0L;
return memoryStream;
}
}
return executingAssembly.GetManifestResourceStream(fullName);
}
private static Stream LoadStream(Dictionary<string, string> resourceNames, string name)
{
if (resourceNames.TryGetValue(name, out var value))
{
return LoadStream(value);
}
return null;
}
private static byte[] ReadStream(Stream stream)
{
byte[] array = new byte[stream.Length];
stream.Read(array, 0, array.Length);
return array;
}
private static Assembly ReadFromEmbeddedResources(Dictionary<string, string> assemblyNames, Dictionary<string, string> symbolNames, AssemblyName requestedAssemblyName)
{
string text = requestedAssemblyName.Name.ToLowerInvariant();
if (requestedAssemblyName.CultureInfo != null && !string.IsNullOrEmpty(requestedAssemblyName.CultureInfo.Name))
{
text = requestedAssemblyName.CultureInfo.Name + "." + text;
}
byte[] rawAssembly;
using (Stream stream = LoadStream(assemblyNames, text))
{
if (stream == null)
{
return null;
}
rawAssembly = ReadStream(stream);
}
using (Stream stream2 = LoadStream(symbolNames, text))
{
if (stream2 != null)
{
byte[] rawSymbolStore = ReadStream(stream2);
return Assembly.Load(rawAssembly, rawSymbolStore);
}
}
return Assembly.Load(rawAssembly);
}
public static Assembly ResolveAssembly(object sender, ResolveEventArgs e)
{
lock (nullCacheLock)
{
if (nullCache.ContainsKey(e.Name))
{
return null;
}
}
AssemblyName assemblyName = new AssemblyName(e.Name);
Assembly assembly = ReadExistingAssembly(assemblyName);
if ((object)assembly != null)
{
return assembly;
}
assembly = ReadFromEmbeddedResources(assemblyNames, symbolNames, assemblyName);
if ((object)assembly == null)
{
lock (nullCacheLock)
{
nullCache[e.Name] = true;
}
if ((assemblyName.Flags & AssemblyNameFlags.Retargetable) != 0)
{
assembly = Assembly.Load(assemblyName);
}
}
return assembly;
}
static AssemblyLoader()
{
assemblyNames.Add("buttplug.client.connectors.websocketconnector", "costura.buttplug.client.connectors.websocketconnector.dll.compressed");
assemblyNames.Add("buttplug", "costura.buttplug.dll.compressed");
assemblyNames.Add("deniszykov.websocketlistener", "costura.deniszykov.websocketlistener.dll.compressed");
assemblyNames.Add("system.appcontext", "costura.system.appcontext.dll.compressed");
assemblyNames.Add("system.collections.concurrent", "costura.system.collections.concurrent.dll.compressed");
assemblyNames.Add("system.collections", "costura.system.collections.dll.compressed");
assemblyNames.Add("system.collections.nongeneric", "costura.system.collections.nongeneric.dll.compressed");
assemblyNames.Add("system.collections.specialized", "costura.system.collections.specialized.dll.compressed");
assemblyNames.Add("system.componentmodel.annotations", "costura.system.componentmodel.annotations.dll.compressed");
assemblyNames.Add("system.componentmodel.composition", "costura.system.componentmodel.composition.dll.compressed");
assemblyNames.Add("system.componentmodel", "costura.system.componentmodel.dll.compressed");
assemblyNames.Add("system.componentmodel.eventbasedasync", "costura.system.componentmodel.eventbasedasync.dll.compressed");
assemblyNames.Add("system.componentmodel.primitives", "costura.system.componentmodel.primitives.dll.compressed");
assemblyNames.Add("system.componentmodel.typeconverter", "costura.system.componentmodel.typeconverter.dll.compressed");
assemblyNames.Add("system.console", "costura.system.console.dll.compressed");
assemblyNames.Add("system.core", "costura.system.core.dll.compressed");
assemblyNames.Add("system.data.common", "costura.system.data.common.dll.compressed");
assemblyNames.Add("system.data", "costura.system.data.dll.compressed");
assemblyNames.Add("system.diagnostics.contracts", "costura.system.diagnostics.contracts.dll.compressed");
assemblyNames.Add("system.diagnostics.debug", "costura.system.diagnostics.debug.dll.compressed");
assemblyNames.Add("system.diagnostics.diagnosticsource", "costura.system.diagnostics.diagnosticsource.dll.compressed");
assemblyNames.Add("system.diagnostics.fileversioninfo", "costura.system.diagnostics.fileversioninfo.dll.compressed");
assemblyNames.Add("system.diagnostics.process", "costura.system.diagnostics.process.dll.compressed");
assemblyNames.Add("system.diagnostics.stacktrace", "costura.system.diagnostics.stacktrace.dll.compressed");
assemblyNames.Add("system.diagnostics.textwritertracelistener", "costura.system.diagnostics.textwritertracelistener.dll.compressed");
assemblyNames.Add("system.diagnostics.tools", "costura.system.diagnostics.tools.dll.compressed");
assemblyNames.Add("system.diagnostics.tracesource", "costura.system.diagnostics.tracesource.dll.compressed");
assemblyNames.Add("system.diagnostics.tracing", "costura.system.diagnostics.tracing.dll.compressed");
assemblyNames.Add("system.drawing", "costura.system.drawing.dll.compressed");
assemblyNames.Add("system.drawing.primitives", "costura.system.drawing.primitives.dll.compressed");
assemblyNames.Add("system.dynamic.runtime", "costura.system.dynamic.runtime.dll.compressed");
assemblyNames.Add("system.globalization.calendars", "costura.system.globalization.calendars.dll.compressed");
assemblyNames.Add("system.globalization", "costura.system.globalization.dll.compressed");
assemblyNames.Add("system.globalization.extensions", "costura.system.globalization.extensions.dll.compressed");
assemblyNames.Add("system.io.compression", "costura.system.io.compression.dll.compressed");
assemblyNames.Add("system.io.compression.filesystem", "costura.system.io.compression.filesystem.dll.compressed");
assemblyNames.Add("system.io.compression.zipfile", "costura.system.io.compression.zipfile.dll.compressed");
assemblyNames.Add("system.io", "costura.system.io.dll.compressed");
assemblyNames.Add("system.io.filesystem", "costura.system.io.filesystem.dll.compressed");
assemblyNames.Add("system.io.filesystem.driveinfo", "costura.system.io.filesystem.driveinfo.dll.compressed");
assemblyNames.Add("system.io.filesystem.primitives", "costura.system.io.filesystem.primitives.dll.compressed");
assemblyNames.Add("system.io.filesystem.watcher", "costura.system.io.filesystem.watcher.dll.compressed");
assemblyNames.Add("system.io.isolatedstorage", "costura.system.io.isolatedstorage.dll.compressed");
assemblyNames.Add("system.io.memorymappedfiles", "costura.system.io.memorymappedfiles.dll.compressed");
assemblyNames.Add("system.io.pipes", "costura.system.io.pipes.dll.compressed");
assemblyNames.Add("system.io.unmanagedmemorystream", "costura.system.io.unmanagedmemorystream.dll.compressed");
assemblyNames.Add("system.linq", "costura.system.linq.dll.compressed");
assemblyNames.Add("system.linq.expressions", "costura.system.linq.expressions.dll.compressed");
assemblyNames.Add("system.linq.parallel", "costura.system.linq.parallel.dll.compressed");
assemblyNames.Add("system.linq.queryable", "costura.system.linq.queryable.dll.compressed");
assemblyNames.Add("system.net.http", "costura.system.net.http.dll.compressed");
assemblyNames.Add("system.net.nameresolution", "costura.system.net.nameresolution.dll.compressed");
assemblyNames.Add("system.net.networkinformation", "costura.system.net.networkinformation.dll.compressed");
assemblyNames.Add("system.net.ping", "costura.system.net.ping.dll.compressed");
assemblyNames.Add("system.net.primitives", "costura.system.net.primitives.dll.compressed");
assemblyNames.Add("system.net.requests", "costura.system.net.requests.dll.compressed");
assemblyNames.Add("system.net.security", "costura.system.net.security.dll.compressed");
assemblyNames.Add("system.net.sockets", "costura.system.net.sockets.dll.compressed");
assemblyNames.Add("system.net.webheadercollection", "costura.system.net.webheadercollection.dll.compressed");
assemblyNames.Add("system.net.websockets.client", "costura.system.net.websockets.client.dll.compressed");
assemblyNames.Add("system.net.websockets", "costura.system.net.websockets.dll.compressed");
assemblyNames.Add("system.numerics", "costura.system.numerics.dll.compressed");
assemblyNames.Add("system.objectmodel", "costura.system.objectmodel.dll.compressed");
assemblyNames.Add("system.reflection", "costura.system.reflection.dll.compressed");
assemblyNames.Add("system.reflection.emit", "costura.system.reflection.emit.dll.compressed");
assemblyNames.Add("system.reflection.emit.ilgeneration", "costura.system.reflection.emit.ilgeneration.dll.compressed");
assemblyNames.Add("system.reflection.emit.lightweight", "costura.system.reflection.emit.lightweight.dll.compressed");
assemblyNames.Add("system.reflection.extensions", "costura.system.reflection.extensions.dll.compressed");
assemblyNames.Add("system.reflection.primitives", "costura.system.reflection.primitives.dll.compressed");
assemblyNames.Add("system.resources.reader", "costura.system.resources.reader.dll.compressed");
assemblyNames.Add("system.resources.resourcemanager", "costura.system.resources.resourcemanager.dll.compressed");
assemblyNames.Add("system.resources.writer", "costura.system.resources.writer.dll.compressed");
assemblyNames.Add("system.runtime.compilerservices.unsafe", "costura.system.runtime.compilerservices.unsafe.dll.compressed");
assemblyNames.Add("system.runtime.compilerservices.visualc", "costura.system.runtime.compilerservices.visualc.dll.compressed");
assemblyNames.Add("system.runtime", "costura.system.runtime.dll.compressed");
assemblyNames.Add("system.runtime.extensions", "costura.system.runtime.extensions.dll.compressed");
assemblyNames.Add("system.runtime.handles", "costura.system.runtime.handles.dll.compressed");
assemblyNames.Add("system.runtime.interopservices", "costura.system.runtime.interopservices.dll.compressed");
assemblyNames.Add("system.runtime.interopservices.runtimeinformation", "costura.system.runtime.interopservices.runtimeinformation.dll.compressed");
assemblyNames.Add("system.runtime.interopservices.windowsruntime", "costura.system.runtime.interopservices.windowsruntime.dll.compressed");
assemblyNames.Add("system.runtime.numerics", "costura.system.runtime.numerics.dll.compressed");
assemblyNames.Add("system.runtime.serialization", "costura.system.runtime.serialization.dll.compressed");
assemblyNames.Add("system.runtime.serialization.formatters", "costura.system.runtime.serialization.formatters.dll.compressed");
assemblyNames.Add("system.runtime.serialization.json", "costura.system.runtime.serialization.json.dll.compressed");
assemblyNames.Add("system.runtime.serialization.primitives", "costura.system.runtime.serialization.primitives.dll.compressed");
assemblyNames.Add("system.runtime.serialization.xml", "costura.system.runtime.serialization.xml.dll.compressed");
assemblyNames.Add("system.security.claims", "costura.system.security.claims.dll.compressed");
assemblyNames.Add("system.security.cryptography.algorithms", "costura.system.security.cryptography.algorithms.dll.compressed");
assemblyNames.Add("system.security.cryptography.csp", "costura.system.security.cryptography.csp.dll.compressed");
assemblyNames.Add("system.security.cryptography.encoding", "costura.system.security.cryptography.encoding.dll.compressed");
assemblyNames.Add("system.security.cryptography.primitives", "costura.system.security.cryptography.primitives.dll.compressed");
assemblyNames.Add("system.security.cryptography.x509certificates", "costura.system.security.cryptography.x509certificates.dll.compressed");
assemblyNames.Add("system.security.principal", "costura.system.security.principal.dll.compressed");
assemblyNames.Add("system.security.securestring", "costura.system.security.securestring.dll.compressed");
assemblyNames.Add("system.servicemodel.duplex", "costura.system.servicemodel.duplex.dll.compressed");
assemblyNames.Add("system.servicemodel.http", "costura.system.servicemodel.http.dll.compressed");
assemblyNames.Add("system.servicemodel.nettcp", "costura.system.servicemodel.nettcp.dll.compressed");
assemblyNames.Add("system.servicemodel.primitives", "costura.system.servicemodel.primitives.dll.compressed");
assemblyNames.Add("system.servicemodel.security", "costura.system.servicemodel.security.dll.compressed");
assemblyNames.Add("system.text.encoding", "costura.system.text.encoding.dll.compressed");
assemblyNames.Add("system.text.encoding.extensions", "costura.system.text.encoding.extensions.dll.compressed");
assemblyNames.Add("system.text.regularexpressions", "costura.system.text.regularexpressions.dll.compressed");
assemblyNames.Add("system.threading.channels", "costura.system.threading.channels.dll.compressed");
assemblyNames.Add("system.threading", "costura.system.threading.dll.compressed");
assemblyNames.Add("system.threading.overlapped", "costura.system.threading.overlapped.dll.compressed");
assemblyNames.Add("system.threading.tasks", "costura.system.threading.tasks.dll.compressed");
assemblyNames.Add("system.threading.tasks.extensions", "costura.system.threading.tasks.extensions.dll.compressed");
assemblyNames.Add("system.threading.tasks.parallel", "costura.system.threading.tasks.parallel.dll.compressed");
assemblyNames.Add("system.threading.thread", "costura.system.threading.thread.dll.compressed");
assemblyNames.Add("system.threading.threadpool", "costura.system.threading.threadpool.dll.compressed");
assemblyNames.Add("system.threading.timer", "costura.system.threading.timer.dll.compressed");
assemblyNames.Add("system.valuetuple", "costura.system.valuetuple.dll.compressed");
assemblyNames.Add("system.xml", "costura.system.xml.dll.compressed");
assemblyNames.Add("system.xml.linq", "costura.system.xml.linq.dll.compressed");
assemblyNames.Add("system.xml.readerwriter", "costura.system.xml.readerwriter.dll.compressed");
assemblyNames.Add("system.xml.xdocument", "costura.system.xml.xdocument.dll.compressed");
assemblyNames.Add("system.xml.xmldocument", "costura.system.xml.xmldocument.dll.compressed");
assemblyNames.Add("system.xml.xmlserializer", "costura.system.xml.xmlserializer.dll.compressed");
assemblyNames.Add("system.xml.xpath", "costura.system.xml.xpath.dll.compressed");
assemblyNames.Add("system.xml.xpath.xdocument", "costura.system.xml.xpath.xdocument.dll.compressed");
}
public static void Attach()
{
if (Interlocked.Exchange(ref isAttached, 1) == 1)
{
return;
}
AppDomain currentDomain = AppDomain.CurrentDomain;
currentDomain.AssemblyResolve += delegate(object sender, ResolveEventArgs e)
{
lock (nullCacheLock)
{
if (nullCache.ContainsKey(e.Name))
{
return null;
}
}
AssemblyName assemblyName = new AssemblyName(e.Name);
Assembly assembly = ReadExistingAssembly(assemblyName);
if ((object)assembly != null)
{
return assembly;
}
assembly = ReadFromEmbeddedResources(assemblyNames, symbolNames, assemblyName);
if ((object)assembly == null)
{
lock (nullCacheLock)
{
nullCache[e.Name] = true;
}
if ((assemblyName.Flags & AssemblyNameFlags.Retargetable) != 0)
{
assembly = Assembly.Load(assemblyName);
}
}
return assembly;
};
}
}
}
internal class LethalVibrations_ProcessedByFody
{
internal const string FodyVersion = "6.8.0.0";
internal const string Costura = "5.7.0";
}