mirror of
https://gitee.com/jisol/jisol-game/
synced 2025-09-27 02:36:14 +00:00
提交Unity 联机Pro
This commit is contained in:
@@ -0,0 +1,59 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using Internal;
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IBugReportService))]
|
||||
class BugReportApiService : IBugReportService
|
||||
{
|
||||
private IBugReporterHandler _handler = new InternalBugReporterHandler();
|
||||
|
||||
public bool IsUsable
|
||||
{
|
||||
get
|
||||
{
|
||||
return _handler != null && _handler.IsUsable;
|
||||
}
|
||||
}
|
||||
|
||||
public void SetHandler(IBugReporterHandler handler)
|
||||
{
|
||||
Debug.LogFormat("[SRDebugger] Bug Report handler set to {0}", handler);
|
||||
_handler = handler;
|
||||
}
|
||||
|
||||
public void SendBugReport(BugReport report, BugReportCompleteCallback completeHandler,
|
||||
IProgress<float> progress = null)
|
||||
{
|
||||
if (_handler == null)
|
||||
{
|
||||
throw new InvalidOperationException("No bug report handler has been configured.");
|
||||
}
|
||||
|
||||
if (!_handler.IsUsable)
|
||||
{
|
||||
throw new InvalidOperationException("Bug report handler is not usable.");
|
||||
}
|
||||
|
||||
if (report == null)
|
||||
{
|
||||
throw new ArgumentNullException("report");
|
||||
}
|
||||
|
||||
if (completeHandler == null)
|
||||
{
|
||||
throw new ArgumentNullException("completeHandler");
|
||||
}
|
||||
|
||||
if (Application.internetReachability == NetworkReachability.NotReachable)
|
||||
{
|
||||
completeHandler(false, "No Internet Connection");
|
||||
return;
|
||||
}
|
||||
|
||||
_handler.Submit(report, result => completeHandler(result.IsSuccessful, result.ErrorMessage), progress);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 0f0a70f9ea64595459ec202791f9954a
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,167 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using System.Collections;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UI.Other;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (BugReportPopoverService))]
|
||||
public class BugReportPopoverService : SRServiceBase<BugReportPopoverService>
|
||||
{
|
||||
private BugReportCompleteCallback _callback;
|
||||
private bool _isVisible;
|
||||
private BugReportPopoverRoot _popover;
|
||||
private BugReportSheetController _sheet;
|
||||
|
||||
public bool IsShowingPopover
|
||||
{
|
||||
get { return _isVisible; }
|
||||
}
|
||||
|
||||
public void ShowBugReporter(BugReportCompleteCallback callback, bool takeScreenshotFirst = true,
|
||||
string descriptionText = null)
|
||||
{
|
||||
if (_isVisible)
|
||||
{
|
||||
throw new InvalidOperationException("Bug report popover is already visible.");
|
||||
}
|
||||
|
||||
if (_popover == null)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
|
||||
if (_popover == null)
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Bug report popover failed loading, executing callback with fail result");
|
||||
callback(false, "Resource load failed");
|
||||
return;
|
||||
}
|
||||
|
||||
_callback = callback;
|
||||
|
||||
_isVisible = true;
|
||||
SRDebuggerUtil.EnsureEventSystemExists();
|
||||
|
||||
StartCoroutine(OpenCo(takeScreenshotFirst, descriptionText));
|
||||
}
|
||||
|
||||
private IEnumerator OpenCo(bool takeScreenshot, string descriptionText)
|
||||
{
|
||||
if (takeScreenshot)
|
||||
{
|
||||
// Wait for screenshot to be captured
|
||||
yield return StartCoroutine(BugReportScreenshotUtil.ScreenshotCaptureCo());
|
||||
}
|
||||
_popover.CachedGameObject.SetActive(true);
|
||||
|
||||
yield return new WaitForEndOfFrame();
|
||||
|
||||
if (!string.IsNullOrEmpty(descriptionText))
|
||||
{
|
||||
_sheet.DescriptionField.text = descriptionText;
|
||||
}
|
||||
}
|
||||
|
||||
private void SubmitComplete(bool didSucceed, string errorMessage)
|
||||
{
|
||||
OnComplete(didSucceed, errorMessage, false);
|
||||
}
|
||||
|
||||
private void CancelPressed()
|
||||
{
|
||||
OnComplete(false, "User Cancelled", true);
|
||||
}
|
||||
|
||||
private void OnComplete(bool success, string errorMessage, bool close)
|
||||
{
|
||||
if (!_isVisible)
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received callback at unexpected time. ???");
|
||||
return;
|
||||
}
|
||||
|
||||
if (!success && !close)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
_isVisible = false;
|
||||
|
||||
// Destroy it all so it doesn't linger in the scene using memory
|
||||
_popover.gameObject.SetActive(false);
|
||||
Destroy(_popover.gameObject);
|
||||
|
||||
_popover = null;
|
||||
_sheet = null;
|
||||
|
||||
BugReportScreenshotUtil.ScreenshotData = null;
|
||||
|
||||
_callback(success, errorMessage);
|
||||
}
|
||||
|
||||
private void TakingScreenshot()
|
||||
{
|
||||
if (!IsShowingPopover)
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received callback at unexpected time. ???");
|
||||
return;
|
||||
}
|
||||
|
||||
_popover.CanvasGroup.alpha = 0f;
|
||||
}
|
||||
|
||||
private void ScreenshotComplete()
|
||||
{
|
||||
if (!IsShowingPopover)
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received callback at unexpected time. ???");
|
||||
return;
|
||||
}
|
||||
|
||||
_popover.CanvasGroup.alpha = 1f;
|
||||
}
|
||||
|
||||
protected override void Awake()
|
||||
{
|
||||
base.Awake();
|
||||
|
||||
CachedTransform.SetParent(Hierarchy.Get("SRDebugger"));
|
||||
}
|
||||
|
||||
private void Load()
|
||||
{
|
||||
var popoverPrefab = Resources.Load<BugReportPopoverRoot>(SRDebugPaths.BugReportPopoverPath);
|
||||
var sheetPrefab = Resources.Load<BugReportSheetController>(SRDebugPaths.BugReportSheetPath);
|
||||
|
||||
if (popoverPrefab == null)
|
||||
{
|
||||
Debug.LogError("[SRDebugger] Unable to load bug report popover prefab");
|
||||
return;
|
||||
}
|
||||
|
||||
if (sheetPrefab == null)
|
||||
{
|
||||
Debug.LogError("[SRDebugger] Unable to load bug report sheet prefab");
|
||||
return;
|
||||
}
|
||||
|
||||
_popover = SRInstantiate.Instantiate(popoverPrefab);
|
||||
_popover.CachedTransform.SetParent(CachedTransform, false);
|
||||
|
||||
_sheet = SRInstantiate.Instantiate(sheetPrefab);
|
||||
_sheet.CachedTransform.SetParent(_popover.Container, false);
|
||||
|
||||
_sheet.SubmitComplete = SubmitComplete;
|
||||
_sheet.CancelPressed = CancelPressed;
|
||||
|
||||
_sheet.TakingScreenshot = TakingScreenshot;
|
||||
_sheet.ScreenshotComplete = ScreenshotComplete;
|
||||
|
||||
_popover.CachedGameObject.SetActive(false);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 80565ccf143b6fc40aafeb9c7d23aeef
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,57 @@
|
||||
using System;
|
||||
using SRDebugger.Services;
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
|
||||
namespace Assets.StompyRobot.SRDebugger.Scripts.Services.Implementation
|
||||
{
|
||||
[Service(typeof(IConsoleFilterState))]
|
||||
public sealed class ConsoleFilterStateService : IConsoleFilterState
|
||||
{
|
||||
public event ConsoleStateChangedEventHandler FilterStateChange;
|
||||
|
||||
private readonly bool[] _states;
|
||||
|
||||
public ConsoleFilterStateService()
|
||||
{
|
||||
_states = new bool[Enum.GetValues(typeof(LogType)).Length];
|
||||
for (var i = 0; i < _states.Length; i++)
|
||||
{
|
||||
_states[i] = true;
|
||||
}
|
||||
}
|
||||
|
||||
public void SetConsoleFilterState(LogType type, bool newState)
|
||||
{
|
||||
type = GetType(type);
|
||||
if (_states[(int)type] == newState)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
//Debug.Log($"FilterState changed {type} {!newState} -> {newState}");
|
||||
|
||||
_states[(int)type] = newState;
|
||||
FilterStateChange?.Invoke(type, newState);
|
||||
}
|
||||
|
||||
public bool GetConsoleFilterState(LogType type)
|
||||
{
|
||||
type = GetType(type);
|
||||
return _states[(int)type];
|
||||
}
|
||||
|
||||
private static LogType GetType(LogType type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case LogType.Error:
|
||||
case LogType.Assert:
|
||||
case LogType.Exception:
|
||||
return LogType.Error;
|
||||
default:
|
||||
return type;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,11 @@
|
||||
fileFormatVersion: 2
|
||||
guid: d2010dcb3030fd543840eedcac6c1e1b
|
||||
MonoImporter:
|
||||
externalObjects: {}
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
||||
assetBundleName:
|
||||
assetBundleVariant:
|
@@ -0,0 +1,32 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IDebugCameraService))]
|
||||
public class DebugCameraServiceImpl : IDebugCameraService
|
||||
{
|
||||
private Camera _debugCamera;
|
||||
|
||||
public DebugCameraServiceImpl()
|
||||
{
|
||||
if (Settings.Instance.UseDebugCamera)
|
||||
{
|
||||
_debugCamera = new GameObject("SRDebugCamera").AddComponent<Camera>();
|
||||
|
||||
_debugCamera.cullingMask = 1 << Settings.Instance.DebugLayer;
|
||||
_debugCamera.depth = Settings.Instance.DebugCameraDepth;
|
||||
|
||||
_debugCamera.clearFlags = CameraClearFlags.Depth;
|
||||
|
||||
_debugCamera.transform.SetParent(Hierarchy.Get("SRDebugger"));
|
||||
}
|
||||
}
|
||||
|
||||
public Camera Camera
|
||||
{
|
||||
get { return _debugCamera; }
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 07b63666d1ce0074a8e9be3dae9d39a3
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,171 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UI;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IDebugPanelService))]
|
||||
public class DebugPanelServiceImpl : ScriptableObject, IDebugPanelService, IDisposable
|
||||
{
|
||||
private DebugPanelRoot _debugPanelRootObject;
|
||||
public event Action<IDebugPanelService, bool> VisibilityChanged;
|
||||
|
||||
private bool _isVisible;
|
||||
|
||||
private bool? _cursorWasVisible;
|
||||
|
||||
private CursorLockMode? _cursorLockMode;
|
||||
|
||||
|
||||
public DebugPanelRoot RootObject
|
||||
{
|
||||
get { return _debugPanelRootObject; }
|
||||
}
|
||||
|
||||
public bool IsLoaded
|
||||
{
|
||||
get { return _debugPanelRootObject != null; }
|
||||
}
|
||||
|
||||
public bool IsVisible
|
||||
{
|
||||
get { return IsLoaded && _isVisible; }
|
||||
set
|
||||
{
|
||||
if (_isVisible == value)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (value)
|
||||
{
|
||||
if (!IsLoaded)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
|
||||
SRDebuggerUtil.EnsureEventSystemExists();
|
||||
|
||||
_debugPanelRootObject.CanvasGroup.alpha = 1.0f;
|
||||
_debugPanelRootObject.CanvasGroup.interactable = true;
|
||||
_debugPanelRootObject.CanvasGroup.blocksRaycasts = true;
|
||||
_cursorWasVisible = Cursor.visible;
|
||||
_cursorLockMode = Cursor.lockState;
|
||||
|
||||
foreach (var c in _debugPanelRootObject.GetComponentsInChildren<Canvas>())
|
||||
{
|
||||
c.enabled = true;
|
||||
}
|
||||
|
||||
if (Settings.Instance.AutomaticallyShowCursor)
|
||||
{
|
||||
Cursor.visible = true;
|
||||
Cursor.lockState = CursorLockMode.None;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (IsLoaded)
|
||||
{
|
||||
_debugPanelRootObject.CanvasGroup.alpha = 0.0f;
|
||||
_debugPanelRootObject.CanvasGroup.interactable = false;
|
||||
_debugPanelRootObject.CanvasGroup.blocksRaycasts = false;
|
||||
|
||||
foreach (var c in _debugPanelRootObject.GetComponentsInChildren<Canvas>())
|
||||
{
|
||||
c.enabled = false;
|
||||
}
|
||||
}
|
||||
|
||||
if (_cursorWasVisible.HasValue)
|
||||
{
|
||||
Cursor.visible = _cursorWasVisible.Value;
|
||||
_cursorWasVisible = null;
|
||||
}
|
||||
|
||||
if (_cursorLockMode.HasValue)
|
||||
{
|
||||
Cursor.lockState = _cursorLockMode.Value;
|
||||
_cursorLockMode = null;
|
||||
}
|
||||
}
|
||||
|
||||
_isVisible = value;
|
||||
|
||||
if (VisibilityChanged != null)
|
||||
{
|
||||
VisibilityChanged(this, _isVisible);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public DefaultTabs? ActiveTab
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_debugPanelRootObject == null)
|
||||
{
|
||||
return null;
|
||||
}
|
||||
|
||||
return _debugPanelRootObject.TabController.ActiveTab;
|
||||
}
|
||||
}
|
||||
|
||||
public void OpenTab(DefaultTabs tab)
|
||||
{
|
||||
if (!IsVisible)
|
||||
{
|
||||
IsVisible = true;
|
||||
}
|
||||
|
||||
_debugPanelRootObject.TabController.OpenTab(tab);
|
||||
}
|
||||
|
||||
public void Unload()
|
||||
{
|
||||
if (_debugPanelRootObject == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
IsVisible = false;
|
||||
|
||||
_debugPanelRootObject.CachedGameObject.SetActive(false);
|
||||
Destroy(_debugPanelRootObject.CachedGameObject);
|
||||
|
||||
_debugPanelRootObject = null;
|
||||
}
|
||||
|
||||
private void Load()
|
||||
{
|
||||
var prefab = Resources.Load<DebugPanelRoot>(SRDebugPaths.DebugPanelPrefabPath);
|
||||
|
||||
if (prefab == null)
|
||||
{
|
||||
Debug.LogError("[SRDebugger] Error loading debug panel prefab");
|
||||
return;
|
||||
}
|
||||
|
||||
_debugPanelRootObject = SRInstantiate.Instantiate(prefab);
|
||||
_debugPanelRootObject.name = "Panel";
|
||||
|
||||
DontDestroyOnLoad(_debugPanelRootObject);
|
||||
|
||||
_debugPanelRootObject.CachedTransform.SetParent(Hierarchy.Get("SRDebugger"), true);
|
||||
|
||||
SRDebuggerUtil.EnsureEventSystemExists();
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
if (_debugPanelRootObject != null)
|
||||
{
|
||||
DestroyImmediate(_debugPanelRootObject.gameObject);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 3395027a4a5c704439ebf91760920165
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,225 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UI.Other;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IDebugTriggerService))]
|
||||
public class DebugTriggerImpl : SRServiceBase<IDebugTriggerService>, IDebugTriggerService
|
||||
{
|
||||
private PinAlignment _position;
|
||||
private TriggerRoot _trigger;
|
||||
private IConsoleService _consoleService;
|
||||
private bool _showErrorNotification;
|
||||
|
||||
public bool IsEnabled
|
||||
{
|
||||
get { return _trigger != null && _trigger.CachedGameObject.activeSelf; }
|
||||
set
|
||||
{
|
||||
// Create trigger if it does not yet exist
|
||||
if (value && _trigger == null)
|
||||
{
|
||||
CreateTrigger();
|
||||
}
|
||||
|
||||
if (_trigger != null)
|
||||
{
|
||||
_trigger.CachedGameObject.SetActive(value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public bool ShowErrorNotification
|
||||
{
|
||||
get
|
||||
{
|
||||
return _showErrorNotification;
|
||||
}
|
||||
set
|
||||
{
|
||||
if (_showErrorNotification == value) return;
|
||||
|
||||
_showErrorNotification = value;
|
||||
|
||||
if (_trigger == null) return;
|
||||
|
||||
if(_showErrorNotification)
|
||||
{
|
||||
_consoleService = SRServiceManager.GetService<IConsoleService>();
|
||||
_consoleService.Error += OnError;
|
||||
}
|
||||
else
|
||||
{
|
||||
_consoleService.Error -= OnError;
|
||||
_consoleService = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public PinAlignment Position
|
||||
{
|
||||
get { return _position; }
|
||||
set
|
||||
{
|
||||
if (_trigger != null)
|
||||
{
|
||||
SetTriggerPosition(_trigger.TriggerTransform, value);
|
||||
}
|
||||
|
||||
_position = value;
|
||||
}
|
||||
}
|
||||
|
||||
protected override void Awake()
|
||||
{
|
||||
base.Awake();
|
||||
DontDestroyOnLoad(CachedGameObject);
|
||||
|
||||
CachedTransform.SetParent(Hierarchy.Get("SRDebugger"), true);
|
||||
ShowErrorNotification = Settings.Instance.ErrorNotification;
|
||||
|
||||
name = "Trigger";
|
||||
}
|
||||
|
||||
private void OnError(IConsoleService console)
|
||||
{
|
||||
if (_trigger != null)
|
||||
{
|
||||
_trigger.ErrorNotifier.ShowErrorWarning();
|
||||
}
|
||||
}
|
||||
|
||||
private void CreateTrigger()
|
||||
{
|
||||
var prefab = Resources.Load<TriggerRoot>(SRDebugPaths.TriggerPrefabPath);
|
||||
|
||||
if (prefab == null)
|
||||
{
|
||||
Debug.LogError("[SRDebugger] Error loading trigger prefab");
|
||||
return;
|
||||
}
|
||||
|
||||
_trigger = SRInstantiate.Instantiate(prefab);
|
||||
_trigger.CachedTransform.SetParent(CachedTransform, true);
|
||||
|
||||
SetTriggerPosition(_trigger.TriggerTransform, _position);
|
||||
|
||||
switch (Settings.Instance.TriggerBehaviour)
|
||||
{
|
||||
case Settings.TriggerBehaviours.TripleTap:
|
||||
{
|
||||
_trigger.TripleTapButton.onClick.AddListener(OnTriggerButtonClick);
|
||||
_trigger.TapHoldButton.gameObject.SetActive(false);
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case Settings.TriggerBehaviours.TapAndHold:
|
||||
{
|
||||
_trigger.TapHoldButton.onLongPress.AddListener(OnTriggerButtonClick);
|
||||
_trigger.TripleTapButton.gameObject.SetActive(false);
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case Settings.TriggerBehaviours.DoubleTap:
|
||||
{
|
||||
_trigger.TripleTapButton.RequiredTapCount = 2;
|
||||
_trigger.TripleTapButton.onClick.AddListener(OnTriggerButtonClick);
|
||||
_trigger.TapHoldButton.gameObject.SetActive(false);
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
throw new Exception("Unhandled TriggerBehaviour");
|
||||
}
|
||||
|
||||
SRDebuggerUtil.EnsureEventSystemExists();
|
||||
|
||||
UnityEngine.SceneManagement.SceneManager.activeSceneChanged += OnActiveSceneChanged;
|
||||
|
||||
if (_showErrorNotification)
|
||||
{
|
||||
_consoleService = SRServiceManager.GetService<IConsoleService>();
|
||||
_consoleService.Error += OnError;
|
||||
}
|
||||
}
|
||||
|
||||
protected override void OnDestroy()
|
||||
{
|
||||
UnityEngine.SceneManagement.SceneManager.activeSceneChanged -= OnActiveSceneChanged;
|
||||
|
||||
if (_consoleService != null)
|
||||
{
|
||||
_consoleService.Error -= OnError;
|
||||
}
|
||||
|
||||
base.OnDestroy();
|
||||
}
|
||||
|
||||
private static void OnActiveSceneChanged(UnityEngine.SceneManagement.Scene s1, UnityEngine.SceneManagement.Scene s2)
|
||||
{
|
||||
SRDebuggerUtil.EnsureEventSystemExists();
|
||||
}
|
||||
|
||||
private void OnTriggerButtonClick()
|
||||
{
|
||||
if (_trigger.ErrorNotifier.IsVisible)
|
||||
{
|
||||
// Open into console if there is an error.
|
||||
SRDebug.Instance.ShowDebugPanel(DefaultTabs.Console);
|
||||
}
|
||||
else
|
||||
{
|
||||
SRDebug.Instance.ShowDebugPanel();
|
||||
}
|
||||
}
|
||||
|
||||
private static void SetTriggerPosition(RectTransform t, PinAlignment position)
|
||||
{
|
||||
var pivotX = 0f;
|
||||
var pivotY = 0f;
|
||||
|
||||
var posX = 0f;
|
||||
var posY = 0f;
|
||||
|
||||
if (position == PinAlignment.TopLeft || position == PinAlignment.TopRight || position == PinAlignment.TopCenter)
|
||||
{
|
||||
pivotY = 1f;
|
||||
posY = 1f;
|
||||
}
|
||||
else if (position == PinAlignment.BottomLeft || position == PinAlignment.BottomRight || position == PinAlignment.BottomCenter)
|
||||
{
|
||||
pivotY = 0f;
|
||||
posY = 0f;
|
||||
} else if (position == PinAlignment.CenterLeft || position == PinAlignment.CenterRight)
|
||||
{
|
||||
pivotY = 0.5f;
|
||||
posY = 0.5f;
|
||||
}
|
||||
|
||||
if (position == PinAlignment.TopLeft || position == PinAlignment.BottomLeft || position == PinAlignment.CenterLeft)
|
||||
{
|
||||
pivotX = 0f;
|
||||
posX = 0f;
|
||||
}
|
||||
else if (position == PinAlignment.TopRight || position == PinAlignment.BottomRight || position == PinAlignment.CenterRight)
|
||||
{
|
||||
pivotX = 1f;
|
||||
posX = 1f;
|
||||
} else if (position == PinAlignment.TopCenter || position == PinAlignment.BottomCenter)
|
||||
{
|
||||
pivotX = 0.5f;
|
||||
posX = 0.5f;
|
||||
}
|
||||
|
||||
t.pivot = new Vector2(pivotX, pivotY);
|
||||
t.anchorMax = t.anchorMin = new Vector2(posX, posY);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 5cbf8bc5e9eb92448bc12690ebd84a02
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,148 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using Internal;
|
||||
using SRF.Service;
|
||||
using UI.Other;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IDockConsoleService))]
|
||||
public class DockConsoleServiceImpl : IDockConsoleService
|
||||
{
|
||||
private ConsoleAlignment _alignment;
|
||||
private DockConsoleController _consoleRoot;
|
||||
private bool _didSuspendTrigger;
|
||||
private bool _isExpanded = true;
|
||||
private bool _isVisible;
|
||||
|
||||
public DockConsoleServiceImpl()
|
||||
{
|
||||
_alignment = Settings.Instance.ConsoleAlignment;
|
||||
}
|
||||
|
||||
public bool IsVisible
|
||||
{
|
||||
get { return _isVisible; }
|
||||
|
||||
set
|
||||
{
|
||||
if (value == _isVisible)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
_isVisible = value;
|
||||
|
||||
if (_consoleRoot == null && value)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
else
|
||||
{
|
||||
_consoleRoot.CachedGameObject.SetActive(value);
|
||||
}
|
||||
|
||||
CheckTrigger();
|
||||
}
|
||||
}
|
||||
|
||||
public bool IsExpanded
|
||||
{
|
||||
get { return _isExpanded; }
|
||||
|
||||
set
|
||||
{
|
||||
if (value == _isExpanded)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
_isExpanded = value;
|
||||
|
||||
if (_consoleRoot == null && value)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
else
|
||||
{
|
||||
_consoleRoot.SetDropdownVisibility(value);
|
||||
}
|
||||
|
||||
CheckTrigger();
|
||||
}
|
||||
}
|
||||
|
||||
public ConsoleAlignment Alignment
|
||||
{
|
||||
get { return _alignment; }
|
||||
set
|
||||
{
|
||||
_alignment = value;
|
||||
|
||||
if (_consoleRoot != null)
|
||||
{
|
||||
_consoleRoot.SetAlignmentMode(value);
|
||||
}
|
||||
|
||||
CheckTrigger();
|
||||
}
|
||||
}
|
||||
|
||||
private void Load()
|
||||
{
|
||||
var dockService = SRServiceManager.GetService<IPinnedUIService>();
|
||||
|
||||
if (dockService == null)
|
||||
{
|
||||
Debug.LogError("[DockConsoleService] PinnedUIService not found");
|
||||
return;
|
||||
}
|
||||
|
||||
var pinService = dockService as PinnedUIServiceImpl;
|
||||
|
||||
if (pinService == null)
|
||||
{
|
||||
Debug.LogError("[DockConsoleService] Expected IPinnedUIService to be PinnedUIServiceImpl");
|
||||
return;
|
||||
}
|
||||
|
||||
_consoleRoot = pinService.DockConsoleController;
|
||||
|
||||
_consoleRoot.SetDropdownVisibility(_isExpanded);
|
||||
_consoleRoot.IsVisible = _isVisible;
|
||||
_consoleRoot.SetAlignmentMode(_alignment);
|
||||
|
||||
CheckTrigger();
|
||||
}
|
||||
|
||||
private void CheckTrigger()
|
||||
{
|
||||
ConsoleAlignment? triggerAlignment = null;
|
||||
var pinAlignment = Service.Trigger.Position;
|
||||
|
||||
if (pinAlignment == PinAlignment.TopLeft ||
|
||||
pinAlignment == PinAlignment.TopRight || pinAlignment == PinAlignment.TopCenter)
|
||||
{
|
||||
triggerAlignment = ConsoleAlignment.Top;
|
||||
} else if (pinAlignment == PinAlignment.BottomLeft ||
|
||||
pinAlignment == PinAlignment.BottomRight ||
|
||||
pinAlignment == PinAlignment.BottomCenter)
|
||||
{
|
||||
triggerAlignment = ConsoleAlignment.Bottom;
|
||||
}
|
||||
|
||||
var shouldHide = triggerAlignment.HasValue && IsVisible && Alignment == triggerAlignment.Value;
|
||||
|
||||
// Show trigger if we have hidden it, and we no longer need to hide it.
|
||||
if (_didSuspendTrigger && !shouldHide)
|
||||
{
|
||||
Service.Trigger.IsEnabled = true;
|
||||
_didSuspendTrigger = false;
|
||||
}
|
||||
else if (Service.Trigger.IsEnabled && shouldHide)
|
||||
{
|
||||
Service.Trigger.IsEnabled = false;
|
||||
_didSuspendTrigger = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 456e72e9efa4586489f625dc79f1c54d
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,265 @@
|
||||
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System.Collections.Generic;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
#if ENABLE_INPUT_SYSTEM
|
||||
using UnityEngine.InputSystem;
|
||||
using UnityEngine.InputSystem.Controls;
|
||||
#endif
|
||||
|
||||
|
||||
[Service(typeof (KeyboardShortcutListenerService))]
|
||||
public class KeyboardShortcutListenerService : SRServiceBase<KeyboardShortcutListenerService>
|
||||
{
|
||||
private List<Settings.KeyboardShortcut> _shortcuts;
|
||||
|
||||
protected override void Awake()
|
||||
{
|
||||
base.Awake();
|
||||
|
||||
CachedTransform.SetParent(Hierarchy.Get("SRDebugger"));
|
||||
|
||||
_shortcuts = new List<Settings.KeyboardShortcut>(Settings.Instance.KeyboardShortcuts);
|
||||
|
||||
#if ENABLE_INPUT_SYSTEM
|
||||
|
||||
foreach (var s in _shortcuts)
|
||||
{
|
||||
// Cache the actual keycode so we don't have to use strings each time we want to use it.
|
||||
string keyName = s.Key.ToString();
|
||||
KeyControl keyControl = Keyboard.current[keyName] as KeyControl;
|
||||
|
||||
if (keyControl == null)
|
||||
{
|
||||
Debug.LogErrorFormat(
|
||||
"[SRDebugger] Input System: Unable to find shortcut key: {0}. Shortcut ({1}) will not be functional.",
|
||||
keyName, s.Action);
|
||||
s.Cached_KeyCode = Key.None;
|
||||
}
|
||||
|
||||
// Find the index for this key control
|
||||
for (var index = 0; index < Keyboard.current.allKeys.Count; index++)
|
||||
{
|
||||
if (Keyboard.current.allKeys[index] == keyControl)
|
||||
{
|
||||
s.Cached_KeyCode = (Key) (index + 1);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
private void ToggleTab(DefaultTabs t)
|
||||
{
|
||||
var activeTab = Service.Panel.ActiveTab;
|
||||
|
||||
if (Service.Panel.IsVisible && activeTab.HasValue && activeTab.Value == t)
|
||||
{
|
||||
SRDebug.Instance.HideDebugPanel();
|
||||
}
|
||||
else
|
||||
{
|
||||
SRDebug.Instance.ShowDebugPanel(t);
|
||||
}
|
||||
}
|
||||
|
||||
private void ExecuteShortcut(Settings.KeyboardShortcut shortcut)
|
||||
{
|
||||
switch (shortcut.Action)
|
||||
{
|
||||
case Settings.ShortcutActions.OpenSystemInfoTab:
|
||||
|
||||
ToggleTab(DefaultTabs.SystemInformation);
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.OpenConsoleTab:
|
||||
|
||||
ToggleTab(DefaultTabs.Console);
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.OpenOptionsTab:
|
||||
|
||||
ToggleTab(DefaultTabs.Options);
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.OpenProfilerTab:
|
||||
|
||||
ToggleTab(DefaultTabs.Profiler);
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.OpenBugReporterTab:
|
||||
|
||||
ToggleTab(DefaultTabs.BugReporter);
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.ClosePanel:
|
||||
|
||||
SRDebug.Instance.HideDebugPanel();
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.OpenPanel:
|
||||
|
||||
SRDebug.Instance.ShowDebugPanel();
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.TogglePanel:
|
||||
|
||||
if (SRDebug.Instance.IsDebugPanelVisible)
|
||||
{
|
||||
SRDebug.Instance.HideDebugPanel();
|
||||
}
|
||||
else
|
||||
{
|
||||
SRDebug.Instance.ShowDebugPanel();
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.ShowBugReportPopover:
|
||||
|
||||
SRDebug.Instance.ShowBugReportSheet();
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.ToggleDockedConsole:
|
||||
|
||||
SRDebug.Instance.DockConsole.IsVisible = !SRDebug.Instance.DockConsole.IsVisible;
|
||||
|
||||
break;
|
||||
|
||||
case Settings.ShortcutActions.ToggleDockedProfiler:
|
||||
|
||||
SRDebug.Instance.IsProfilerDocked = !SRDebug.Instance.IsProfilerDocked;
|
||||
|
||||
break;
|
||||
|
||||
default:
|
||||
|
||||
Debug.LogWarning("[SRDebugger] Unhandled keyboard shortcut: " + shortcut.Action);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
protected override void Update()
|
||||
{
|
||||
base.Update();
|
||||
|
||||
#if ENABLE_INPUT_SYSTEM && ENABLE_LEGACY_INPUT_MANAGER
|
||||
switch (Settings.Instance.UIInputMode)
|
||||
{
|
||||
case Settings.UIModes.NewInputSystem:
|
||||
UpdateInputSystem();
|
||||
break;
|
||||
case Settings.UIModes.LegacyInputSystem:
|
||||
UpdateLegacyInputSystem();
|
||||
break;
|
||||
}
|
||||
#elif ENABLE_INPUT_SYSTEM
|
||||
UpdateInputSystem();
|
||||
#elif ENABLE_LEGACY_INPUT_MANAGER || (!ENABLE_INPUT_SYSTEM && !UNITY_2019_3_OR_NEWER)
|
||||
UpdateLegacyInputSystem();
|
||||
#endif
|
||||
}
|
||||
|
||||
#if ENABLE_INPUT_SYSTEM
|
||||
private void UpdateInputSystem()
|
||||
{
|
||||
var keyboard = Keyboard.current;
|
||||
|
||||
if (Settings.Instance.KeyboardEscapeClose && keyboard.escapeKey.isPressed && Service.Panel.IsVisible)
|
||||
{
|
||||
SRDebug.Instance.HideDebugPanel();
|
||||
}
|
||||
|
||||
var ctrl = keyboard.leftCtrlKey.isPressed || keyboard.rightCtrlKey.isPressed;
|
||||
var alt = keyboard.leftAltKey.isPressed || keyboard.rightAltKey.isPressed;
|
||||
var shift = keyboard.leftShiftKey.isPressed || keyboard.rightShiftKey.isPressed;
|
||||
|
||||
for (var i = 0; i < _shortcuts.Count; i++)
|
||||
{
|
||||
var s = _shortcuts[i];
|
||||
|
||||
if (s.Control && !ctrl)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (s.Shift && !shift)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (s.Alt && !alt)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!s.Cached_KeyCode.HasValue)
|
||||
{
|
||||
continue; // We can't use this shortcut since we didn't find the keycode.
|
||||
}
|
||||
|
||||
if (keyboard[s.Cached_KeyCode.Value].wasPressedThisFrame)
|
||||
{
|
||||
ExecuteShortcut(s);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#if ENABLE_LEGACY_INPUT_MANAGER || (!ENABLE_INPUT_SYSTEM && !UNITY_2019_3_OR_NEWER)
|
||||
private void UpdateLegacyInputSystem()
|
||||
{
|
||||
if (Settings.Instance.KeyboardEscapeClose && Input.GetKeyDown(KeyCode.Escape) && Service.Panel.IsVisible)
|
||||
{
|
||||
SRDebug.Instance.HideDebugPanel();
|
||||
}
|
||||
|
||||
var ctrl = Input.GetKey(KeyCode.LeftControl) || Input.GetKey(KeyCode.RightControl);
|
||||
var alt = Input.GetKey(KeyCode.LeftAlt) || Input.GetKey(KeyCode.RightAlt);
|
||||
var shift = Input.GetKey(KeyCode.LeftShift) || Input.GetKey(KeyCode.RightShift);
|
||||
|
||||
for (var i = 0; i < _shortcuts.Count; i++)
|
||||
{
|
||||
var s = _shortcuts[i];
|
||||
|
||||
if (s.Control && !ctrl)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (s.Shift && !shift)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (s.Alt && !alt)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (Input.GetKeyDown(s.Key))
|
||||
{
|
||||
ExecuteShortcut(s);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: cad04a63089e6e844969aa944ba22fdd
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,75 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using SRDebugger.Internal;
|
||||
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
public sealed partial class OptionsServiceImpl
|
||||
{
|
||||
/// <summary>
|
||||
/// Options container that is implemented via reflection.
|
||||
/// This is the normal behaviour used when options container is added as an `object`.
|
||||
/// </summary>
|
||||
private class ReflectionOptionContainer : IOptionContainer
|
||||
{
|
||||
// Options don't change, so just leave stubs that do nothing.
|
||||
public event Action<OptionDefinition> OptionAdded
|
||||
{
|
||||
add { }
|
||||
remove { }
|
||||
}
|
||||
|
||||
public event Action<OptionDefinition> OptionRemoved
|
||||
{
|
||||
add { }
|
||||
remove { }
|
||||
}
|
||||
|
||||
public bool IsDynamic
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
private List<OptionDefinition> Options
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_options == null) _options = SRDebuggerUtil.ScanForOptions(_target);
|
||||
return _options;
|
||||
}
|
||||
}
|
||||
|
||||
private List<OptionDefinition> _options;
|
||||
|
||||
public IEnumerable<OptionDefinition> GetOptions()
|
||||
{
|
||||
return Options;
|
||||
}
|
||||
|
||||
private readonly object _target;
|
||||
|
||||
public ReflectionOptionContainer(object target)
|
||||
{
|
||||
_target = target;
|
||||
}
|
||||
|
||||
protected bool Equals(ReflectionOptionContainer other)
|
||||
{
|
||||
return Equals(other._target, this._target);
|
||||
}
|
||||
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
if (ReferenceEquals(null, obj)) return false;
|
||||
if (ReferenceEquals(this, obj)) return true;
|
||||
if (obj.GetType() != this.GetType()) return false;
|
||||
return Equals((ReflectionOptionContainer) obj);
|
||||
}
|
||||
|
||||
public override int GetHashCode()
|
||||
{
|
||||
return _target.GetHashCode();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,3 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 3343cb41b53a47568cb627f032f95dd7
|
||||
timeCreated: 1609341203
|
@@ -0,0 +1,185 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Collections.ObjectModel;
|
||||
using Internal;
|
||||
using SRF.Service;
|
||||
using SRF.Helpers;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IOptionsService))]
|
||||
public partial class OptionsServiceImpl : IOptionsService
|
||||
{
|
||||
public event EventHandler OptionsUpdated;
|
||||
|
||||
public ICollection<OptionDefinition> Options
|
||||
{
|
||||
get { return _optionsReadonly; }
|
||||
}
|
||||
|
||||
private void OptionsContainerOnOptionAdded(IOptionContainer container, OptionDefinition optionDefinition)
|
||||
{
|
||||
List<OptionDefinition> options;
|
||||
if(!_optionContainerLookup.TryGetValue(container, out options))
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received event from unknown option container.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (options.Contains(optionDefinition))
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received option added event from option container, but option has already been added.");
|
||||
return;
|
||||
}
|
||||
|
||||
options.Add(optionDefinition);
|
||||
_options.Add(optionDefinition);
|
||||
OnOptionsUpdated();
|
||||
}
|
||||
|
||||
private void OptionsContainerOnOptionRemoved(IOptionContainer container, OptionDefinition optionDefinition)
|
||||
{
|
||||
List<OptionDefinition> options;
|
||||
if (!_optionContainerLookup.TryGetValue(container, out options))
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received event from unknown option container.");
|
||||
return;
|
||||
}
|
||||
|
||||
if (options.Remove(optionDefinition))
|
||||
{
|
||||
_options.Remove(optionDefinition);
|
||||
OnOptionsUpdated();
|
||||
}
|
||||
else
|
||||
{
|
||||
Debug.LogWarning("[SRDebugger] Received option removed event from option container, but option does not exist.");
|
||||
}
|
||||
}
|
||||
|
||||
private readonly Dictionary<IOptionContainer, List<OptionDefinition>> _optionContainerLookup = new Dictionary<IOptionContainer, List<OptionDefinition>>();
|
||||
|
||||
private readonly Dictionary<IOptionContainer, OptionContainerEventHandler> _optionContainerEventHandlerLookup = new Dictionary<IOptionContainer, OptionContainerEventHandler>();
|
||||
|
||||
private readonly List<OptionDefinition> _options = new List<OptionDefinition>();
|
||||
|
||||
private readonly IList<OptionDefinition> _optionsReadonly;
|
||||
|
||||
public OptionsServiceImpl()
|
||||
{
|
||||
_optionsReadonly = new ReadOnlyCollection<OptionDefinition>(_options);
|
||||
}
|
||||
|
||||
public void Scan(object obj)
|
||||
{
|
||||
AddContainer(obj);
|
||||
}
|
||||
|
||||
public void AddContainer(object obj)
|
||||
{
|
||||
var container = obj as IOptionContainer ?? new ReflectionOptionContainer(obj);
|
||||
AddContainer(container);
|
||||
}
|
||||
|
||||
public void AddContainer(IOptionContainer optionContainer)
|
||||
{
|
||||
if (_optionContainerLookup.ContainsKey(optionContainer))
|
||||
{
|
||||
throw new Exception("An options container should only be added once.");
|
||||
}
|
||||
|
||||
List<OptionDefinition> options = new List<OptionDefinition>();
|
||||
options.AddRange(optionContainer.GetOptions());
|
||||
|
||||
_optionContainerLookup.Add(optionContainer, options);
|
||||
|
||||
if (optionContainer.IsDynamic)
|
||||
{
|
||||
var handler = new OptionContainerEventHandler(this, optionContainer);
|
||||
_optionContainerEventHandlerLookup.Add(optionContainer, handler);
|
||||
}
|
||||
|
||||
if (options.Count > 0)
|
||||
{
|
||||
_options.AddRange(options);
|
||||
OnOptionsUpdated();
|
||||
}
|
||||
}
|
||||
|
||||
public void RemoveContainer(object obj)
|
||||
{
|
||||
var container = obj as IOptionContainer ?? new ReflectionOptionContainer(obj);
|
||||
RemoveContainer(container);
|
||||
}
|
||||
|
||||
public void RemoveContainer(IOptionContainer optionContainer)
|
||||
{
|
||||
if (!_optionContainerLookup.ContainsKey(optionContainer))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
bool isDirty = false;
|
||||
var list = _optionContainerLookup[optionContainer];
|
||||
_optionContainerLookup.Remove(optionContainer);
|
||||
foreach (var op in list)
|
||||
{
|
||||
_options.Remove(op);
|
||||
isDirty = true;
|
||||
}
|
||||
|
||||
OptionContainerEventHandler handler;
|
||||
if (_optionContainerEventHandlerLookup.TryGetValue(optionContainer,
|
||||
out handler))
|
||||
{
|
||||
handler.Dispose();
|
||||
_optionContainerEventHandlerLookup.Remove(optionContainer);
|
||||
}
|
||||
|
||||
if (isDirty)
|
||||
{
|
||||
OnOptionsUpdated();
|
||||
}
|
||||
}
|
||||
|
||||
private void OnOptionsUpdated()
|
||||
{
|
||||
if (OptionsUpdated != null)
|
||||
{
|
||||
OptionsUpdated(this, EventArgs.Empty);
|
||||
}
|
||||
}
|
||||
|
||||
class OptionContainerEventHandler : IDisposable
|
||||
{
|
||||
private readonly OptionsServiceImpl _service;
|
||||
private readonly IOptionContainer _container;
|
||||
|
||||
public OptionContainerEventHandler(OptionsServiceImpl service, IOptionContainer container)
|
||||
{
|
||||
_container = container;
|
||||
_service = service;
|
||||
|
||||
container.OptionAdded += ContainerOnOptionAdded;
|
||||
container.OptionRemoved += ContainerOnOptionRemoved;
|
||||
}
|
||||
|
||||
private void ContainerOnOptionAdded(OptionDefinition obj)
|
||||
{
|
||||
_service.OptionsContainerOnOptionAdded(_container, obj);
|
||||
}
|
||||
|
||||
private void ContainerOnOptionRemoved(OptionDefinition obj)
|
||||
{
|
||||
_service.OptionsContainerOnOptionRemoved(_container, obj);
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
_container.OptionAdded -= ContainerOnOptionAdded;
|
||||
_container.OptionRemoved -= ContainerOnOptionRemoved;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: d1614fef8faa5954d8bda6699bed3fdb
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,129 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UI.Controls;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IPinEntryService))]
|
||||
public class PinEntryServiceImpl : SRServiceBase<IPinEntryService>, IPinEntryService
|
||||
{
|
||||
private PinEntryCompleteCallback _callback;
|
||||
private bool _isVisible;
|
||||
private PinEntryControl _pinControl;
|
||||
private readonly List<int> _requiredPin = new List<int>(4);
|
||||
|
||||
public bool IsShowingKeypad
|
||||
{
|
||||
get { return _isVisible; }
|
||||
}
|
||||
|
||||
public void ShowPinEntry(IReadOnlyList<int> requiredPin, string message, PinEntryCompleteCallback callback,
|
||||
bool allowCancel = true)
|
||||
{
|
||||
if (_isVisible)
|
||||
{
|
||||
throw new InvalidOperationException("Pin entry is already in progress");
|
||||
}
|
||||
|
||||
VerifyPin(requiredPin);
|
||||
|
||||
if (_pinControl == null)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
|
||||
if (_pinControl == null)
|
||||
{
|
||||
Debug.LogWarning("[PinEntry] Pin entry failed loading, executing callback with fail result");
|
||||
callback(false);
|
||||
return;
|
||||
}
|
||||
|
||||
_pinControl.Clear();
|
||||
_pinControl.PromptText.text = message;
|
||||
|
||||
_pinControl.CanCancel = allowCancel;
|
||||
|
||||
_callback = callback;
|
||||
|
||||
_requiredPin.Clear();
|
||||
_requiredPin.AddRange(requiredPin);
|
||||
|
||||
_pinControl.Show();
|
||||
|
||||
_isVisible = true;
|
||||
|
||||
SRDebuggerUtil.EnsureEventSystemExists();
|
||||
}
|
||||
|
||||
protected override void Awake()
|
||||
{
|
||||
base.Awake();
|
||||
|
||||
CachedTransform.SetParent(Hierarchy.Get("SRDebugger"));
|
||||
}
|
||||
|
||||
private void Load()
|
||||
{
|
||||
var prefab = Resources.Load<PinEntryControl>(SRDebugPaths.PinEntryPrefabPath);
|
||||
|
||||
if (prefab == null)
|
||||
{
|
||||
Debug.LogError("[PinEntry] Unable to load pin entry prefab");
|
||||
return;
|
||||
}
|
||||
|
||||
_pinControl = SRInstantiate.Instantiate(prefab);
|
||||
_pinControl.CachedTransform.SetParent(CachedTransform, false);
|
||||
|
||||
_pinControl.Hide();
|
||||
|
||||
_pinControl.Complete += PinControlOnComplete;
|
||||
}
|
||||
|
||||
private void PinControlOnComplete(IList<int> result, bool didCancel)
|
||||
{
|
||||
var isValid = _requiredPin.SequenceEqual(result);
|
||||
|
||||
if (!didCancel && !isValid)
|
||||
{
|
||||
_pinControl.Clear();
|
||||
_pinControl.PlayInvalidCodeAnimation();
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
_isVisible = false;
|
||||
_pinControl.Hide();
|
||||
|
||||
if (didCancel)
|
||||
{
|
||||
_callback(false);
|
||||
return;
|
||||
}
|
||||
|
||||
_callback(isValid);
|
||||
}
|
||||
|
||||
private void VerifyPin(IReadOnlyList<int> pin)
|
||||
{
|
||||
if (pin.Count != 4)
|
||||
{
|
||||
throw new ArgumentException("Pin list must have 4 elements");
|
||||
}
|
||||
|
||||
for (var i = 0; i < pin.Count; i++)
|
||||
{
|
||||
if (pin[i] < 0 || pin[i] > 9)
|
||||
{
|
||||
throw new ArgumentException("Pin numbers must be >= 0 && <= 9");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 43bd0242747ae6042a436f1ff85403d4
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,271 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
using System.Linq;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UI.Controls;
|
||||
using UI.Other;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IPinnedUIService))]
|
||||
public class PinnedUIServiceImpl : SRServiceBase<IPinnedUIService>, IPinnedUIService
|
||||
{
|
||||
private readonly List<OptionsControlBase> _controlList = new List<OptionsControlBase>();
|
||||
|
||||
private readonly Dictionary<OptionDefinition, OptionsControlBase> _pinnedObjects =
|
||||
new Dictionary<OptionDefinition, OptionsControlBase>();
|
||||
|
||||
private bool _queueRefresh;
|
||||
private PinnedUIRoot _uiRoot;
|
||||
|
||||
public DockConsoleController DockConsoleController
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_uiRoot == null)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
return _uiRoot.DockConsoleController;
|
||||
}
|
||||
}
|
||||
|
||||
public event Action<OptionDefinition, bool> OptionPinStateChanged;
|
||||
public event Action<RectTransform> OptionsCanvasCreated;
|
||||
|
||||
public bool IsProfilerPinned
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_uiRoot == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
return _uiRoot.Profiler.activeSelf;
|
||||
}
|
||||
set
|
||||
{
|
||||
if (_uiRoot == null)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
_uiRoot.Profiler.SetActive(value);
|
||||
}
|
||||
}
|
||||
|
||||
public void Pin(OptionDefinition obj, int order = -1)
|
||||
{
|
||||
if (_uiRoot == null)
|
||||
{
|
||||
Load();
|
||||
}
|
||||
|
||||
if (_pinnedObjects.ContainsKey(obj))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var control = OptionControlFactory.CreateControl(obj);
|
||||
|
||||
control.CachedTransform.SetParent(_uiRoot.Container, false);
|
||||
|
||||
if (order >= 0)
|
||||
{
|
||||
control.CachedTransform.SetSiblingIndex(order);
|
||||
}
|
||||
|
||||
_pinnedObjects.Add(obj, control);
|
||||
_controlList.Add(control);
|
||||
|
||||
OnPinnedStateChanged(obj, true);
|
||||
}
|
||||
|
||||
public void Unpin(OptionDefinition obj)
|
||||
{
|
||||
if (!_pinnedObjects.ContainsKey(obj))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var control = _pinnedObjects[obj];
|
||||
|
||||
_pinnedObjects.Remove(obj);
|
||||
_controlList.Remove(control);
|
||||
|
||||
Destroy(control.CachedGameObject);
|
||||
|
||||
OnPinnedStateChanged(obj, false);
|
||||
}
|
||||
|
||||
private void OnPinnedStateChanged(OptionDefinition option, bool isPinned)
|
||||
{
|
||||
if (OptionPinStateChanged != null)
|
||||
{
|
||||
OptionPinStateChanged(option, isPinned);
|
||||
}
|
||||
}
|
||||
|
||||
public void UnpinAll()
|
||||
{
|
||||
foreach (var op in _pinnedObjects)
|
||||
{
|
||||
Destroy(op.Value.CachedGameObject);
|
||||
}
|
||||
|
||||
_pinnedObjects.Clear();
|
||||
_controlList.Clear();
|
||||
}
|
||||
|
||||
public bool HasPinned(OptionDefinition option)
|
||||
{
|
||||
return _pinnedObjects.ContainsKey(option);
|
||||
}
|
||||
|
||||
protected override void Awake()
|
||||
{
|
||||
base.Awake();
|
||||
|
||||
CachedTransform.SetParent(Hierarchy.Get("SRDebugger"));
|
||||
}
|
||||
|
||||
private void Load()
|
||||
{
|
||||
var prefab = Resources.Load<PinnedUIRoot>(SRDebugPaths.PinnedUIPrefabPath);
|
||||
|
||||
if (prefab == null)
|
||||
{
|
||||
Debug.LogError("[SRDebugger.PinnedUI] Error loading ui prefab");
|
||||
return;
|
||||
}
|
||||
|
||||
var instance = SRInstantiate.Instantiate(prefab);
|
||||
instance.CachedTransform.SetParent(CachedTransform, false);
|
||||
|
||||
_uiRoot = instance;
|
||||
UpdateAnchors();
|
||||
SRDebug.Instance.PanelVisibilityChanged += OnDebugPanelVisibilityChanged;
|
||||
|
||||
Service.Options.OptionsUpdated += OnOptionsUpdated;
|
||||
|
||||
if (OptionsCanvasCreated != null)
|
||||
{
|
||||
OptionsCanvasCreated(_uiRoot.Canvas.GetComponent<RectTransform>());
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateAnchors()
|
||||
{
|
||||
// Setup alignment of Profiler/Options splitter
|
||||
switch (Settings.Instance.ProfilerAlignment)
|
||||
{
|
||||
case PinAlignment.BottomLeft:
|
||||
case PinAlignment.TopLeft:
|
||||
case PinAlignment.CenterLeft:
|
||||
_uiRoot.Profiler.transform.SetSiblingIndex(0);
|
||||
break;
|
||||
|
||||
case PinAlignment.BottomRight:
|
||||
case PinAlignment.TopRight:
|
||||
case PinAlignment.CenterRight:
|
||||
_uiRoot.Profiler.transform.SetSiblingIndex(1);
|
||||
break;
|
||||
}
|
||||
|
||||
// Setup alignment of Profiler vertical layout group
|
||||
switch (Settings.Instance.ProfilerAlignment)
|
||||
{
|
||||
case PinAlignment.TopRight:
|
||||
case PinAlignment.TopLeft:
|
||||
_uiRoot.ProfilerVerticalLayoutGroup.childAlignment = TextAnchor.UpperCenter;
|
||||
break;
|
||||
|
||||
case PinAlignment.BottomRight:
|
||||
case PinAlignment.BottomLeft:
|
||||
_uiRoot.ProfilerVerticalLayoutGroup.childAlignment = TextAnchor.LowerCenter;
|
||||
break;
|
||||
|
||||
case PinAlignment.CenterLeft:
|
||||
case PinAlignment.CenterRight:
|
||||
_uiRoot.ProfilerVerticalLayoutGroup.childAlignment = TextAnchor.MiddleCenter;
|
||||
break;
|
||||
}
|
||||
|
||||
_uiRoot.ProfilerHandleManager.SetAlignment(Settings.Instance.ProfilerAlignment);
|
||||
|
||||
// Setup alignment of options flow layout group
|
||||
switch (Settings.Instance.OptionsAlignment)
|
||||
{
|
||||
case PinAlignment.BottomLeft: // OptionsBottomLeft
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.LowerLeft;
|
||||
break;
|
||||
case PinAlignment.TopLeft:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.UpperLeft;
|
||||
break;
|
||||
case PinAlignment.BottomRight:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.LowerRight;
|
||||
break;
|
||||
case PinAlignment.TopRight:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.UpperRight;
|
||||
break;
|
||||
case PinAlignment.BottomCenter:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.LowerCenter;
|
||||
break;
|
||||
case PinAlignment.TopCenter:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.UpperCenter;
|
||||
break;
|
||||
case PinAlignment.CenterLeft:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.MiddleLeft;
|
||||
break;
|
||||
case PinAlignment.CenterRight:
|
||||
_uiRoot.OptionsLayoutGroup.childAlignment = TextAnchor.MiddleRight;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
protected override void Update()
|
||||
{
|
||||
base.Update();
|
||||
|
||||
if (_queueRefresh)
|
||||
{
|
||||
_queueRefresh = false;
|
||||
Refresh();
|
||||
}
|
||||
}
|
||||
|
||||
private void OnOptionsUpdated(object sender, EventArgs eventArgs)
|
||||
{
|
||||
// Check for removed options.
|
||||
var pinned = _pinnedObjects.Keys.ToList();
|
||||
|
||||
foreach (var op in pinned)
|
||||
{
|
||||
if (!Service.Options.Options.Contains(op))
|
||||
{
|
||||
Unpin(op);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void OnDebugPanelVisibilityChanged(bool isVisible)
|
||||
{
|
||||
// Refresh bindings when debug panel is no longer visible
|
||||
if (!isVisible)
|
||||
{
|
||||
_queueRefresh = true;
|
||||
}
|
||||
}
|
||||
|
||||
private void Refresh()
|
||||
{
|
||||
for (var i = 0; i < _controlList.Count; i++)
|
||||
{
|
||||
_controlList[i].Refresh();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: ba911226d6eee2441ba45b76f81a1d62
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,382 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using Internal;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
using Object = UnityEngine.Object;
|
||||
using SRF.UI;
|
||||
using UnityEngine.UI;
|
||||
|
||||
[Service(typeof (IDebugService))]
|
||||
public class SRDebugService : IDebugService
|
||||
{
|
||||
public IDockConsoleService DockConsole
|
||||
{
|
||||
get { return Service.DockConsole; }
|
||||
}
|
||||
|
||||
public IConsoleFilterState ConsoleFilter
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_consoleFilterState == null)
|
||||
{
|
||||
_consoleFilterState = SRServiceManager.GetService<IConsoleFilterState>();
|
||||
}
|
||||
return _consoleFilterState;
|
||||
}
|
||||
}
|
||||
|
||||
public event VisibilityChangedDelegate PanelVisibilityChanged;
|
||||
public event PinnedUiCanvasCreated PinnedUiCanvasCreated;
|
||||
|
||||
private readonly IDebugPanelService _debugPanelService;
|
||||
private readonly IDebugTriggerService _debugTrigger;
|
||||
private readonly ISystemInformationService _informationService;
|
||||
private readonly IOptionsService _optionsService;
|
||||
private readonly IPinnedUIService _pinnedUiService;
|
||||
private IConsoleFilterState _consoleFilterState;
|
||||
|
||||
private EntryCode? _entryCode;
|
||||
private bool _hasAuthorised;
|
||||
|
||||
private DefaultTabs? _queuedTab;
|
||||
private RectTransform _worldSpaceTransform;
|
||||
private DynamicOptionContainer _looseOptionContainer;
|
||||
|
||||
|
||||
public SRDebugService()
|
||||
{
|
||||
SRServiceManager.RegisterService<IDebugService>(this);
|
||||
|
||||
// Load profiler
|
||||
SRServiceManager.GetService<IProfilerService>();
|
||||
|
||||
// Setup trigger service
|
||||
_debugTrigger = SRServiceManager.GetService<IDebugTriggerService>();
|
||||
|
||||
_informationService = SRServiceManager.GetService<ISystemInformationService>();
|
||||
|
||||
_pinnedUiService = SRServiceManager.GetService<IPinnedUIService>();
|
||||
_pinnedUiService.OptionsCanvasCreated += transform =>
|
||||
{
|
||||
if (PinnedUiCanvasCreated == null) return;
|
||||
try
|
||||
{
|
||||
PinnedUiCanvasCreated(transform);
|
||||
}
|
||||
catch(Exception e)
|
||||
{
|
||||
Debug.LogException(e);
|
||||
}
|
||||
};
|
||||
|
||||
_optionsService = SRServiceManager.GetService<IOptionsService>();
|
||||
|
||||
// Create debug panel service (this does not actually load any UI resources until opened)
|
||||
_debugPanelService = SRServiceManager.GetService<IDebugPanelService>();
|
||||
|
||||
// Subscribe to visibility changes to provide API-facing event for panel open/close
|
||||
_debugPanelService.VisibilityChanged += DebugPanelServiceOnVisibilityChanged;
|
||||
|
||||
_debugTrigger.IsEnabled = Settings.EnableTrigger == Settings.TriggerEnableModes.Enabled ||
|
||||
Settings.EnableTrigger == Settings.TriggerEnableModes.MobileOnly && Application.isMobilePlatform ||
|
||||
Settings.EnableTrigger == Settings.TriggerEnableModes.DevelopmentBuildsOnly && Debug.isDebugBuild;
|
||||
|
||||
_debugTrigger.Position = Settings.TriggerPosition;
|
||||
|
||||
if (Settings.EnableKeyboardShortcuts)
|
||||
{
|
||||
SRServiceManager.GetService<KeyboardShortcutListenerService>();
|
||||
}
|
||||
|
||||
if (Settings.Instance.RequireCode)
|
||||
{
|
||||
if (Settings.Instance.EntryCode.Count != 4)
|
||||
{
|
||||
Debug.LogError("[SRDebugger] RequireCode is enabled, but pin is not 4 digits");
|
||||
}
|
||||
else
|
||||
{
|
||||
_entryCode = new EntryCode(Settings.Instance.EntryCode[0], Settings.Instance.EntryCode[1],
|
||||
Settings.Instance.EntryCode[2], Settings.Instance.EntryCode[3]);
|
||||
}
|
||||
}
|
||||
|
||||
// Ensure that root object cannot be destroyed on scene loads
|
||||
var srDebuggerParent = Hierarchy.Get("SRDebugger");
|
||||
Object.DontDestroyOnLoad(srDebuggerParent.gameObject);
|
||||
|
||||
// Add any options containers that were created on init
|
||||
var internalRegistry = SRServiceManager.GetService<InternalOptionsRegistry>();
|
||||
internalRegistry.SetHandler(_optionsService.AddContainer);
|
||||
}
|
||||
|
||||
public Settings Settings
|
||||
{
|
||||
get { return Settings.Instance; }
|
||||
}
|
||||
|
||||
public bool IsDebugPanelVisible
|
||||
{
|
||||
get { return _debugPanelService.IsVisible; }
|
||||
}
|
||||
|
||||
public bool IsTriggerEnabled
|
||||
{
|
||||
get { return _debugTrigger.IsEnabled; }
|
||||
set { _debugTrigger.IsEnabled = value; }
|
||||
}
|
||||
|
||||
public bool IsTriggerErrorNotificationEnabled
|
||||
{
|
||||
get { return _debugTrigger.ShowErrorNotification; }
|
||||
set { _debugTrigger.ShowErrorNotification = value; }
|
||||
}
|
||||
|
||||
public bool IsProfilerDocked
|
||||
{
|
||||
get { return Service.PinnedUI.IsProfilerPinned; }
|
||||
set { Service.PinnedUI.IsProfilerPinned = value; }
|
||||
}
|
||||
|
||||
public void AddSystemInfo(InfoEntry entry, string category = "Default")
|
||||
{
|
||||
_informationService.Add(entry, category);
|
||||
}
|
||||
|
||||
public void ShowDebugPanel(bool requireEntryCode = true)
|
||||
{
|
||||
if (requireEntryCode && _entryCode.HasValue && !_hasAuthorised)
|
||||
{
|
||||
PromptEntryCode();
|
||||
return;
|
||||
}
|
||||
|
||||
_debugPanelService.IsVisible = true;
|
||||
}
|
||||
|
||||
public void ShowDebugPanel(DefaultTabs tab, bool requireEntryCode = true)
|
||||
{
|
||||
if (requireEntryCode && _entryCode.HasValue && !_hasAuthorised)
|
||||
{
|
||||
_queuedTab = tab;
|
||||
PromptEntryCode();
|
||||
return;
|
||||
}
|
||||
|
||||
_debugPanelService.IsVisible = true;
|
||||
_debugPanelService.OpenTab(tab);
|
||||
}
|
||||
|
||||
public void HideDebugPanel()
|
||||
{
|
||||
_debugPanelService.IsVisible = false;
|
||||
}
|
||||
|
||||
public void SetEntryCode(EntryCode newCode)
|
||||
{
|
||||
_hasAuthorised = false;
|
||||
_entryCode = newCode;
|
||||
}
|
||||
|
||||
public void DisableEntryCode()
|
||||
{
|
||||
_entryCode = null;
|
||||
}
|
||||
|
||||
public void DestroyDebugPanel()
|
||||
{
|
||||
_debugPanelService.IsVisible = false;
|
||||
_debugPanelService.Unload();
|
||||
}
|
||||
|
||||
#region Options
|
||||
|
||||
public void AddOptionContainer(object container)
|
||||
{
|
||||
_optionsService.AddContainer(container);
|
||||
}
|
||||
|
||||
public void RemoveOptionContainer(object container)
|
||||
{
|
||||
_optionsService.RemoveContainer(container);
|
||||
}
|
||||
|
||||
public void AddOption(OptionDefinition option)
|
||||
{
|
||||
if(_looseOptionContainer == null)
|
||||
{
|
||||
_looseOptionContainer = new DynamicOptionContainer();
|
||||
_optionsService.AddContainer(_looseOptionContainer);
|
||||
}
|
||||
|
||||
_looseOptionContainer.AddOption(option);
|
||||
}
|
||||
|
||||
public bool RemoveOption(OptionDefinition option)
|
||||
{
|
||||
if (_looseOptionContainer != null)
|
||||
{
|
||||
return _looseOptionContainer.RemoveOption(option);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public void PinAllOptions(string category)
|
||||
{
|
||||
foreach (var op in _optionsService.Options)
|
||||
{
|
||||
if (op.Category == category)
|
||||
{
|
||||
_pinnedUiService.Pin(op);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void UnpinAllOptions(string category)
|
||||
{
|
||||
foreach (var op in _optionsService.Options)
|
||||
{
|
||||
if (op.Category == category)
|
||||
{
|
||||
_pinnedUiService.Unpin(op);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void PinOption(string name)
|
||||
{
|
||||
foreach (var op in _optionsService.Options)
|
||||
{
|
||||
if (op.Name == name)
|
||||
{
|
||||
_pinnedUiService.Pin(op);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void UnpinOption(string name)
|
||||
{
|
||||
foreach (var op in _optionsService.Options)
|
||||
{
|
||||
if (op.Name == name)
|
||||
{
|
||||
_pinnedUiService.Unpin(op);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void ClearPinnedOptions()
|
||||
{
|
||||
_pinnedUiService.UnpinAll();
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Bug Reporter
|
||||
|
||||
public void ShowBugReportSheet(ActionCompleteCallback onComplete = null, bool takeScreenshot = true,
|
||||
string descriptionContent = null)
|
||||
{
|
||||
var popoverService = SRServiceManager.GetService<BugReportPopoverService>();
|
||||
|
||||
if (popoverService.IsShowingPopover)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
popoverService.ShowBugReporter((succeed, message) =>
|
||||
{
|
||||
if (onComplete != null)
|
||||
{
|
||||
onComplete(succeed);
|
||||
}
|
||||
}, takeScreenshot, descriptionContent);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
private void DebugPanelServiceOnVisibilityChanged(IDebugPanelService debugPanelService, bool b)
|
||||
{
|
||||
if (PanelVisibilityChanged == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
PanelVisibilityChanged(b);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Debug.LogError("[SRDebugger] Event target threw exception (IDebugService.PanelVisiblityChanged)");
|
||||
Debug.LogException(e);
|
||||
}
|
||||
}
|
||||
|
||||
private void PromptEntryCode()
|
||||
{
|
||||
SRServiceManager.GetService<IPinEntryService>()
|
||||
.ShowPinEntry(_entryCode.Value, SRDebugStrings.Current.PinEntryPrompt,
|
||||
entered =>
|
||||
{
|
||||
if (entered)
|
||||
{
|
||||
if (!Settings.Instance.RequireEntryCodeEveryTime)
|
||||
{
|
||||
_hasAuthorised = true;
|
||||
}
|
||||
|
||||
if (_queuedTab.HasValue)
|
||||
{
|
||||
var t = _queuedTab.Value;
|
||||
|
||||
_queuedTab = null;
|
||||
ShowDebugPanel(t, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
ShowDebugPanel(false);
|
||||
}
|
||||
}
|
||||
|
||||
_queuedTab = null;
|
||||
});
|
||||
}
|
||||
|
||||
public RectTransform EnableWorldSpaceMode()
|
||||
{
|
||||
if (_worldSpaceTransform != null)
|
||||
{
|
||||
return _worldSpaceTransform;
|
||||
}
|
||||
|
||||
if (Settings.Instance.UseDebugCamera)
|
||||
{
|
||||
throw new InvalidOperationException("UseDebugCamera cannot be enabled at the same time as EnableWorldSpaceMode.");
|
||||
}
|
||||
|
||||
_debugPanelService.IsVisible = true;
|
||||
|
||||
var root = ((DebugPanelServiceImpl) _debugPanelService).RootObject;
|
||||
root.Canvas.gameObject.RemoveComponentIfExists<SRRetinaScaler>();
|
||||
root.Canvas.gameObject.RemoveComponentIfExists<CanvasScaler>();
|
||||
root.Canvas.renderMode = RenderMode.WorldSpace;
|
||||
|
||||
var rectTransform = root.Canvas.GetComponent<RectTransform>();
|
||||
rectTransform.sizeDelta = new Vector2(1024, 768);
|
||||
rectTransform.position = Vector3.zero;
|
||||
|
||||
return _worldSpaceTransform = rectTransform;
|
||||
}
|
||||
|
||||
public void SetBugReporterHandler(IBugReporterHandler bugReporterHandler)
|
||||
{
|
||||
SRServiceManager.GetService<IBugReportService>().SetHandler(bugReporterHandler);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: aa53ffe51d3a35545b9277a06967b48a
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,210 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
|
||||
[Service(typeof (IConsoleService))]
|
||||
public class StandardConsoleService : IConsoleService, IDisposable
|
||||
{
|
||||
private readonly bool _collapseEnabled;
|
||||
private bool _hasCleared;
|
||||
|
||||
private readonly CircularBuffer<ConsoleEntry> _allConsoleEntries;
|
||||
private CircularBuffer<ConsoleEntry> _consoleEntries;
|
||||
private readonly object _threadLock = new object();
|
||||
|
||||
private ILogHandler _expectedLogHandler;
|
||||
|
||||
public StandardConsoleService()
|
||||
{
|
||||
Application.logMessageReceivedThreaded += UnityLogCallback;
|
||||
_expectedLogHandler = Debug.unityLogger.logHandler;
|
||||
|
||||
SRServiceManager.RegisterService<IConsoleService>(this);
|
||||
_collapseEnabled = Settings.Instance.CollapseDuplicateLogEntries;
|
||||
_allConsoleEntries = new CircularBuffer<ConsoleEntry>(Settings.Instance.MaximumConsoleEntries);
|
||||
}
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
Application.logMessageReceivedThreaded -= UnityLogCallback;
|
||||
if (_consoleEntries != null)
|
||||
{
|
||||
_consoleEntries.Clear();
|
||||
}
|
||||
|
||||
_allConsoleEntries.Clear();
|
||||
}
|
||||
|
||||
public int ErrorCount { get; private set; }
|
||||
public int WarningCount { get; private set; }
|
||||
public int InfoCount { get; private set; }
|
||||
|
||||
public event ConsoleUpdatedEventHandler Updated;
|
||||
public event ConsoleUpdatedEventHandler Error;
|
||||
|
||||
public bool LoggingEnabled
|
||||
{
|
||||
get { return Debug.unityLogger.logEnabled; }
|
||||
set { Debug.unityLogger.logEnabled = value; }
|
||||
}
|
||||
|
||||
public bool LogHandlerIsOverriden
|
||||
{
|
||||
get
|
||||
{
|
||||
return Debug.unityLogger.logHandler != _expectedLogHandler;
|
||||
}
|
||||
}
|
||||
|
||||
public IReadOnlyList<ConsoleEntry> Entries
|
||||
{
|
||||
get
|
||||
{
|
||||
if (!_hasCleared)
|
||||
{
|
||||
return _allConsoleEntries;
|
||||
}
|
||||
|
||||
return _consoleEntries;
|
||||
}
|
||||
}
|
||||
|
||||
public IReadOnlyList<ConsoleEntry> AllEntries
|
||||
{
|
||||
get { return _allConsoleEntries; }
|
||||
}
|
||||
|
||||
public void Clear()
|
||||
{
|
||||
lock (_threadLock)
|
||||
{
|
||||
_hasCleared = true;
|
||||
|
||||
if (_consoleEntries == null)
|
||||
{
|
||||
_consoleEntries = new CircularBuffer<ConsoleEntry>(Settings.Instance.MaximumConsoleEntries);
|
||||
}
|
||||
else
|
||||
{
|
||||
_consoleEntries.Clear();
|
||||
}
|
||||
|
||||
ErrorCount = WarningCount = InfoCount = 0;
|
||||
}
|
||||
|
||||
OnUpdated();
|
||||
}
|
||||
|
||||
protected void OnEntryAdded(ConsoleEntry entry)
|
||||
{
|
||||
if (_hasCleared)
|
||||
{
|
||||
// Decrement counters if adding this entry will push another
|
||||
// entry from the buffer.
|
||||
if (_consoleEntries.IsFull)
|
||||
{
|
||||
AdjustCounter(_consoleEntries.Front().LogType, -1);
|
||||
_consoleEntries.PopFront();
|
||||
}
|
||||
|
||||
_consoleEntries.PushBack(entry);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (_allConsoleEntries.IsFull)
|
||||
{
|
||||
AdjustCounter(_allConsoleEntries.Front().LogType, -1);
|
||||
_allConsoleEntries.PopFront();
|
||||
}
|
||||
}
|
||||
|
||||
_allConsoleEntries.PushBack(entry);
|
||||
OnUpdated();
|
||||
}
|
||||
|
||||
protected void OnEntryDuplicated(ConsoleEntry entry)
|
||||
{
|
||||
entry.Count++;
|
||||
OnUpdated();
|
||||
|
||||
// If has cleared, add this entry again for the current list
|
||||
if (_hasCleared && _consoleEntries.Count == 0)
|
||||
{
|
||||
OnEntryAdded(new ConsoleEntry(entry) {Count = 1});
|
||||
}
|
||||
}
|
||||
|
||||
private void OnUpdated()
|
||||
{
|
||||
if (Updated != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
Updated(this);
|
||||
}
|
||||
catch {}
|
||||
}
|
||||
}
|
||||
|
||||
private void UnityLogCallback(string condition, string stackTrace, LogType type)
|
||||
{
|
||||
//if (condition.StartsWith("[SRConsole]"))
|
||||
// return;
|
||||
|
||||
lock (_threadLock)
|
||||
{
|
||||
var prevMessage = _collapseEnabled && _allConsoleEntries.Count > 0
|
||||
? _allConsoleEntries[_allConsoleEntries.Count - 1]
|
||||
: null;
|
||||
|
||||
AdjustCounter(type, 1);
|
||||
|
||||
if (prevMessage != null && prevMessage.LogType == type && prevMessage.Message == condition &&
|
||||
prevMessage.StackTrace == stackTrace)
|
||||
{
|
||||
OnEntryDuplicated(prevMessage);
|
||||
}
|
||||
else
|
||||
{
|
||||
var newEntry = new ConsoleEntry
|
||||
{
|
||||
LogType = type,
|
||||
StackTrace = stackTrace,
|
||||
Message = condition
|
||||
};
|
||||
|
||||
OnEntryAdded(newEntry);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void AdjustCounter(LogType type, int amount)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case LogType.Assert:
|
||||
case LogType.Error:
|
||||
case LogType.Exception:
|
||||
ErrorCount += amount;
|
||||
|
||||
if (Error != null)
|
||||
{
|
||||
Error.Invoke(this);
|
||||
}
|
||||
break;
|
||||
|
||||
case LogType.Warning:
|
||||
WarningCount += amount;
|
||||
break;
|
||||
|
||||
case LogType.Log:
|
||||
InfoCount += amount;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: b4ff166e8452e1c468f1d0490738b02f
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
@@ -0,0 +1,270 @@
|
||||
namespace SRDebugger.Services.Implementation
|
||||
{
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using SRF;
|
||||
using SRF.Service;
|
||||
using UnityEngine;
|
||||
|
||||
/// <summary>
|
||||
/// Reports system specifications and environment information. Information that can
|
||||
/// be used to identify a user is marked as private, and won't be included in any generated
|
||||
/// reports.
|
||||
/// </summary>
|
||||
[Service(typeof(ISystemInformationService))]
|
||||
public class StandardSystemInformationService : ISystemInformationService
|
||||
{
|
||||
private readonly Dictionary<string, IList<InfoEntry>> _info = new Dictionary<string, IList<InfoEntry>>();
|
||||
|
||||
public StandardSystemInformationService()
|
||||
{
|
||||
CreateDefaultSet();
|
||||
}
|
||||
|
||||
public IEnumerable<string> GetCategories()
|
||||
{
|
||||
return _info.Keys;
|
||||
}
|
||||
|
||||
public IList<InfoEntry> GetInfo(string category)
|
||||
{
|
||||
IList<InfoEntry> list;
|
||||
|
||||
if (!_info.TryGetValue(category, out list))
|
||||
{
|
||||
Debug.LogError("[SystemInformationService] Category not found: {0}".Fmt(category));
|
||||
return new InfoEntry[0];
|
||||
}
|
||||
|
||||
return list;
|
||||
}
|
||||
|
||||
public void Add(InfoEntry info, string category = "Default")
|
||||
{
|
||||
IList<InfoEntry> list;
|
||||
|
||||
if (!_info.TryGetValue(category, out list))
|
||||
{
|
||||
list = new List<InfoEntry>();
|
||||
_info.Add(category, list);
|
||||
}
|
||||
|
||||
if (list.Any(p => p.Title == info.Title))
|
||||
{
|
||||
throw new ArgumentException("An InfoEntry object with the same title already exists in that category.", "info");
|
||||
}
|
||||
|
||||
list.Add(info);
|
||||
}
|
||||
|
||||
public Dictionary<string, Dictionary<string, object>> CreateReport(bool includePrivate = false)
|
||||
{
|
||||
var dict = new Dictionary<string, Dictionary<string, object>>(_info.Count);
|
||||
|
||||
foreach (var keyValuePair in _info)
|
||||
{
|
||||
var category = new Dictionary<string, object>(keyValuePair.Value.Count);
|
||||
|
||||
foreach (var systemInfo in keyValuePair.Value)
|
||||
{
|
||||
if (systemInfo.IsPrivate && !includePrivate)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
category.Add(systemInfo.Title, systemInfo.Value);
|
||||
}
|
||||
|
||||
dict.Add(keyValuePair.Key, category);
|
||||
}
|
||||
|
||||
return dict;
|
||||
}
|
||||
|
||||
private void CreateDefaultSet()
|
||||
{
|
||||
_info.Add("System", new[]
|
||||
{
|
||||
InfoEntry.Create("Operating System", UnityEngine.SystemInfo.operatingSystem),
|
||||
InfoEntry.Create("Device Name", UnityEngine.SystemInfo.deviceName, true),
|
||||
InfoEntry.Create("Device Type", UnityEngine.SystemInfo.deviceType),
|
||||
InfoEntry.Create("Device Model", UnityEngine.SystemInfo.deviceModel),
|
||||
InfoEntry.Create("CPU Type", UnityEngine.SystemInfo.processorType),
|
||||
InfoEntry.Create("CPU Count", UnityEngine.SystemInfo.processorCount),
|
||||
InfoEntry.Create("System Memory", SRFileUtil.GetBytesReadable(((long) UnityEngine.SystemInfo.systemMemorySize)*1024*1024))
|
||||
//Info.Create("Process Name", () => Process.GetCurrentProcess().ProcessName)
|
||||
});
|
||||
|
||||
if (SystemInfo.batteryStatus != BatteryStatus.Unknown)
|
||||
{
|
||||
_info.Add("Battery", new[]
|
||||
{
|
||||
InfoEntry.Create("Status", UnityEngine.SystemInfo.batteryStatus),
|
||||
InfoEntry.Create("Battery Level", UnityEngine.SystemInfo.batteryLevel)
|
||||
});
|
||||
}
|
||||
|
||||
#if ENABLE_IL2CPP
|
||||
const string IL2CPP = "Yes";
|
||||
#else
|
||||
const string IL2CPP = "No";
|
||||
#endif
|
||||
|
||||
_info.Add("Unity", new[]
|
||||
{
|
||||
InfoEntry.Create("Version", Application.unityVersion),
|
||||
InfoEntry.Create("Debug", Debug.isDebugBuild),
|
||||
InfoEntry.Create("Unity Pro", Application.HasProLicense()),
|
||||
InfoEntry.Create("Genuine",
|
||||
"{0} ({1})".Fmt(Application.genuine ? "Yes" : "No",
|
||||
Application.genuineCheckAvailable ? "Trusted" : "Untrusted")),
|
||||
InfoEntry.Create("System Language", Application.systemLanguage),
|
||||
InfoEntry.Create("Platform", Application.platform),
|
||||
InfoEntry.Create("Install Mode", Application.installMode),
|
||||
InfoEntry.Create("Sandbox", Application.sandboxType),
|
||||
InfoEntry.Create("IL2CPP", IL2CPP),
|
||||
InfoEntry.Create("Application Version", Application.version),
|
||||
InfoEntry.Create("Application Id", Application.identifier),
|
||||
InfoEntry.Create("SRDebugger Version", SRDebug.Version),
|
||||
});
|
||||
|
||||
_info.Add("Display", new[]
|
||||
{
|
||||
InfoEntry.Create("Resolution", () => Screen.width + "x" + Screen.height),
|
||||
InfoEntry.Create("DPI", () => Screen.dpi),
|
||||
InfoEntry.Create("Fullscreen", () => Screen.fullScreen),
|
||||
InfoEntry.Create("Fullscreen Mode", () => Screen.fullScreenMode),
|
||||
InfoEntry.Create("Orientation", () => Screen.orientation),
|
||||
});
|
||||
|
||||
_info.Add("Runtime", new[]
|
||||
{
|
||||
InfoEntry.Create("Play Time", () => Time.unscaledTime),
|
||||
InfoEntry.Create("Level Play Time", () => Time.timeSinceLevelLoad),
|
||||
#if UNITY_4_6 || UNITY_4_7 || UNITY_5_0 || UNITY_5_1 || UNITY_5_2
|
||||
InfoEntry.Create("Current Level", () => Application.loadedLevelName),
|
||||
#else
|
||||
InfoEntry.Create("Current Level", () =>
|
||||
{
|
||||
var activeScene = UnityEngine.SceneManagement.SceneManager.GetActiveScene();
|
||||
return "{0} (Index: {1})".Fmt(activeScene.name, activeScene.buildIndex);
|
||||
}),
|
||||
#endif
|
||||
InfoEntry.Create("Quality Level",
|
||||
() =>
|
||||
QualitySettings.names[QualitySettings.GetQualityLevel()] + " (" +
|
||||
QualitySettings.GetQualityLevel() + ")")
|
||||
});
|
||||
|
||||
// Check for cloud build manifest
|
||||
var cloudBuildManifest = (TextAsset)Resources.Load("UnityCloudBuildManifest.json");
|
||||
var manifestDict = cloudBuildManifest != null
|
||||
? Json.Deserialize(cloudBuildManifest.text) as Dictionary<string, object>
|
||||
: null;
|
||||
|
||||
if (manifestDict != null)
|
||||
{
|
||||
var manifestList = new List<InfoEntry>(manifestDict.Count);
|
||||
|
||||
foreach (var kvp in manifestDict)
|
||||
{
|
||||
if (kvp.Value == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
var value = kvp.Value.ToString();
|
||||
manifestList.Add(InfoEntry.Create(GetCloudManifestPrettyName(kvp.Key), value));
|
||||
}
|
||||
|
||||
_info.Add("Build", manifestList);
|
||||
}
|
||||
|
||||
_info.Add("Features", new[]
|
||||
{
|
||||
InfoEntry.Create("Location", UnityEngine.SystemInfo.supportsLocationService),
|
||||
InfoEntry.Create("Accelerometer", UnityEngine.SystemInfo.supportsAccelerometer),
|
||||
InfoEntry.Create("Gyroscope", UnityEngine.SystemInfo.supportsGyroscope),
|
||||
InfoEntry.Create("Vibration", UnityEngine.SystemInfo.supportsVibration),
|
||||
InfoEntry.Create("Audio", UnityEngine.SystemInfo.supportsAudio)
|
||||
});
|
||||
|
||||
#if UNITY_IOS
|
||||
|
||||
_info.Add("iOS", new[] {
|
||||
|
||||
#if UNITY_5 || UNITY_5_3_OR_NEWER
|
||||
InfoEntry.Create("Generation", UnityEngine.iOS.Device.generation),
|
||||
InfoEntry.Create("Ad Tracking", UnityEngine.iOS.Device.advertisingTrackingEnabled),
|
||||
#else
|
||||
InfoEntry.Create("Generation", iPhone.generation),
|
||||
InfoEntry.Create("Ad Tracking", iPhone.advertisingTrackingEnabled),
|
||||
#endif
|
||||
});
|
||||
|
||||
#endif
|
||||
#pragma warning disable 618
|
||||
_info.Add("Graphics - Device", new[]
|
||||
{
|
||||
InfoEntry.Create("Device Name", UnityEngine.SystemInfo.graphicsDeviceName),
|
||||
InfoEntry.Create("Device Vendor", UnityEngine.SystemInfo.graphicsDeviceVendor),
|
||||
InfoEntry.Create("Device Version", UnityEngine.SystemInfo.graphicsDeviceVersion),
|
||||
InfoEntry.Create("Graphics Memory", SRFileUtil.GetBytesReadable(((long) UnityEngine.SystemInfo.graphicsMemorySize)*1024*1024)),
|
||||
InfoEntry.Create("Max Tex Size", UnityEngine.SystemInfo.maxTextureSize),
|
||||
});
|
||||
|
||||
_info.Add("Graphics - Features", new[]
|
||||
{
|
||||
InfoEntry.Create("UV Starts at top", UnityEngine.SystemInfo.graphicsUVStartsAtTop),
|
||||
InfoEntry.Create("Shader Level", UnityEngine.SystemInfo.graphicsShaderLevel),
|
||||
InfoEntry.Create("Multi Threaded", UnityEngine.SystemInfo.graphicsMultiThreaded),
|
||||
InfoEntry.Create("Hidden Service Removal (GPU)", UnityEngine.SystemInfo.hasHiddenSurfaceRemovalOnGPU),
|
||||
InfoEntry.Create("Uniform Array Indexing (Fragment Shaders)", UnityEngine.SystemInfo.hasDynamicUniformArrayIndexingInFragmentShaders),
|
||||
InfoEntry.Create("Shadows", UnityEngine.SystemInfo.supportsShadows),
|
||||
InfoEntry.Create("Raw Depth Sampling (Shadows)", UnityEngine.SystemInfo.supportsRawShadowDepthSampling),
|
||||
InfoEntry.Create("Motion Vectors", UnityEngine.SystemInfo.supportsMotionVectors),
|
||||
InfoEntry.Create("Cubemaps", UnityEngine.SystemInfo.supportsRenderToCubemap),
|
||||
InfoEntry.Create("Image Effects", UnityEngine.SystemInfo.supportsImageEffects),
|
||||
InfoEntry.Create("3D Textures", UnityEngine.SystemInfo.supports3DTextures),
|
||||
InfoEntry.Create("2D Array Textures", UnityEngine.SystemInfo.supports2DArrayTextures),
|
||||
InfoEntry.Create("3D Render Textures", UnityEngine.SystemInfo.supports3DRenderTextures),
|
||||
InfoEntry.Create("Cubemap Array Textures", UnityEngine.SystemInfo.supportsCubemapArrayTextures),
|
||||
InfoEntry.Create("Copy Texture Support", UnityEngine.SystemInfo.copyTextureSupport),
|
||||
InfoEntry.Create("Compute Shaders", UnityEngine.SystemInfo.supportsComputeShaders),
|
||||
InfoEntry.Create("Instancing", UnityEngine.SystemInfo.supportsInstancing),
|
||||
InfoEntry.Create("Hardware Quad Topology", UnityEngine.SystemInfo.supportsHardwareQuadTopology),
|
||||
InfoEntry.Create("32-bit index buffer", UnityEngine.SystemInfo.supports32bitsIndexBuffer),
|
||||
InfoEntry.Create("Sparse Textures", UnityEngine.SystemInfo.supportsSparseTextures),
|
||||
InfoEntry.Create("Render Target Count", UnityEngine.SystemInfo.supportedRenderTargetCount),
|
||||
InfoEntry.Create("Separated Render Targets Blend", UnityEngine.SystemInfo.supportsSeparatedRenderTargetsBlend),
|
||||
InfoEntry.Create("Multisampled Textures", UnityEngine.SystemInfo.supportsMultisampledTextures),
|
||||
InfoEntry.Create("Texture Wrap Mirror Once", UnityEngine.SystemInfo.supportsTextureWrapMirrorOnce),
|
||||
InfoEntry.Create("Reversed Z Buffer", UnityEngine.SystemInfo.usesReversedZBuffer)
|
||||
});
|
||||
#pragma warning restore 618
|
||||
|
||||
}
|
||||
|
||||
private static string GetCloudManifestPrettyName(string name)
|
||||
{
|
||||
switch (name)
|
||||
{
|
||||
case "scmCommitId":
|
||||
return "Commit";
|
||||
|
||||
case "scmBranch":
|
||||
return "Branch";
|
||||
|
||||
case "cloudBuildTargetName":
|
||||
return "Build Target";
|
||||
|
||||
case "buildStartTime":
|
||||
return "Build Date";
|
||||
}
|
||||
|
||||
// Return name with first letter capitalised
|
||||
return name.Substring(0, 1).ToUpper() + name.Substring(1);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,8 @@
|
||||
fileFormatVersion: 2
|
||||
guid: 605ec79db587f5345b0a0b989487631e
|
||||
MonoImporter:
|
||||
serializedVersion: 2
|
||||
defaultReferences: []
|
||||
executionOrder: 0
|
||||
icon: {instanceID: 0}
|
||||
userData:
|
Reference in New Issue
Block a user