| // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include "ui/base/accelerators/accelerator_manager.h" |
| |
| #include "base/compiler_specific.h" |
| #include "testing/gtest/include/gtest/gtest.h" |
| #include "ui/events/event_constants.h" |
| #include "ui/events/keycodes/keyboard_codes.h" |
| |
| namespace ui { |
| namespace test { |
| |
| namespace { |
| |
| class TestTarget : public AcceleratorTarget { |
| public: |
| TestTarget() : accelerator_pressed_count_(0) {} |
| virtual ~TestTarget() {} |
| |
| int accelerator_pressed_count() const { |
| return accelerator_pressed_count_; |
| } |
| |
| void set_accelerator_pressed_count(int accelerator_pressed_count) { |
| accelerator_pressed_count_ = accelerator_pressed_count; |
| } |
| |
| // Overridden from AcceleratorTarget: |
| virtual bool AcceleratorPressed(const Accelerator& accelerator) OVERRIDE; |
| virtual bool CanHandleAccelerators() const OVERRIDE; |
| |
| private: |
| int accelerator_pressed_count_; |
| |
| DISALLOW_COPY_AND_ASSIGN(TestTarget); |
| }; |
| |
| bool TestTarget::AcceleratorPressed(const Accelerator& accelerator) { |
| ++accelerator_pressed_count_; |
| return true; |
| } |
| |
| bool TestTarget::CanHandleAccelerators() const { |
| return true; |
| } |
| |
| Accelerator GetAccelerator(KeyboardCode code, int mask) { |
| return Accelerator(code, mask); |
| } |
| |
| } // namespace |
| |
| class AcceleratorManagerTest : public testing::Test { |
| public: |
| AcceleratorManagerTest() {} |
| virtual ~AcceleratorManagerTest() {} |
| |
| AcceleratorManager manager_; |
| }; |
| |
| TEST_F(AcceleratorManagerTest, Register) { |
| const Accelerator accelerator_a(VKEY_A, EF_NONE); |
| TestTarget target; |
| manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, |
| &target); |
| |
| // The registered accelerator is processed. |
| EXPECT_TRUE(manager_.Process(accelerator_a)); |
| EXPECT_EQ(1, target.accelerator_pressed_count()); |
| } |
| |
| TEST_F(AcceleratorManagerTest, RegisterMultipleTarget) { |
| const Accelerator accelerator_a(VKEY_A, EF_NONE); |
| TestTarget target1; |
| manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, |
| &target1); |
| TestTarget target2; |
| manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, |
| &target2); |
| |
| // If multiple targets are registered with the same accelerator, the target |
| // registered later processes the accelerator. |
| EXPECT_TRUE(manager_.Process(accelerator_a)); |
| EXPECT_EQ(0, target1.accelerator_pressed_count()); |
| EXPECT_EQ(1, target2.accelerator_pressed_count()); |
| } |
| |
| TEST_F(AcceleratorManagerTest, Unregister) { |
| const Accelerator accelerator_a(VKEY_A, EF_NONE); |
| TestTarget target; |
| manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, |
| &target); |
| const Accelerator accelerator_b(VKEY_B, EF_NONE); |
| manager_.Register(accelerator_b, AcceleratorManager::kNormalPriority, |
| &target); |
| |
| // Unregistering a different accelerator does not affect the other |
| // accelerator. |
| manager_.Unregister(accelerator_b, &target); |
| EXPECT_TRUE(manager_.Process(accelerator_a)); |
| EXPECT_EQ(1, target.accelerator_pressed_count()); |
| |
| // The unregistered accelerator is no longer processed. |
| target.set_accelerator_pressed_count(0); |
| manager_.Unregister(accelerator_a, &target); |
| EXPECT_FALSE(manager_.Process(accelerator_a)); |
| EXPECT_EQ(0, target.accelerator_pressed_count()); |
| } |
| |
| TEST_F(AcceleratorManagerTest, UnregisterAll) { |
| const Accelerator accelerator_a(VKEY_A, EF_NONE); |
| TestTarget target1; |
| manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, |
| &target1); |
| const Accelerator accelerator_b(VKEY_B, EF_NONE); |
| manager_.Register(accelerator_b, AcceleratorManager::kNormalPriority, |
| &target1); |
| const Accelerator accelerator_c(VKEY_C, EF_NONE); |
| TestTarget target2; |
| manager_.Register(accelerator_c, AcceleratorManager::kNormalPriority, |
| &target2); |
| manager_.UnregisterAll(&target1); |
| |
| // All the accelerators registered for |target1| are no longer processed. |
| EXPECT_FALSE(manager_.Process(accelerator_a)); |
| EXPECT_FALSE(manager_.Process(accelerator_b)); |
| EXPECT_EQ(0, target1.accelerator_pressed_count()); |
| |
| // UnregisterAll with a different target does not affect the other target. |
| EXPECT_TRUE(manager_.Process(accelerator_c)); |
| EXPECT_EQ(1, target2.accelerator_pressed_count()); |
| } |
| |
| TEST_F(AcceleratorManagerTest, Process) { |
| TestTarget target; |
| |
| // Test all 2*2*2 cases (shift/control/alt = on/off). |
| for (int mask = 0; mask < 2 * 2 * 2; ++mask) { |
| Accelerator accelerator(GetAccelerator(VKEY_A, mask)); |
| const base::string16 text = accelerator.GetShortcutText(); |
| manager_.Register(accelerator, AcceleratorManager::kNormalPriority, |
| &target); |
| |
| // The registered accelerator is processed. |
| const int last_count = target.accelerator_pressed_count(); |
| EXPECT_TRUE(manager_.Process(accelerator)) << text; |
| EXPECT_EQ(last_count + 1, target.accelerator_pressed_count()) << text; |
| |
| // The non-registered accelerators are not processed. |
| accelerator.set_type(ET_UNKNOWN); |
| EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type |
| accelerator.set_type(ET_TRANSLATED_KEY_PRESS); |
| EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type |
| accelerator.set_type(ET_KEY_RELEASED); |
| EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type |
| accelerator.set_type(ET_TRANSLATED_KEY_RELEASE); |
| EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type |
| |
| EXPECT_FALSE(manager_.Process(GetAccelerator(VKEY_UNKNOWN, mask))) |
| << text; // different vkey |
| EXPECT_FALSE(manager_.Process(GetAccelerator(VKEY_B, mask))) |
| << text; // different vkey |
| EXPECT_FALSE(manager_.Process(GetAccelerator(VKEY_SHIFT, mask))) |
| << text; // different vkey |
| |
| for (int test_mask = 0; test_mask < 2 * 2 * 2; ++test_mask) { |
| if (test_mask == mask) |
| continue; |
| const Accelerator test_accelerator(GetAccelerator(VKEY_A, test_mask)); |
| const base::string16 test_text = test_accelerator.GetShortcutText(); |
| EXPECT_FALSE(manager_.Process(test_accelerator)) |
| << text << ", " << test_text; // different modifiers |
| } |
| |
| EXPECT_EQ(last_count + 1, target.accelerator_pressed_count()) << text; |
| manager_.UnregisterAll(&target); |
| } |
| } |
| |
| } // namespace test |
| } // namespace ui |