Skip to content

Commit

Permalink
Ask user for confirmation before rebinding key mapping (fix #683)
Browse files Browse the repository at this point in the history
  • Loading branch information
falko17 committed Nov 16, 2024
1 parent 1865e76 commit a1bcdd8
Show file tree
Hide file tree
Showing 2 changed files with 57 additions and 33 deletions.
14 changes: 11 additions & 3 deletions Assets/SEE/Controls/KeyActions/KeyMap.cs
Original file line number Diff line number Diff line change
Expand Up @@ -134,8 +134,8 @@ internal void ResetKeyCode(KeyActionDescriptor descriptor, KeyCode keyCode)
{
if (TryGetKeyAction(keyCode, out KeyAction action))
{
throw new($"Cannot register key {keyCode} for {descriptor.Name}."
+ $" Key {keyCode} is already bound to {action}.\n");
throw new KeyBindingsExistsException($"Cannot register key {keyCode} for {descriptor.Name}."
+ $" Key {keyCode} is already bound to {action}.\n");
}
else
{
Expand Down Expand Up @@ -351,5 +351,13 @@ IEnumerator IEnumerable.GetEnumerator()
}
}
#endregion

/// <summary>
/// An exception indicating that the attempted rebind would result in a duplicate key binding.
/// </summary>
public class KeyBindingsExistsException : Exception
{
public KeyBindingsExistsException(string message) : base(message) { }
};
}
}
}
76 changes: 46 additions & 30 deletions Assets/SEE/UI/SettingsMenu.cs
Original file line number Diff line number Diff line change
@@ -1,13 +1,17 @@
using UnityEngine.UI;
using UnityEngine;
using TMPro;
using SEE.Controls;
using SEE.Utils;
using SEE.GO;
using System;
using System.Collections.Generic;
using SEE.UI.Notification;
using System.Linq;
using Cysharp.Threading.Tasks;
using SEE.Controls;
using SEE.Controls.KeyActions;
using SEE.GO;
using SEE.UI.Menu;
using SEE.UI.Notification;
using SEE.Utils;
using TMPro;
using UnityEditor;
using UnityEngine;
using UnityEngine.UI;

namespace SEE.UI
{
Expand All @@ -19,17 +23,17 @@ public class SettingsMenu : PlatformDependentComponent
/// <summary>
/// Prefab for the <see cref="SettingsMenu"/>.
/// </summary>
private string SettingsPrefab => UIPrefabFolder + "SettingsMenu";
private static string SettingsPrefab => UIPrefabFolder + "SettingsMenu";

/// <summary>
/// Prefab for the KeyBindingContent.
/// </summary>
private string KeyBindingContent => UIPrefabFolder + "KeyBindingContent";
private static string KeyBindingContent => UIPrefabFolder + "KeyBindingContent";

/// <summary>
/// Prefab for the ScrollView.
/// </summary>
private string ScrollPrefab => UIPrefabFolder + "ScrollPrefab";
private static string ScrollPrefab => UIPrefabFolder + "ScrollPrefab";

/// <summary>
/// The game object instantiated for the <see cref="SettingsPrefab"/>.
Expand Down Expand Up @@ -99,26 +103,11 @@ protected override void UpdateDesktop()
// the next button that gets pressed will be the new keyBind.
if (Input.anyKeyDown)
{
foreach (KeyCode key in Enum.GetValues(typeof(KeyCode)))
KeyCode newKey = Enum.GetValues(typeof(KeyCode)).Cast<KeyCode>()
.FirstOrDefault(key => Input.GetKeyDown(key) && KeyBindings.AssignableKeyCode(key));
if (newKey != KeyCode.None)
{
if (Input.GetKeyDown(key) && KeyBindings.AssignableKeyCode(key))
{
try
{
KeyBindings.SetBindingForKey(bindingToRebind, key);
// TODO (#683): We need to open a modal dialog and ask the user
// whether he/she really wants to change the binding.
shortNameOfBindingToLabel[bindingToRebind.Name].text = key.ToString();
}
catch (Exception ex)
{
ShowNotification.Error("Key code already bound", ex.Message);
}

bindingToRebind = null;
SEEInput.KeyboardShortcutsEnabled = true;
break;
}
ReassignKeyAsync(bindingToRebind, newKey).Forget();
}
}
}
Expand All @@ -139,6 +128,33 @@ protected override void UpdateDesktop()
}
}

/// <summary>
/// Reassigns the binding of the given <paramref name="descriptor"/> to the new key <paramref name="newKey"/>
/// after confirming the action with the user.
/// </summary>
/// <param name="descriptor">The key binding to reassign.</param>
/// <param name="newKey">The new key code to assign to the key binding.</param>
private async UniTaskVoid ReassignKeyAsync(KeyActionDescriptor descriptor, KeyCode newKey)
{
string question = $"Do you really want to reassign action \"{descriptor.Name}\" to key {newKey}?";
if (!await ConfirmDialog.ConfirmAsync(new(question, title: "Change Key?")))
{
return;
}
try
{
KeyBindings.SetBindingForKey(descriptor, newKey);
shortNameOfBindingToLabel[descriptor.Name].text = newKey.ToString();
}
catch (KeyMap.KeyBindingsExistsException ex)
{
ShowNotification.Error("Key code already bound", ex.Message, log: false);
}

bindingToRebind = null;
SEEInput.KeyboardShortcutsEnabled = true;
}

/// <summary>
/// The keyBinding which gets updated.
/// </summary>
Expand All @@ -159,7 +175,7 @@ private void StartRebindFor(KeyActionDescriptor binding)
private static void ExitGame()
{
#if UNITY_EDITOR
UnityEditor.EditorApplication.isPlaying = false;
EditorApplication.isPlaying = false;
#else
Application.Quit();
#endif
Expand Down

0 comments on commit a1bcdd8

Please sign in to comment.