Please disclose if your mod was created primarily using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of CustomTvVideos v0.1.3
CustomTvVideos.dll
Decompiled 2 years agousing System; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Logging; using CustomTvVideos.Patches; using GameNetcodeStuff; using HarmonyLib; using JetBrains.Annotations; using Microsoft.CodeAnalysis; using Unity.Netcode; using UnityEngine; using UnityEngine.Video; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("CustomTvVideos")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyDescription("Allowes you to set custom videos for the tv")] [assembly: AssemblyFileVersion("0.1.3.0")] [assembly: AssemblyInformationalVersion("0.1.3")] [assembly: AssemblyProduct("CustomTvVideos")] [assembly: AssemblyTitle("CustomTvVideos")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.1.3.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)] internal sealed class NullableAttribute : Attribute { public readonly byte[] NullableFlags; public NullableAttribute(byte P_0) { NullableFlags = new byte[1] { P_0 }; } public NullableAttribute(byte[] P_0) { NullableFlags = P_0; } } [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)] internal sealed class NullableContextAttribute : Attribute { public readonly byte Flag; public NullableContextAttribute(byte P_0) { Flag = P_0; } } [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 CustomTvVideos { internal interface ITryGet<T> { bool TryGetValue(out T? value); } public class MyPluginInfo { public const string PLUGIN_GUID = "sakura.custom-tv-videos"; public const string PLUGIN_NAME = "CustomTvVideos"; public const string PLUGIN_VERSION = "0.1.3"; } [BepInPlugin("sakura.custom-tv-videos", "CustomTvVideos", "0.1.3")] public class CustomTvVideos : BaseUnityPlugin { private static string videosDir = Path.Combine(Paths.BepInExRootPath, "CustomTvVideos", "VideoClips"); private static ManualLogSource logger; private Harmony harmony = new Harmony("sakura.custom-tv-videos"); [UsedImplicitly] private void Awake() { try { logger = ((BaseUnityPlugin)this).Logger; CreateDirectoryIfItDoesNotExist(); if (LoadClips()) { harmony.PatchAll(typeof(TvScriptPatch)); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Plugin sakura.custom-tv-videos is loaded!"); } } catch (Exception arg) { ((BaseUnityPlugin)this).Logger.LogError((object)$"Encountered an error in Awake()\n {arg}"); } } private bool LoadClips() { if (new VideoGetter(((BaseUnityPlugin)this).Logger).TryGetValue(out var value)) { List<FileInfo> list = new List<FileInfo>(); string[] array = value; foreach (string fileName in array) { list.Add(new FileInfo(fileName)); } FileInfo[] array2 = list.ToArray(); ((BaseUnityPlugin)this).Logger.LogInfo((object)$"Got {value.Length} video files."); if (array2.Length == 0) { ((BaseUnityPlugin)this).Logger.LogInfo((object)"No video clips where loaded, Aborting..."); ((Component)this).gameObject.SetActive(false); return false; } TvScriptPatch.Init(array2, logger); return true; } ((BaseUnityPlugin)this).Logger.LogFatal((object)"Unable to get video clips."); ((Component)this).gameObject.SetActive(false); return false; } private void CreateDirectoryIfItDoesNotExist() { Directory.CreateDirectory(videosDir); ((BaseUnityPlugin)this).Logger.LogInfo((object)("Video Directory: " + videosDir)); } } internal class VideoGetter : ITryGet<string[]> { [Flags] private enum PlatformFlag { Unknown = 0, Windows = 1, MacOS = 2, Linux = 4 } private struct FileType { public string Extension; public PlatformFlag Platform; public FileType(string extension, PlatformFlag platform) { Extension = extension; Platform = platform; } } private ManualLogSource logger; private static string videosDir = Path.Combine(Paths.BepInExRootPath, "CustomTvVideos", "VideoClips"); private static FileType[] videoFileTypes = new FileType[12] { new FileType(".asf", PlatformFlag.Windows), new FileType(".avi", PlatformFlag.Windows), new FileType(".dv", PlatformFlag.Windows | PlatformFlag.MacOS), new FileType(".mv4", PlatformFlag.Windows | PlatformFlag.MacOS), new FileType(".mov", PlatformFlag.Windows | PlatformFlag.MacOS), new FileType(".mp4", PlatformFlag.Windows | PlatformFlag.MacOS), new FileType(".mpg", PlatformFlag.Windows | PlatformFlag.MacOS), new FileType(".mpeg", PlatformFlag.Windows | PlatformFlag.MacOS), new FileType(".ogv", PlatformFlag.Windows | PlatformFlag.MacOS | PlatformFlag.Linux), new FileType(".vp8", PlatformFlag.Windows | PlatformFlag.MacOS | PlatformFlag.Linux), new FileType(".webm", PlatformFlag.Windows | PlatformFlag.MacOS | PlatformFlag.Linux), new FileType(".wmv", PlatformFlag.Windows) }; public VideoGetter(ManualLogSource logger) { this.logger = logger; } private static bool IsSupportedOnCurrentPlatform(string extension, PlatformFlag platform) { return videoFileTypes.Any((FileType x) => string.Compare(x.Extension, extension) == 0 && x.Platform.HasFlag(platform)); } private string[] GetSupportedVideoFiles(string dir, PlatformFlag platform) { List<string> list = new List<string>(); foreach (string item in Directory.EnumerateFiles(dir)) { FileInfo fileInfo = new FileInfo(item); if (fileInfo.Exists) { if (IsSupportedOnCurrentPlatform(fileInfo.Extension, platform)) { list.Add(fileInfo.FullName); } else { logger.LogWarning((object)("File: \"" + fileInfo.Name + "\" Is not supported.")); } } } return list.ToArray(); } public bool TryGetValue(out string[] value) { try { PlatformFlag currentPlatform = GetCurrentPlatform(); string[] supportedVideoFiles = GetSupportedVideoFiles(videosDir, currentPlatform); value = supportedVideoFiles; return true; } catch (Exception ex) { logger.LogError((object)ex); value = null; return false; } } private static PlatformFlag GetCurrentPlatform() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0008: Invalid comparison between Unknown and I4 //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Invalid comparison between Unknown and I4 //IL_000e: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Invalid comparison between Unknown and I4 //IL_0026: Unknown result type (might be due to invalid IL or missing references) RuntimePlatform platform = Application.platform; if ((int)platform != 1) { if ((int)platform != 2) { if ((int)platform == 13) { return PlatformFlag.Linux; } throw new PlatformNotSupportedException($"Platform: \"{platform}\" is not supported."); } return PlatformFlag.Windows; } return PlatformFlag.MacOS; } } public static class PluginInfo { public const string PLUGIN_GUID = "CustomTvVideos"; public const string PLUGIN_NAME = "CustomTvVideos"; public const string PLUGIN_VERSION = "0.1.3"; } } namespace CustomTvVideos.Patches { [HarmonyPatch(typeof(PlayerControllerB))] internal static class PlayerControllerBPatch { } [HarmonyPatch(typeof(TVScript))] internal class TvScriptPatch { private static ManualLogSource logger; private static FileInfo[] videoFiles; private static int currentClip; private static bool setupDone; private static bool wasTvOnLastFrame; private static float currentClipTime; internal static void Init(FileInfo[] videos, ManualLogSource logSource) { videoFiles = videos; logger = logSource; } private static void IncrementCurrentClip() { if (currentClip + 1 >= videoFiles.Length) { currentClip = 0; } else { currentClip++; } } private static void SetVideo(TVScript tv, FileInfo videoFile) { tv.video.clip = null; tv.tvSFX.clip = null; tv.video.url = "file://" + videoFile.FullName; tv.video.source = (VideoSource)1; tv.video.controlledAudioTrackCount = 1; tv.video.audioOutputMode = (VideoAudioOutputMode)1; tv.video.SetTargetAudioSource((ushort)0, tv.tvSFX); tv.video.Prepare(); tv.video.Stop(); tv.tvSFX.Stop(); } [HarmonyPatch(typeof(TVScript), "TVFinishedClip")] [HarmonyPrefix] private static bool TV_TVFinishedClip(TVScript __instance, VideoPlayer source) { logger.LogInfo((object)"TV_TVFinishedClip"); if (__instance.tvOn && !GameNetworkManager.Instance.localPlayerController.isInsideFactory) { IncrementCurrentClip(); FileInfo fileInfo = videoFiles[currentClip]; logger.LogInfo((object)("Playing " + fileInfo.FullName)); SetVideo(__instance, fileInfo); } return false; } [HarmonyPatch(typeof(TVScript), "TurnTVOnOff")] [HarmonyPrefix] private static bool TV_TurnTVOnOff(TVScript __instance, bool on) { logger.LogInfo((object)"TV_TurnTVOnOff"); __instance.tvOn = on; if (!setupDone) { __instance.video.clip = null; __instance.tvSFX.clip = null; IncrementCurrentClip(); FileInfo videoFile = videoFiles[currentClip]; SetVideo(__instance, videoFile); setupDone = true; } if (on) { IncrementCurrentClip(); FileInfo videoFile2 = videoFiles[currentClip]; SetVideo(__instance, videoFile2); SetTVScreenMaterial(__instance, b: true); __instance.video.Play(); __instance.tvSFX.Play(); __instance.tvSFX.PlayOneShot(__instance.switchTVOn); WalkieTalkie.TransmitOneShotAudio(__instance.tvSFX, __instance.switchTVOn, 1f); } else { SetTVScreenMaterial(__instance, b: false); __instance.tvSFX.Stop(); __instance.tvSFX.PlayOneShot(__instance.switchTVOff); __instance.video.Stop(); WalkieTalkie.TransmitOneShotAudio(__instance.tvSFX, __instance.switchTVOff, 1f); } return false; } [HarmonyPatch(typeof(TVScript), "Update")] [HarmonyPrefix] private static bool TV_Update(TVScript __instance) { if (NetworkManager.Singleton.ShutdownInProgress || (Object)(object)GameNetworkManager.Instance.localPlayerController == (Object)null) { return false; } if ((!__instance.tvOn || GameNetworkManager.Instance.localPlayerController.isInsideFactory) && wasTvOnLastFrame) { wasTvOnLastFrame = false; SetTVScreenMaterial(__instance, b: false); currentClipTime = (float)__instance.video.time; __instance.video.Stop(); } return false; } private static void SetTVScreenMaterial(TVScript instance, bool b) { ((object)instance).GetType().GetMethod("SetTVScreenMaterial", BindingFlags.Instance | BindingFlags.NonPublic).Invoke(instance, new object[1] { b }); } } }