diff --git a/HugMod/Assets/hug_bundle b/HugMod/Assets/hug_bundle index 08589db..fb42e62 100644 Binary files a/HugMod/Assets/hug_bundle and b/HugMod/Assets/hug_bundle differ diff --git a/HugMod/Assets/hug_bundle.manifest b/HugMod/Assets/hug_bundle.manifest index c0dd6e4..9a82fb4 100644 --- a/HugMod/Assets/hug_bundle.manifest +++ b/HugMod/Assets/hug_bundle.manifest @@ -1,9 +1,9 @@ ManifestFileVersion: 0 -CRC: 2035962915 +CRC: 4286573153 Hashes: AssetFileHash: serializedVersion: 2 - Hash: 6b4888750e29bc0c2f383a16efc70007 + Hash: 56a78e3700c5c2ce3fbf9650e89543d0 TypeTreeHash: serializedVersion: 2 Hash: 81be94c203cbc62109b6f5f6fe206615 diff --git a/HugMod/HugComponent.cs b/HugMod/HugComponent.cs index ef661ec..76f2238 100644 --- a/HugMod/HugComponent.cs +++ b/HugMod/HugComponent.cs @@ -22,7 +22,7 @@ public class HugComponent : MonoBehaviour //tabled private ScreenPrompt hugPrompt = new(InputLibrary.interactSecondary, " " + "Hug"); - private Vector3 focusPoint = new(0, 0.1f, 0); + private Vector3 focusPoint = new(0, 0, 0); private string hugTrigger = "react_None"; private bool fullbodyReact = true, keepFootAnimRight = false, keepFootAnimLeft = false, keepHandAnimRight = false, keepHandAnimLeft = false; @@ -52,8 +52,13 @@ public class HugComponent : MonoBehaviour public event Action OnDestroyEvent; + private void Awake() { SetHugEnabled(false); } + public void Initialise() { + var flag = gameObject.activeInHierarchy; + gameObject.SetActive(true); + HugReceiver = gameObject.GetComponentInChildren(); if (HugReceiver == null) { @@ -61,7 +66,7 @@ public void Initialise() if (receiverCollider == null) { HugModInstance.ModHelper.Console.WriteLine($"Couldn't find OWCollider in children of object \"{gameObject.name}\". HugComponent will be disabled.", MessageType.Error); - enabled = false; + SetHugEnabled(false); return; } if (receiverCollider.gameObject.layer == LayerMask.NameToLayer("Ignore Raycast")) receiverCollider.gameObject.layer = LayerMask.NameToLayer("Default"); @@ -83,7 +88,7 @@ public void Initialise() } else { - HugAnimator = gameObject.GetComponentInChildren(true); + HugAnimator = gameObject.GetComponentInChildren(); lookSpring = new(50, 14, 1); } @@ -96,13 +101,15 @@ public void Initialise() } hugOverrider.runtimeAnimatorController = AltRuntimeController; + SetHugEnabled(true); + gameObject.SetActive(flag); } private bool AddTriggerCollider(Collider compareCollider) { if (compareCollider == null) return false; - var triggerObj = compareCollider.gameObject.transform.CreateChild("Hug_TriggerCollider"); + var triggerObj = compareCollider.gameObject.CreateChild("Hug_TriggerCollider"); triggerObj.layer = LayerMask.NameToLayer("Ignore Raycast"); hugTriggerCollider = triggerObj.AddComponent(); @@ -115,11 +122,10 @@ private bool AddTriggerCollider(Collider compareCollider) else { hugTriggerCollider.Remove(); - HugModInstance.ModHelper.Console.WriteLine($"Collider type associated with object \"{gameObject.name}\" is not supported. HugComponent will be disabled.", MessageType.Error); - enabled = false; + HugModInstance.ModHelper.Console.WriteLine($"Collider type is not supported. HugComponent associated with object \"{gameObject.name}\" will be disabled.", MessageType.Error); + SetHugEnabled(false); return false; } - return true; } @@ -169,7 +175,7 @@ public void SetHugEnabled(bool enable) public void SetLookAtPlayerEnabled(bool enable) { if (hugIK != null) hugIK.enabled = enable; - else HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugIK Component on object \"{HugAnimator.gameObject.name}\".", MessageType.Error); + else HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugIK Component associated with object \"{gameObject.name}\".", MessageType.Error); } public void ForceLookAtPlayer(bool enable) { forceLookAtPlayer = enable; } public void SetPrompt(string name) { hugPrompt = new(InputLibrary.interactSecondary, " " + "Hug " + name); } @@ -207,8 +213,8 @@ public void GetUnderlayTransitionData(out float transitionTime, out int transiti transitionClip = this.transitionClip; } - public bool IsSequenceInProgress() { return sequenceInProgress; } - public bool IsAnimatorControllerSwapped() { return HugAnimator.runtimeAnimatorController == hugOverrider; } + public bool IsSequenceInProgress() => sequenceInProgress; + public bool IsAnimatorControllerSwapped() => (HugAnimator != null) && (HugAnimator.runtimeAnimatorController == hugOverrider); public void ChangeInteractReceiver(InteractReceiver newReceiver, bool resetTriggerCollider = false) { @@ -218,6 +224,7 @@ public void ChangeInteractReceiver(InteractReceiver newReceiver, bool resetTrigg HugReceiver.OnLoseFocus -= DisableHug; } HugReceiver = newReceiver; + if (newReceiver == null) return; newReceiver.OnGainFocus += EnableHug; newReceiver.OnLoseFocus += DisableHug; @@ -226,26 +233,26 @@ public void ChangeInteractReceiver(InteractReceiver newReceiver, bool resetTrigg } public void ChangeTriggerCollider(Collider newCompareCollider) { - if (hugTriggerCollider != null) hugTriggerCollider.Remove(); + hugTriggerCollider.Exists()?.Remove(); AddTriggerCollider(newCompareCollider); } - public void ChangePrimaryAnimator(Animator newAnimator, RuntimeAnimatorController newAnimatorController) + public void ChangePrimaryAnimator(Animator newAnimator, bool resetAnimatorController = true) { HugAnimator = newAnimator; - initialRuntimeController = newAnimatorController; isAnimated = newAnimator != null && newAnimator.avatar.isHuman; + if (resetAnimatorController && isAnimated) initialRuntimeController = newAnimator.runtimeAnimatorController; if ((hugIK == null && !isAnimated) || (hugIK != null && isAnimated && hugIK.gameObject == newAnimator.gameObject)) return; - if (hugIK != null) hugIK.Remove(); - if (newAnimator == null) return; - hugIK = newAnimator.gameObject.AddComponent(); - hugIK.SetHugComponent(this); + hugIK.Exists()?.Remove(); + hugIK = newAnimator.Exists()?.gameObject.AddComponent(); + hugIK.Exists()?.SetHugComponent(this); } + public void ChangeAnimatorController(RuntimeAnimatorController newAnimatorController) { initialRuntimeController = newAnimatorController; } public void ChangeSecondaryAnimator(Animator newAnimator) { SecondaryAnimator = newAnimator; } - public void ChangeCharacterAnimController(CharacterAnimController newAnimController) + public void ChangeCharacterAnimController(CharacterAnimController newCharacterAnimController) { - characterAnimController = newAnimController; - lookSpring = newAnimController.lookSpring; + characterAnimController = newCharacterAnimController; + lookSpring = newCharacterAnimController.Exists()?.lookSpring ?? new(50, 14, 1); } @@ -253,7 +260,7 @@ public void ChangeCharacterAnimController(CharacterAnimController newAnimControl private void EnableHug() { if (!enabled) return; - Locator.GetPromptManager().AddScreenPrompt(hugPrompt, PromptPosition.Center, true); + Locator.GetPromptManager().AddScreenPrompt(hugPrompt, PromptPosition.Center, OWInput.IsInputMode(InputMode.Character)); canHug = true; } @@ -280,10 +287,9 @@ public void OnAnimatorIK() private void Update() { - if (OWInput.GetInputMode() == InputMode.Character) hugPrompt.SetVisibility(true); - else hugPrompt.SetVisibility(false); + hugPrompt.SetVisibility(OWInput.IsInputMode(InputMode.Character)); - if (OWInput.IsNewlyPressed(InputLibrary.interactSecondary) && canHug && OWInput.GetInputMode() == InputMode.Character) BeginHugSequence(); + if (OWInput.IsNewlyPressed(InputLibrary.interactSecondary, InputMode.Character) && canHug) BeginHugSequence(); } @@ -320,7 +326,7 @@ private IEnumerator HugSequenceMain() { CommenceHug(); yield return null; - if (isAnimated && HugAnimator.enabled && hugTrigger != "react_None") + if (isAnimated && hugTrigger != "react_None" && HugAnimator.enabled) { var wasHugging = IsAnimatorControllerSwapped(); while (HugAnimator.GetCurrentAnimatorClipInfo(0).Length == 0) yield return null; @@ -373,7 +379,7 @@ private void PlayHugAnimation(bool wasHugging) HugAnimator.SetLayerWeight(HugAnimator.GetLayerIndex("Keep Right Hand Pose"), keepHandAnimRight ? 1 : 0); HugAnimator.SetLayerWeight(HugAnimator.GetLayerIndex("Keep Left Hand Pose"), keepHandAnimLeft ? 1 : 0); } - SecondaryAnimator?.Play(SecondaryAnimator.GetCurrentAnimatorStateInfo(0).shortNameHash, 0, time); + SecondaryAnimator.Exists()?.Play(SecondaryAnimator.GetCurrentAnimatorStateInfo(0).shortNameHash, 0, time); HugAnimator.SetTrigger(hugTrigger); } @@ -411,7 +417,7 @@ private IEnumerator ResetAnimator(float delay) HugAnimator.Play(stateHash, 0, time); if (HugAnimator.layerCount > 1 && HugAnimator.GetCurrentAnimatorStateInfo(1).shortNameHash == stateHash) HugAnimator.Play(stateHash, 1, time); } - SecondaryAnimator?.Play(SecondaryAnimator.GetCurrentAnimatorStateInfo(0).shortNameHash, 0, time); + SecondaryAnimator.Exists()?.Play(SecondaryAnimator.GetCurrentAnimatorStateInfo(0).shortNameHash, 0, time); OnHugFinish?.Invoke(); sequenceInProgress = false; } @@ -456,6 +462,15 @@ private void CancelPending() } - private void OnDestroy() { OnDestroyEvent?.Invoke(); } + private void OnDestroy() + { + SetHugEnabled(false); + if (HugReceiver != null) + { + HugReceiver.OnGainFocus -= EnableHug; + HugReceiver.OnLoseFocus -= DisableHug; + } + OnDestroyEvent?.Invoke(); + } } } diff --git a/HugMod/HugMod.cs b/HugMod/HugMod.cs index 7917b9d..a96307e 100644 --- a/HugMod/HugMod.cs +++ b/HugMod/HugMod.cs @@ -11,6 +11,7 @@ public class HugMod : ModBehaviour { public static HugMod HugModInstance; public static Harmony HarmonyInstance; + public static HugModSettings Settings = new(); public static RuntimeAnimatorController AltRuntimeController; public static bool PlayerHasDLC; @@ -21,7 +22,6 @@ private void Awake() { HugModInstance = this; HarmonyInstance = new Harmony("VioVayo.HugMod"); - HugPatches.Apply(); } private bool MurderCheck() @@ -37,9 +37,11 @@ private void Start() { ModHelper.Console.WriteLine("Murder is bad >:C", MessageType.Error); this.enabled = false; - return; + return; } + var settings = HugModInstance.ModHelper.Storage.Load("settings.json"); + if (settings != null) Settings = settings; var hugBundle = ModHelper.Assets.LoadBundle("Assets/hug_bundle"); AltRuntimeController = hugBundle.LoadAsset("Assets/HugModAssets/HugAnims.prefab").GetComponent().runtimeAnimatorController; @@ -57,7 +59,16 @@ private void Start() TargetManager.SetUpHugTargets(loadScene); }; + HugPatches.Apply(); ModHelper.Console.WriteLine($"{nameof(HugMod)} is loaded! " + (PlayerHasDLC ? HuggableFrightsMain.HFEnabledMessage(false) : ""), MessageType.Success); } + + public static void UpdateSettings() { HugModInstance.ModHelper.Storage.Save(Settings, "settings.json"); } + + public class HugModSettings + { + public bool FriendmakerModeEnabled = false; + public bool SillyGhostNames = false; + } } } \ No newline at end of file diff --git a/HugMod/HugModApi.cs b/HugMod/HugModApi.cs index 7498863..a22d903 100644 --- a/HugMod/HugModApi.cs +++ b/HugMod/HugModApi.cs @@ -72,21 +72,21 @@ public void SetAnimationMasks(GameObject hugObject, bool fullbodyReact, bool kee else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } - public void SetUnderlayTransition(GameObject hugObject, string transitionClipName, int transitionHash, float transitionTime) + public void SetUnderlayTransition(GameObject hugObject, AnimationClip transitionClip, int transitionHash, float transitionTime) { - if (hugObject.TryGetComponent(out HugComponent hug)) hug.SetUnderlayTransition(transitionClipName, transitionHash, transitionTime); + if (hugObject.TryGetComponent(out HugComponent hug)) hug.SetUnderlayTransition(transitionClip, transitionHash, transitionTime); else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } - public void SetUnderlayTransition(GameObject hugObject, AnimationClip transitionClip, int transitionHash, float transitionTime) + public void SetUnderlayTransition(GameObject hugObject, string transitionClipName, int transitionHash, float transitionTime) { - if (hugObject.TryGetComponent(out HugComponent hug)) hug.SetUnderlayTransition(transitionClip, transitionHash, transitionTime); + if (hugObject.TryGetComponent(out HugComponent hug)) hug.SetUnderlayTransition(transitionClipName, transitionHash, transitionTime); else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } //-----Get stuff----- - public InteractReceiver GetHugReceiver(GameObject hugObject) + public InteractReceiver GetInteractReceiver(GameObject hugObject) { if (hugObject.TryGetComponent(out HugComponent hug)) return hug.HugReceiver; else @@ -96,7 +96,7 @@ public InteractReceiver GetHugReceiver(GameObject hugObject) } } - public Animator GetHugAnimator(GameObject hugObject) + public Animator GetPrimaryAnimator(GameObject hugObject) { if (hugObject.TryGetComponent(out HugComponent hug)) return hug.HugAnimator; else @@ -204,9 +204,15 @@ public void ChangeTriggerCollider(GameObject hugObject, Collider newCompareColli else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } - public void ChangePrimaryAnimator(GameObject hugObject, Animator newAnimator, RuntimeAnimatorController newAnimatorController) + public void ChangePrimaryAnimator(GameObject hugObject, Animator newAnimator, bool resetAnimatorController) + { + if (hugObject.TryGetComponent(out HugComponent hug)) hug.ChangePrimaryAnimator(newAnimator, resetAnimatorController); + else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); + } + + public void ChangeAnimatorController(GameObject hugObject, RuntimeAnimatorController newAnimatorController) { - if (hugObject.TryGetComponent(out HugComponent hug)) hug.ChangePrimaryAnimator(newAnimator, newAnimatorController); + if (hugObject.TryGetComponent(out HugComponent hug)) hug.ChangeAnimatorController(newAnimatorController); else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } @@ -216,9 +222,9 @@ public void ChangeSecondaryAnimator(GameObject hugObject, Animator newAnimator) else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } - public void ChangeCharacterAnimController(GameObject hugObject, CharacterAnimController newAnimController) + public void ChangeCharacterAnimController(GameObject hugObject, CharacterAnimController newCharacterAnimController) { - if (hugObject.TryGetComponent(out HugComponent hug)) hug.ChangeCharacterAnimController(newAnimController); + if (hugObject.TryGetComponent(out HugComponent hug)) hug.ChangeCharacterAnimController(newCharacterAnimController); else HugMod.HugModInstance.ModHelper.Console.WriteLine($"Couldn't find HugComponent on \"{hugObject.name}\".", MessageType.Error); } } diff --git a/HugMod/HugModUtilities.cs b/HugMod/HugModUtilities.cs index 24d1802..b9d0892 100644 --- a/HugMod/HugModUtilities.cs +++ b/HugMod/HugModUtilities.cs @@ -5,7 +5,7 @@ namespace HugMod { public static class HugModUtilities { - public static T[] AddToArray(T[] array, params T[] toAdd) + public static T[] AddToArray(this T[] array, params T[] toAdd) { var list = array.ToList(); foreach (var addition in toAdd) list.Add(addition); @@ -13,10 +13,17 @@ public static T[] AddToArray(T[] array, params T[] toAdd) } public static Transform FindInDescendants(this GameObject gameObject, string name, bool includeInactive = true) + => gameObject.GetComponentsInChildren(includeInactive).FirstOrDefault(obj => obj.gameObject.name == name); + + public static bool TryGetComponentInChildren(this GameObject gameObject, out T component) where T : Component { - return gameObject.GetComponentsInChildren(includeInactive).Where(obj => obj.gameObject.name == name).First(); + component = gameObject.GetComponentInChildren(); + return component != null; } + public static GameObject CreateChild(this GameObject parentObject, string name, Vector3 localPosition = default, Vector3 localEulerAngles = default, float scaleMultiplier = 1) + => parentObject.transform.CreateChild(name, localPosition, localEulerAngles, scaleMultiplier); + public static GameObject CreateChild(this Transform parentTransform, string name, Vector3 localPosition = default, Vector3 localEulerAngles = default, float scaleMultiplier = 1) { var childObj = new GameObject(name); @@ -26,5 +33,8 @@ public static GameObject CreateChild(this Transform parentTransform, string name childObj.transform.localScale = scaleMultiplier * Vector3.one; return childObj; } + + public static T Exists(this T obj) where T : Object + => (obj != null) ? obj : null; //Enable use of null conditional operators with destroyed Unity objects } } diff --git a/HugMod/HugPatches.cs b/HugMod/HugPatches.cs index 3a1d278..aa99284 100644 --- a/HugMod/HugPatches.cs +++ b/HugMod/HugPatches.cs @@ -20,7 +20,7 @@ public class HugPatches public static IEnumerable PlayerCharacterController_UpdateMovement_Transpiler(IEnumerable instructions) { var matcher = new CodeMatcher(instructions).MatchForward(false, - new CodeMatch(OpCodes.Call, AccessTools.Method(typeof(OWInput), "OWInput.GetAxisValue", new Type[] { typeof(IInputCommands), typeof(InputMode) })), + new CodeMatch(OpCodes.Call, AccessTools.Method(typeof(OWInput), nameof(OWInput.GetAxisValue), new Type[] { typeof(IInputCommands), typeof(InputMode) })), new CodeMatch(OpCodes.Stloc_0) ).Advance(2); @@ -45,14 +45,5 @@ public static bool UnityLogger_OnLogMessageReceived(string message) // Filter out goofy error that doesn't actually break anything return !message.EndsWith(") is out of bounds (size=0)"); } - - - //ONLY FOR DEBUG - [HarmonyPrefix] - [HarmonyPatch(typeof(ShipLogManager), nameof(ShipLogManager.CheckForCompletionAchievement))] - public static bool ShipLogManager_CheckForCompletionAchievement_Prefix() - { - return false; - } } } diff --git a/HugMod/HuggableFrights/GhostNavigation.cs b/HugMod/HuggableFrights/GhostNavigation.cs index f717d73..c8d26a0 100644 --- a/HugMod/HuggableFrights/GhostNavigation.cs +++ b/HugMod/HuggableFrights/GhostNavigation.cs @@ -11,6 +11,8 @@ public class GhostNavigation : MonoBehaviour private List localWaypoints = new(); private int maxCapacity = 5; + private bool isInBounds = false, wasInBounds = false; + public void Start() { ghostController = gameObject.GetComponent(); } @@ -30,6 +32,16 @@ public void UpdateNavigationToTarget(Vector3 localTarget, MoveType moveType) if (Physics.Raycast(gameObject.transform.position + gameObject.transform.up.normalized, -gameObject.transform.up, out RaycastHit hit, 1.25f, OWLayerMask.physicalMask)) gameObject.transform.position = hit.point; + //use existing navigation code while within bounds + wasInBounds = isInBounds; + isInBounds = ghostController.GetNodeMap().CheckLocalPointInBounds(gameObject.transform.localPosition); + if (isInBounds) + { + if (!ghostController.IsMoving()) ghostController.PathfindToLocalPosition(localTarget, moveType); + return; + } + else if (wasInBounds) AddLocalWaypoint(gameObject.transform.localPosition); + //continuously projects target onto plane going through _transform.position var globalTarget = ghostController.LocalToWorldPosition(localTarget); var projection = Vector3.ProjectOnPlane(globalTarget - gameObject.transform.position, gameObject.transform.up) + gameObject.transform.position; diff --git a/HugMod/HuggableFrights/HuggableFrightsMain.cs b/HugMod/HuggableFrights/HuggableFrightsMain.cs index b4241d6..6fb1dc5 100644 --- a/HugMod/HuggableFrights/HuggableFrightsMain.cs +++ b/HugMod/HuggableFrights/HuggableFrightsMain.cs @@ -6,14 +6,11 @@ using UnityEngine; using UnityEngine.UI; using static HugMod.HugMod; -using static HugMod.HugModUtilities; namespace HugMod.HuggableFrights { public class HuggableFrightsMain { - public static bool IsHuggableFrightsEnabled { get; private set; } = false; - public static List OwlBrains { get; private set; } = new(); public static GhostAction.Name HuggedActionName { get; private set; } @@ -36,7 +33,6 @@ public static void HFSetup() { if (HugModInstance.ModHelper.Interaction.ModExists("Leadpogrommer.PeacefulGhosts")) return; - IsHuggableFrightsEnabled = HugModInstance.ModHelper.Storage.Load("settings.json"); HuggedActionName = EnumUtils.Create("Hugged"); WitnessedHugActionName = EnumUtils.Create("WitnessedHug"); ReturnActionName = EnumUtils.Create("Return"); @@ -57,11 +53,11 @@ public static void HFOwlSetup(HugComponent hugComponent) if (!setupComplete) return; var brain = hugComponent.gameObject.GetComponent(); - brain._actions = AddToArray(brain._actions, HuggedActionName, WitnessedHugActionName, ReturnActionName); + brain._actions = brain._actions.AddToArray(HuggedActionName, WitnessedHugActionName, ReturnActionName); brain._effects.OnGrabComplete += () => { hugComponent.SetHugEnabled(false); }; hugComponent.gameObject.AddComponent(); - hugComponent.HugReceiver._interactRange = owlReceiverRange; + hugComponent.HugReceiver.SetInteractRange(owlReceiverRange); hugComponent.OnHugStart += () => { brain.ChangeAction(HuggedActionName); }; hugComponent.OnHugFinish += () => { if (brain._currentAction.GetName() == HuggedActionName) brain._currentAction._enterTime = Time.time; }; @@ -70,7 +66,7 @@ public static void HFOwlSetup(HugComponent hugComponent) public static string HFEnabledMessage(bool wasChanged) { - return setupComplete ? $"{optionText} is" + (wasChanged ? " now: " : ": ") + (IsHuggableFrightsEnabled ? "Enabled" : "Disabled") : ""; + return setupComplete ? $"{optionText} is" + (wasChanged ? " now: " : ": ") + (Settings.FriendmakerModeEnabled ? "Enabled" : "Disabled") : ""; } @@ -87,21 +83,21 @@ private static void AddHuggableFrightsOption() GameObject.Destroy(settingsOptionObj.GetComponentInChildren()); var toggleElement = settingsOptionObj.GetComponent(); - toggleElement.Initialize(IsHuggableFrightsEnabled); + toggleElement.Initialize(Settings.FriendmakerModeEnabled); toggleElement.SetDisplayText(optionText); toggleElement.SetTooltipText(UITextType.None); toggleElement._overrideTooltipText = optionTooltipText; //make keyboard-selectable var menu = menuObj.GetComponentInChildren(); - menu._menuOptions = AddToArray(menu._menuOptions, toggleElement); + menu._menuOptions = menu._menuOptions.AddToArray(toggleElement); Menu.SetVerticalNavigation(menu, menu._menuOptions); //toggle var toggleButton = settingsOptionObj.GetComponent