Decompiled source of WeatherscannerTV v1.1.1

plugins/TVLoaderExtended.dll

Decompiled a week ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
using System.Runtime.Versioning;
using BepInEx;
using BepInEx.Logging;
using HarmonyLib;
using TVLoaderExtended.Utils;
using Unity.Netcode;
using UnityEngine;
using UnityEngine.Video;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: AssemblyTitle("TVLoaderExtended")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("TVLoaderExtended")]
[assembly: AssemblyCopyright("Copyright ©  2024")]
[assembly: AssemblyTrademark("")]
[assembly: ComVisible(false)]
[assembly: Guid("5F5ACB51-F9E6-4E85-B3A4-028FEE7B0650")]
[assembly: AssemblyFileVersion("1.1.3")]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyVersion("1.1.3.0")]
namespace TVLoaderExtended
{
	[BepInPlugin("Filigrani.TVLoaderExtended", "TVLoaderExtended", "1.1.3")]
	public class TVLoaderExtendedPlugin : BaseUnityPlugin
	{
		private const string MyGUID = "Filigrani.TVLoaderExtended";

		private const string PluginName = "TVLoaderExtended";

		private const string VersionString = "1.1.3";

		private static readonly Harmony Harmony = new Harmony("Filigrani.TVLoaderExtended");

		public static ManualLogSource Log = new ManualLogSource("TVLoaderExtended");

		private void Awake()
		{
			Log = ((BaseUnityPlugin)this).Logger;
			Harmony.PatchAll();
			VideoManager.Load();
			((BaseUnityPlugin)this).Logger.LogInfo((object)string.Format("PluginName: {0}, VersionString: {1} is loaded. Video Count: {2}", "TVLoaderExtended", "1.1.3", VideoManager.Videos.Count));
		}
	}
}
namespace TVLoaderExtended.Utils
{
	internal static class VideoManager
	{
		public static List<string> Videos = new List<string>();

		public static void Load()
		{
			Videos.Clear();
			string[] directories = Directory.GetDirectories(Paths.PluginPath);
			string[] array = directories;
			foreach (string text in array)
			{
				string path = Path.Combine(Paths.PluginPath, text, "Television Videos");
				if (Directory.Exists(path))
				{
					string[] files = Directory.GetFiles(path, "*.mp4");
					Videos.AddRange(files);
					TVLoaderExtendedPlugin.Log.LogInfo((object)$"{text} has {files.Length} videos.");
				}
			}
			string path2 = Path.Combine(Paths.PluginPath, "Television Videos");
			if (!Directory.Exists(path2))
			{
				Directory.CreateDirectory(path2);
			}
			string[] files2 = Directory.GetFiles(path2, "*.mp4");
			Videos.AddRange(files2);
			TVLoaderExtendedPlugin.Log.LogInfo((object)$"Global has {files2.Length} videos.");
			TVLoaderExtendedPlugin.Log.LogInfo((object)$"Loaded {Videos.Count} total.");
		}
	}
}
namespace TVLoaderExtended.Patches
{
	[HarmonyPatch(typeof(TVScript))]
	internal class TVScriptPatches
	{
		[Serializable]
		[CompilerGenerated]
		private sealed class <>c
		{
			public static readonly <>c <>9 = new <>c();

			public static EventHandler <>9__22_0;

			internal void <PrepareVideo>b__22_0(VideoPlayer source)
			{
				TVLoaderExtendedPlugin.Log.LogInfo((object)"Prepared video!");
			}
		}

		private static FieldInfo currentClipProperty = typeof(TVScript).GetField("currentClip", BindingFlags.Instance | BindingFlags.NonPublic);

		private static FieldInfo currentTimeProperty = typeof(TVScript).GetField("currentClipTime", BindingFlags.Instance | BindingFlags.NonPublic);

		private static FieldInfo wasTvOnLastFrameProp = typeof(TVScript).GetField("wasTvOnLastFrame", BindingFlags.Instance | BindingFlags.NonPublic);

		private static FieldInfo timeSinceTurningOffTVProp = typeof(TVScript).GetField("timeSinceTurningOffTV", BindingFlags.Instance | BindingFlags.NonPublic);

		private static MethodInfo setMatMethod = typeof(TVScript).GetMethod("SetTVScreenMaterial", BindingFlags.Instance | BindingFlags.NonPublic);

		private static MethodInfo onEnableMethod = typeof(TVScript).GetMethod("OnEnable", BindingFlags.Instance | BindingFlags.NonPublic);

		private static bool s_EverWasOn = false;

		private static RenderTexture renderTexture;

		private static List<string> m_Videos = new List<string>();

		private static int s_LastSeed = 0;

		private static int s_LastSeenIndex = -1;

		private static string GetVideoPath(int Index)
		{
			return GetFullPath(m_Videos[Index]);
		}

		private static int GetSeed(TVScript Instance)
		{
			return ((NetworkBehaviour)Instance).NetworkObjectId.ToString().GetHashCode();
		}

		private static void Shuffle<T>(List<T> List, int Seed)
		{
			Random random = new Random(Seed);
			int count = List.Count;
			for (int i = 0; i < count - 1; i++)
			{
				int index = i + random.Next(count - i);
				T value = List[index];
				List[index] = List[i];
				List[i] = value;
			}
		}

		public static List<string> GetClearList(List<string> Pathes)
		{
			List<string> list = new List<string>();
			for (int i = 0; i < Pathes.Count; i++)
			{
				string text = Pathes[i];
				string[] separator = new string[1] { "plugins" };
				string[] array = text.Split(separator, StringSplitOptions.None);
				string item = array[1];
				list.Add(item);
			}
			list.Sort();
			return list;
		}

		public static string GetFullPath(string ShortPath)
		{
			foreach (string video in VideoManager.Videos)
			{
				if (video.EndsWith(ShortPath))
				{
					return video;
				}
			}
			return "";
		}

		public static void ShuffleVideos(TVScript Instance)
		{
			m_Videos = GetClearList(VideoManager.Videos);
			TVLoaderExtendedPlugin.Log.LogInfo((object)("[TVScriptExtended] ShuffleVideos " + GetSeed(Instance)));
			Shuffle(m_Videos, GetSeed(Instance));
			for (int i = 0; i < m_Videos.Count; i++)
			{
				TVLoaderExtendedPlugin.Log.LogInfo((object)("[TVScriptExtended] m_Videos[" + i + "] " + m_Videos[i]));
			}
		}

		public static void ClientUpdate(TVScript Instance)
		{
			int num = (int)currentClipProperty.GetValue(Instance);
			if (s_LastSeenIndex != num)
			{
				s_LastSeenIndex = num;
				TVLoaderExtendedPlugin.Log.LogInfo((object)("[ClientUpdate] currentClip " + num + " Instance.tvOn " + Instance.tvOn));
				if (Instance.tvOn)
				{
					PlayVideo(Instance);
				}
			}
		}

		public static bool PlayerIsHost(TVScript __instance)
		{
			if (Object.op_Implicit((Object)(object)__instance))
			{
				return ((NetworkBehaviour)__instance).NetworkManager.IsHost;
			}
			return false;
		}

		[HarmonyPrefix]
		[HarmonyPatch("Update")]
		public static bool Update(TVScript __instance)
		{
			if ((Object)(object)renderTexture == (Object)null)
			{
				renderTexture = ((Component)__instance).GetComponent<VideoPlayer>().targetTexture;
			}
			if (!PlayerIsHost(__instance))
			{
				ClientUpdate(__instance);
			}
			if (s_LastSeed != GetSeed(__instance))
			{
				s_LastSeed = GetSeed(__instance);
				ShuffleVideos(__instance);
				if (PlayerIsHost(__instance))
				{
					currentClipProperty.SetValue(__instance, 0);
				}
				else
				{
					currentClipProperty.SetValue(__instance, -1);
				}
				s_EverWasOn = false;
			}
			return false;
		}

		[HarmonyPrefix]
		[HarmonyPatch("TurnTVOnOff")]
		public static bool TurnTVOnOff(TVScript __instance, bool on)
		{
			TVLoaderExtendedPlugin.Log.LogInfo((object)$"TVOnOff: {on}");
			if (VideoManager.Videos.Count == 0)
			{
				return false;
			}
			int num = (int)currentClipProperty.GetValue(__instance);
			__instance.tvOn = on;
			if (PlayerIsHost(__instance))
			{
				if (on)
				{
					if (!s_EverWasOn)
					{
						s_EverWasOn = true;
					}
					else
					{
						num = (num + 1) % VideoManager.Videos.Count;
						currentClipProperty.SetValue(__instance, num);
					}
					PlayVideo(__instance);
				}
			}
			else if (on)
			{
				currentTimeProperty.SetValue(__instance, 0f);
			}
			if (on)
			{
				__instance.tvSFX.PlayOneShot(__instance.switchTVOn);
				WalkieTalkie.TransmitOneShotAudio(__instance.tvSFX, __instance.switchTVOn, 1f);
			}
			else
			{
				__instance.video.Stop();
				__instance.tvSFX.PlayOneShot(__instance.switchTVOff);
				WalkieTalkie.TransmitOneShotAudio(__instance.tvSFX, __instance.switchTVOff, 1f);
			}
			setMatMethod.Invoke(__instance, new object[1] { on });
			return false;
		}

		[HarmonyPrefix]
		[HarmonyPatch("TVFinishedClip")]
		public static bool TVFinishedClip(TVScript __instance, VideoPlayer source)
		{
			if (__instance.tvOn && PlayerIsHost(__instance))
			{
				TVLoaderExtendedPlugin.Log.LogInfo((object)"TVFinishedClip");
				int num = (int)currentClipProperty.GetValue(__instance);
				if (VideoManager.Videos.Count > 0)
				{
					num = (num + 1) % VideoManager.Videos.Count;
				}
				currentTimeProperty.SetValue(__instance, 0f);
				currentClipProperty.SetValue(__instance, num);
				PlayVideo(__instance);
			}
			return false;
		}

		private static void PrepareVideo(TVScript instance, int index)
		{
			//IL_00b0: Unknown result type (might be due to invalid IL or missing references)
			//IL_00b5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00bb: Expected O, but got Unknown
			if (index < 0)
			{
				return;
			}
			string videoPath = GetVideoPath(index);
			Object.Destroy((Object)(object)instance.video);
			VideoPlayer val = ((Component)instance).gameObject.AddComponent<VideoPlayer>();
			val.playOnAwake = false;
			val.isLooping = false;
			val.source = (VideoSource)1;
			val.controlledAudioTrackCount = 1;
			val.audioOutputMode = (VideoAudioOutputMode)1;
			val.SetTargetAudioSource((ushort)0, instance.tvSFX);
			TVLoaderExtendedPlugin.Log.LogInfo((object)("Going to prepare: " + videoPath));
			val.url = "file://" + videoPath;
			val.skipOnDrop = true;
			val.Prepare();
			object obj = <>c.<>9__22_0;
			if (obj == null)
			{
				EventHandler val2 = delegate
				{
					TVLoaderExtendedPlugin.Log.LogInfo((object)"Prepared video!");
				};
				<>c.<>9__22_0 = val2;
				obj = (object)val2;
			}
			val.prepareCompleted += (EventHandler)obj;
			instance.video = val;
		}

		private static void PlayVideo(TVScript instance)
		{
			if (VideoManager.Videos.Count != 0)
			{
				currentTimeProperty.SetValue(instance, 0f);
				PrepareVideo(instance, (int)currentClipProperty.GetValue(instance));
				onEnableMethod.Invoke(instance, new object[0]);
				TVLoaderExtendedPlugin.Log.LogInfo((object)("TV Current Video Index " + (int)currentClipProperty.GetValue(instance)));
				instance.video.targetTexture = renderTexture;
				instance.video.Play();
				if (PlayerIsHost(instance))
				{
					instance.SyncTVServerRpc();
				}
			}
		}
	}
}