UnityLogSource.cs 2.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. using System;
  2. using System.IO;
  3. using System.Reflection;
  4. using UnityEngine;
  5. namespace BepInEx.Logging
  6. {
  7. /// <summary>
  8. /// Logs entries using Unity specific outputs.
  9. /// </summary>
  10. public class UnityLogSource : ILogSource
  11. {
  12. public string SourceName { get; } = "Unity Log";
  13. public event EventHandler<LogEventArgs> LogEvent;
  14. public UnityLogSource()
  15. {
  16. InternalUnityLogMessage += unityLogMessageHandler;
  17. }
  18. private void unityLogMessageHandler(object sender, LogEventArgs eventArgs)
  19. {
  20. var newEventArgs = new LogEventArgs(eventArgs.Data, eventArgs.Level, this);
  21. LogEvent?.Invoke(this, newEventArgs);
  22. }
  23. private bool disposed = false;
  24. public void Dispose()
  25. {
  26. if (!disposed)
  27. {
  28. InternalUnityLogMessage -= unityLogMessageHandler;
  29. disposed = true;
  30. }
  31. }
  32. #region Static Unity handler
  33. private static event EventHandler<LogEventArgs> InternalUnityLogMessage;
  34. static UnityLogSource()
  35. {
  36. var callback = new Application.LogCallback(OnUnityLogMessageReceived);
  37. EventInfo logEvent = typeof(Application).GetEvent("logMessageReceived", BindingFlags.Public | BindingFlags.Static);
  38. if (logEvent != null)
  39. {
  40. logEvent.AddEventHandler(null, callback);
  41. //UnsubscribeAction = () => logEvent.RemoveEventHandler(null, callback);
  42. }
  43. else
  44. {
  45. MethodInfo registerLogCallback = typeof(Application).GetMethod("RegisterLogCallback", BindingFlags.Public | BindingFlags.Static);
  46. registerLogCallback.Invoke(null, new object[] { callback });
  47. //UnsubscribeAction = () => registerLogCallback.Invoke(null, new object[] { null });
  48. }
  49. }
  50. private static void OnUnityLogMessageReceived(string message, string stackTrace, LogType type)
  51. {
  52. LogLevel logLevel;
  53. switch (type)
  54. {
  55. case LogType.Error:
  56. case LogType.Assert:
  57. case LogType.Exception:
  58. logLevel = LogLevel.Error;
  59. break;
  60. case LogType.Warning:
  61. logLevel = LogLevel.Warning;
  62. break;
  63. case LogType.Log:
  64. default:
  65. logLevel = LogLevel.Info;
  66. break;
  67. }
  68. if (type == LogType.Exception)
  69. message += $"\nStack trace:\n{stackTrace}";
  70. File.WriteAllText("unity.log", $"{message}\n");
  71. InternalUnityLogMessage?.Invoke(null, new LogEventArgs(message, logLevel, null));
  72. }
  73. #endregion
  74. }
  75. }