1// Copyright (c) 2012 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 5#include "ui/base/accelerators/accelerator_manager.h" 6 7#include "base/compiler_specific.h" 8#include "testing/gtest/include/gtest/gtest.h" 9#include "ui/events/event_constants.h" 10#include "ui/events/keycodes/keyboard_codes.h" 11 12namespace ui { 13namespace test { 14 15namespace { 16 17class TestTarget : public AcceleratorTarget { 18 public: 19 TestTarget() : accelerator_pressed_count_(0) {} 20 virtual ~TestTarget() {} 21 22 int accelerator_pressed_count() const { 23 return accelerator_pressed_count_; 24 } 25 26 void set_accelerator_pressed_count(int accelerator_pressed_count) { 27 accelerator_pressed_count_ = accelerator_pressed_count; 28 } 29 30 // Overridden from AcceleratorTarget: 31 virtual bool AcceleratorPressed(const Accelerator& accelerator) OVERRIDE; 32 virtual bool CanHandleAccelerators() const OVERRIDE; 33 34 private: 35 int accelerator_pressed_count_; 36 37 DISALLOW_COPY_AND_ASSIGN(TestTarget); 38}; 39 40bool TestTarget::AcceleratorPressed(const Accelerator& accelerator) { 41 ++accelerator_pressed_count_; 42 return true; 43} 44 45bool TestTarget::CanHandleAccelerators() const { 46 return true; 47} 48 49Accelerator GetAccelerator(KeyboardCode code, int mask) { 50 return Accelerator(code, mask); 51} 52 53} // namespace 54 55class AcceleratorManagerTest : public testing::Test { 56 public: 57 AcceleratorManagerTest() {} 58 virtual ~AcceleratorManagerTest() {} 59 60 AcceleratorManager manager_; 61}; 62 63TEST_F(AcceleratorManagerTest, Register) { 64 const Accelerator accelerator_a(VKEY_A, EF_NONE); 65 TestTarget target; 66 manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, 67 &target); 68 69 // The registered accelerator is processed. 70 EXPECT_TRUE(manager_.Process(accelerator_a)); 71 EXPECT_EQ(1, target.accelerator_pressed_count()); 72} 73 74TEST_F(AcceleratorManagerTest, RegisterMultipleTarget) { 75 const Accelerator accelerator_a(VKEY_A, EF_NONE); 76 TestTarget target1; 77 manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, 78 &target1); 79 TestTarget target2; 80 manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, 81 &target2); 82 83 // If multiple targets are registered with the same accelerator, the target 84 // registered later processes the accelerator. 85 EXPECT_TRUE(manager_.Process(accelerator_a)); 86 EXPECT_EQ(0, target1.accelerator_pressed_count()); 87 EXPECT_EQ(1, target2.accelerator_pressed_count()); 88} 89 90TEST_F(AcceleratorManagerTest, Unregister) { 91 const Accelerator accelerator_a(VKEY_A, EF_NONE); 92 TestTarget target; 93 manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, 94 &target); 95 const Accelerator accelerator_b(VKEY_B, EF_NONE); 96 manager_.Register(accelerator_b, AcceleratorManager::kNormalPriority, 97 &target); 98 99 // Unregistering a different accelerator does not affect the other 100 // accelerator. 101 manager_.Unregister(accelerator_b, &target); 102 EXPECT_TRUE(manager_.Process(accelerator_a)); 103 EXPECT_EQ(1, target.accelerator_pressed_count()); 104 105 // The unregistered accelerator is no longer processed. 106 target.set_accelerator_pressed_count(0); 107 manager_.Unregister(accelerator_a, &target); 108 EXPECT_FALSE(manager_.Process(accelerator_a)); 109 EXPECT_EQ(0, target.accelerator_pressed_count()); 110} 111 112TEST_F(AcceleratorManagerTest, UnregisterAll) { 113 const Accelerator accelerator_a(VKEY_A, EF_NONE); 114 TestTarget target1; 115 manager_.Register(accelerator_a, AcceleratorManager::kNormalPriority, 116 &target1); 117 const Accelerator accelerator_b(VKEY_B, EF_NONE); 118 manager_.Register(accelerator_b, AcceleratorManager::kNormalPriority, 119 &target1); 120 const Accelerator accelerator_c(VKEY_C, EF_NONE); 121 TestTarget target2; 122 manager_.Register(accelerator_c, AcceleratorManager::kNormalPriority, 123 &target2); 124 manager_.UnregisterAll(&target1); 125 126 // All the accelerators registered for |target1| are no longer processed. 127 EXPECT_FALSE(manager_.Process(accelerator_a)); 128 EXPECT_FALSE(manager_.Process(accelerator_b)); 129 EXPECT_EQ(0, target1.accelerator_pressed_count()); 130 131 // UnregisterAll with a different target does not affect the other target. 132 EXPECT_TRUE(manager_.Process(accelerator_c)); 133 EXPECT_EQ(1, target2.accelerator_pressed_count()); 134} 135 136TEST_F(AcceleratorManagerTest, Process) { 137 TestTarget target; 138 139 // Test all 2*2*2 cases (shift/control/alt = on/off). 140 for (int mask = 0; mask < 2 * 2 * 2; ++mask) { 141 Accelerator accelerator(GetAccelerator(VKEY_A, mask)); 142 const base::string16 text = accelerator.GetShortcutText(); 143 manager_.Register(accelerator, AcceleratorManager::kNormalPriority, 144 &target); 145 146 // The registered accelerator is processed. 147 const int last_count = target.accelerator_pressed_count(); 148 EXPECT_TRUE(manager_.Process(accelerator)) << text; 149 EXPECT_EQ(last_count + 1, target.accelerator_pressed_count()) << text; 150 151 // The non-registered accelerators are not processed. 152 accelerator.set_type(ET_UNKNOWN); 153 EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type 154 accelerator.set_type(ET_TRANSLATED_KEY_PRESS); 155 EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type 156 accelerator.set_type(ET_KEY_RELEASED); 157 EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type 158 accelerator.set_type(ET_TRANSLATED_KEY_RELEASE); 159 EXPECT_FALSE(manager_.Process(accelerator)) << text; // different type 160 161 EXPECT_FALSE(manager_.Process(GetAccelerator(VKEY_UNKNOWN, mask))) 162 << text; // different vkey 163 EXPECT_FALSE(manager_.Process(GetAccelerator(VKEY_B, mask))) 164 << text; // different vkey 165 EXPECT_FALSE(manager_.Process(GetAccelerator(VKEY_SHIFT, mask))) 166 << text; // different vkey 167 168 for (int test_mask = 0; test_mask < 2 * 2 * 2; ++test_mask) { 169 if (test_mask == mask) 170 continue; 171 const Accelerator test_accelerator(GetAccelerator(VKEY_A, test_mask)); 172 const base::string16 test_text = test_accelerator.GetShortcutText(); 173 EXPECT_FALSE(manager_.Process(test_accelerator)) 174 << text << ", " << test_text; // different modifiers 175 } 176 177 EXPECT_EQ(last_count + 1, target.accelerator_pressed_count()) << text; 178 manager_.UnregisterAll(&target); 179 } 180} 181 182} // namespace test 183} // namespace ui 184