Ви не можете вибрати більше 25 тем Теми мають розпочинатися з літери або цифри, можуть містити дефіси (-) і не повинні перевищувати 35 символів.

146 рядки
4.9 KiB

  1. // This code is distributed under MIT license.
  2. // Copyright (c) 2010-2018 George Mamaladze
  3. // See license.txt or https://mit-license.org/
  4. using System;
  5. using System.Collections.Generic;
  6. using System.Linq;
  7. using System.Windows.Forms;
  8. using Gma.System.MouseKeyHook.Implementation;
  9. namespace Gma.System.MouseKeyHook
  10. {
  11. /// <summary>
  12. /// Used to represent a key combination as frequently used in application as shortcuts.
  13. /// e.g. Alt+Shift+R. This combination is triggered when 'R' is pressed after 'Alt' and 'Shift' are already down.
  14. /// </summary>
  15. public class Combination
  16. {
  17. private readonly Chord _chord;
  18. private Combination(Keys triggerKey, IEnumerable<Keys> chordKeys)
  19. : this(triggerKey, new Chord(chordKeys))
  20. {
  21. }
  22. private Combination(Keys triggerKey, Chord chord)
  23. {
  24. TriggerKey = triggerKey.Normalize();
  25. _chord = chord;
  26. }
  27. /// <summary>
  28. /// Last key which triggers the combination.
  29. /// </summary>
  30. public Keys TriggerKey { get; }
  31. /// <summary>
  32. /// Keys which all must be alredy down when trigger key is pressed.
  33. /// </summary>
  34. public IEnumerable<Keys> Chord
  35. {
  36. get { return _chord; }
  37. }
  38. /// <summary>
  39. /// Number of chord (modifier) keys which must be already down when the trigger key is pressed.
  40. /// </summary>
  41. public int ChordLength
  42. {
  43. get { return _chord.Count; }
  44. }
  45. /// <summary>
  46. /// A chainable builder method to simplify chord creation. Used along with <see cref="TriggeredBy" />,
  47. /// <see cref="With" />, <see cref="Control" />, <see cref="Shift" />, <see cref="Alt" />.
  48. /// </summary>
  49. /// <param name="key"></param>
  50. public static Combination TriggeredBy(Keys key)
  51. {
  52. return new Combination(key, (IEnumerable<Keys>) new Chord(Enumerable.Empty<Keys>()));
  53. }
  54. /// <summary>
  55. /// A chainable builder method to simplify chord creation. Used along with <see cref="TriggeredBy" />,
  56. /// <see cref="With" />, <see cref="Control" />, <see cref="Shift" />, <see cref="Alt" />.
  57. /// </summary>
  58. /// <param name="key"></param>
  59. public Combination With(Keys key)
  60. {
  61. return new Combination(TriggerKey, Chord.Concat(Enumerable.Repeat(key, 1)));
  62. }
  63. /// <summary>
  64. /// A chainable builder method to simplify chord creation. Used along with <see cref="TriggeredBy" />,
  65. /// <see cref="With" />, <see cref="Control" />, <see cref="Shift" />, <see cref="Alt" />.
  66. /// </summary>
  67. public Combination Control()
  68. {
  69. return With(Keys.Control);
  70. }
  71. /// <summary>
  72. /// A chainable builder method to simplify chord creation. Used along with <see cref="TriggeredBy" />,
  73. /// <see cref="With" />, <see cref="Control" />, <see cref="Shift" />, <see cref="Alt" />.
  74. /// </summary>
  75. public Combination Alt()
  76. {
  77. return With(Keys.Alt);
  78. }
  79. /// <summary>
  80. /// A chainable builder method to simplify chord creation. Used along with <see cref="TriggeredBy" />,
  81. /// <see cref="With" />, <see cref="Control" />, <see cref="Shift" />, <see cref="Alt" />.
  82. /// </summary>
  83. public Combination Shift()
  84. {
  85. return With(Keys.Shift);
  86. }
  87. /// <inheritdoc />
  88. public override string ToString()
  89. {
  90. return string.Join("+", Chord.Concat(Enumerable.Repeat(TriggerKey, 1)));
  91. }
  92. /// <summary>
  93. /// TriggeredBy a chord from any string like this 'Alt+Shift+R'.
  94. /// Nothe that the trigger key must be the last one.
  95. /// </summary>
  96. public static Combination FromString(string trigger)
  97. {
  98. var parts = trigger
  99. .Split('+')
  100. .Select(p => Enum.Parse(typeof(Keys), p))
  101. .Cast<Keys>();
  102. var stack = new Stack<Keys>(parts);
  103. var triggerKey = stack.Pop();
  104. return new Combination(triggerKey, stack);
  105. }
  106. /// <inheritdoc />
  107. protected bool Equals(Combination other)
  108. {
  109. return
  110. TriggerKey == other.TriggerKey
  111. && Chord.Equals(other.Chord);
  112. }
  113. /// <inheritdoc />
  114. public override bool Equals(object obj)
  115. {
  116. if (ReferenceEquals(null, obj)) return false;
  117. if (ReferenceEquals(this, obj)) return true;
  118. if (obj.GetType() != GetType()) return false;
  119. return Equals((Combination) obj);
  120. }
  121. /// <inheritdoc />
  122. public override int GetHashCode()
  123. {
  124. return Chord.GetHashCode() ^
  125. (int) TriggerKey;
  126. }
  127. }
  128. }