keyboard.h 5.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. // Copyright 2015 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef COMPONENTS_EXO_KEYBOARD_H_
  5. #define COMPONENTS_EXO_KEYBOARD_H_
  6. #include <memory>
  7. #include "ash/ime/ime_controller_impl.h"
  8. #include "ash/public/cpp/keyboard/keyboard_controller_observer.h"
  9. #include "base/containers/flat_map.h"
  10. #include "base/observer_list.h"
  11. #include "base/time/time.h"
  12. #include "components/exo/key_state.h"
  13. #include "components/exo/keyboard_observer.h"
  14. #include "components/exo/seat_observer.h"
  15. #include "components/exo/surface_observer.h"
  16. #include "ui/events/event.h"
  17. #include "ui/events/event_handler.h"
  18. namespace ui {
  19. enum class DomCode;
  20. class KeyEvent;
  21. }
  22. namespace exo {
  23. class KeyboardDelegate;
  24. class KeyboardDeviceConfigurationDelegate;
  25. class Seat;
  26. class Surface;
  27. // This class implements a client keyboard that represents one or more keyboard
  28. // devices.
  29. class Keyboard : public ui::EventHandler,
  30. public SurfaceObserver,
  31. public SeatObserver,
  32. public ash::KeyboardControllerObserver,
  33. public ash::ImeControllerImpl::Observer {
  34. public:
  35. Keyboard(std::unique_ptr<KeyboardDelegate> delegate, Seat* seat);
  36. Keyboard(const Keyboard&) = delete;
  37. Keyboard& operator=(const Keyboard&) = delete;
  38. ~Keyboard() override;
  39. KeyboardDelegate* delegate() const { return delegate_.get(); }
  40. bool HasDeviceConfigurationDelegate() const;
  41. void SetDeviceConfigurationDelegate(
  42. KeyboardDeviceConfigurationDelegate* delegate);
  43. // Management of the observer list.
  44. void AddObserver(KeyboardObserver* observer);
  45. bool HasObserver(KeyboardObserver* observer) const;
  46. void RemoveObserver(KeyboardObserver* observer);
  47. void SetNeedKeyboardKeyAcks(bool need_acks);
  48. bool AreKeyboardKeyAcksNeeded() const;
  49. void AckKeyboardKey(uint32_t serial, bool handled);
  50. // Overridden from ui::EventHandler:
  51. void OnKeyEvent(ui::KeyEvent* event) override;
  52. // Overridden from SurfaceObserver:
  53. void OnSurfaceDestroying(Surface* surface) override;
  54. // Overridden from SeatObserver:
  55. void OnSurfaceFocused(Surface* gained_focus,
  56. Surface* lost_focus,
  57. bool has_focused_surface) override;
  58. void OnKeyboardModifierUpdated() override;
  59. // Overridden from ash::KeyboardControllerObserver:
  60. void OnKeyboardEnableFlagsChanged(
  61. const std::set<keyboard::KeyboardEnableFlag>& flags) override;
  62. void OnKeyRepeatSettingsChanged(
  63. const ash::KeyRepeatSettings& settings) override;
  64. // Overridden from ash::ImeControllerImpl::Observer:
  65. void OnCapsLockChanged(bool enabled) override;
  66. void OnKeyboardLayoutNameChanged(const std::string& layout_name) override;
  67. Surface* focused_surface_for_testing() const { return focus_; }
  68. private:
  69. // Change keyboard focus to |surface|.
  70. void SetFocus(Surface* surface);
  71. // Processes expired key state changes in |pending_key_acks_| as they have not
  72. // been acknowledged.
  73. void ProcessExpiredPendingKeyAcks();
  74. // Schedule next call of ProcessExpiredPendingKeyAcks after |delay|
  75. void ScheduleProcessExpiredPendingKeyAcks(base::TimeDelta delay);
  76. // Adds/Removes pre or post event handler depending on if key acks are needed.
  77. // If key acks are needed, pre target handler will be added because this class
  78. // wants to dispatch keys before they are consumed by Chrome. Otherwise, post
  79. // target handler will be added because all accelerators should be handled by
  80. // Chrome before they are dispatched by this class.
  81. void AddEventHandler();
  82. void RemoveEventHandler();
  83. // Notify the current keyboard type.
  84. void UpdateKeyboardType();
  85. // The delegate instance that all events except for events about device
  86. // configuration are dispatched to.
  87. std::unique_ptr<KeyboardDelegate> delegate_;
  88. // Seat that the Keyboard recieves focus events from.
  89. Seat* const seat_;
  90. // The delegate instance that events about device configuration are dispatched
  91. // to.
  92. KeyboardDeviceConfigurationDelegate* device_configuration_delegate_ = nullptr;
  93. // Indicates that each key event is expected to be acknowledged.
  94. bool are_keyboard_key_acks_needed_ = false;
  95. // The current focus surface for the keyboard.
  96. Surface* focus_ = nullptr;
  97. // Set of currently pressed keys. First value is a platform code and second
  98. // value is the code that was delivered to client. See Seat.h for more
  99. // details.
  100. base::flat_map<ui::DomCode, KeyState> pressed_keys_;
  101. // Key state changes that are expected to be acknowledged.
  102. using KeyStateChange = std::pair<ui::KeyEvent, base::TimeTicks>;
  103. base::flat_map<uint32_t, KeyStateChange> pending_key_acks_;
  104. // Indicates that a ProcessExpiredPendingKeyAcks call is pending.
  105. bool process_expired_pending_key_acks_pending_ = false;
  106. // Delay until a key state change expected to be acknowledged is expired.
  107. const base::TimeDelta expiration_delay_for_pending_key_acks_;
  108. // True when the ARC app window is focused.
  109. // TODO(yhanada, https://crbug.com/847500): Remove this when we find a way to
  110. // fix https://crbug.com/847500 without breaking ARC++ apps.
  111. bool focused_on_ime_supported_surface_ = false;
  112. base::ObserverList<KeyboardObserver>::Unchecked observer_list_;
  113. base::WeakPtrFactory<Keyboard> weak_ptr_factory_{this};
  114. };
  115. } // namespace exo
  116. #endif // COMPONENTS_EXO_KEYBOARD_H_