chromeos: bluetooth: add BluetoothNodeClient
[chromium-blink-merge.git] / ash / wm / root_window_event_filter.cc
blobef7b43d2ce28cfb9ad439e668db57fe00ae042a2
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.
5 #include "ash/wm/root_window_event_filter.h"
7 #include "ash/shell.h"
8 #include "ash/wm/activation_controller.h"
9 #include "ash/wm/power_button_controller.h"
10 #include "ash/wm/window_util.h"
11 #include "ui/aura/event.h"
12 #include "ui/aura/focus_manager.h"
13 #include "ui/aura/root_window.h"
14 #include "ui/aura/window_delegate.h"
15 #include "ui/base/hit_test.h"
17 namespace ash {
18 namespace internal {
20 namespace {
22 // Returns the default cursor for a window component.
23 gfx::NativeCursor CursorForWindowComponent(int window_component) {
24 switch (window_component) {
25 case HTBOTTOM:
26 return aura::kCursorSouthResize;
27 case HTBOTTOMLEFT:
28 return aura::kCursorSouthWestResize;
29 case HTBOTTOMRIGHT:
30 return aura::kCursorSouthEastResize;
31 case HTLEFT:
32 return aura::kCursorWestResize;
33 case HTRIGHT:
34 return aura::kCursorEastResize;
35 case HTTOP:
36 return aura::kCursorNorthResize;
37 case HTTOPLEFT:
38 return aura::kCursorNorthWestResize;
39 case HTTOPRIGHT:
40 return aura::kCursorNorthEastResize;
41 default:
42 return aura::kCursorNull;
46 aura::Window* FindFocusableWindowFor(aura::Window* window) {
47 while (window && !window->CanFocus())
48 window = window->parent();
49 return window;
52 } // namespace
54 ////////////////////////////////////////////////////////////////////////////////
55 // RootWindowEventFilter, public:
57 RootWindowEventFilter::RootWindowEventFilter()
58 : cursor_lock_count_(0),
59 did_cursor_change_(false),
60 cursor_to_set_on_unlock_(0),
61 update_cursor_visibility_(true) {
64 RootWindowEventFilter::~RootWindowEventFilter() {
65 // Additional filters are not owned by RootWindowEventFilter and they
66 // should all be removed when running here. |filters_| has
67 // check_empty == true and will DCHECK failure if it is not empty.
70 void RootWindowEventFilter::LockCursor() {
71 cursor_lock_count_++;
74 void RootWindowEventFilter::UnlockCursor() {
75 cursor_lock_count_--;
76 DCHECK_GE(cursor_lock_count_, 0);
77 if (cursor_lock_count_ == 0) {
78 if (did_cursor_change_) {
79 did_cursor_change_ = false;
80 Shell::GetRootWindow()->SetCursor(cursor_to_set_on_unlock_);
82 did_cursor_change_ = false;
83 cursor_to_set_on_unlock_ = 0;
87 void RootWindowEventFilter::AddFilter(aura::EventFilter* filter) {
88 filters_.AddObserver(filter);
91 void RootWindowEventFilter::RemoveFilter(aura::EventFilter* filter) {
92 filters_.RemoveObserver(filter);
95 size_t RootWindowEventFilter::GetFilterCount() const {
96 return filters_.size();
99 ////////////////////////////////////////////////////////////////////////////////
100 // RootWindowEventFilter, EventFilter implementation:
102 bool RootWindowEventFilter::PreHandleKeyEvent(aura::Window* target,
103 aura::KeyEvent* event) {
104 return FilterKeyEvent(target, event);
107 bool RootWindowEventFilter::PreHandleMouseEvent(aura::Window* target,
108 aura::MouseEvent* event) {
109 // We must always update the cursor, otherwise the cursor can get stuck if an
110 // event filter registered with us consumes the event.
111 if (event->type() == ui::ET_MOUSE_MOVED) {
112 if (update_cursor_visibility_)
113 SetCursorVisible(target, event, true);
115 UpdateCursor(target, event);
118 if (FilterMouseEvent(target, event))
119 return true;
121 if (event->type() == ui::ET_MOUSE_PRESSED && GetActiveWindow() != target)
122 target->GetFocusManager()->SetFocusedWindow(FindFocusableWindowFor(target));
124 return false;
127 ui::TouchStatus RootWindowEventFilter::PreHandleTouchEvent(
128 aura::Window* target,
129 aura::TouchEvent* event) {
130 ui::TouchStatus status = FilterTouchEvent(target, event);
131 if (status != ui::TOUCH_STATUS_UNKNOWN)
132 return status;
134 if (event->type() == ui::ET_TOUCH_PRESSED) {
135 if (update_cursor_visibility_)
136 SetCursorVisible(target, event, false);
138 target->GetFocusManager()->SetFocusedWindow(FindFocusableWindowFor(target));
140 return ui::TOUCH_STATUS_UNKNOWN;
143 ui::GestureStatus RootWindowEventFilter::PreHandleGestureEvent(
144 aura::Window* target,
145 aura::GestureEvent* event) {
146 // TODO(sad):
147 return ui::GESTURE_STATUS_UNKNOWN;
150 ////////////////////////////////////////////////////////////////////////////////
151 // RootWindowEventFilter, private:
153 void RootWindowEventFilter::UpdateCursor(aura::Window* target,
154 aura::MouseEvent* event) {
155 gfx::NativeCursor cursor = target->GetCursor(event->location());
156 if (event->flags() & ui::EF_IS_NON_CLIENT) {
157 int window_component =
158 target->delegate()->GetNonClientComponent(event->location());
159 cursor = CursorForWindowComponent(window_component);
161 if (cursor_lock_count_ == 0) {
162 Shell::GetRootWindow()->SetCursor(cursor);
163 } else {
164 cursor_to_set_on_unlock_ = cursor;
165 did_cursor_change_ = true;
169 void RootWindowEventFilter::SetCursorVisible(aura::Window* target,
170 aura::LocatedEvent* event,
171 bool show) {
172 Shell::GetRootWindow()->ShowCursor(show);
175 bool RootWindowEventFilter::FilterKeyEvent(aura::Window* target,
176 aura::KeyEvent* event) {
177 bool handled = false;
178 if (filters_.might_have_observers()) {
179 ObserverListBase<aura::EventFilter>::Iterator it(filters_);
180 aura::EventFilter* filter;
181 while (!handled && (filter = it.GetNext()) != NULL)
182 handled = filter->PreHandleKeyEvent(target, event);
184 return handled;
187 bool RootWindowEventFilter::FilterMouseEvent(aura::Window* target,
188 aura::MouseEvent* event) {
189 bool handled = false;
190 if (filters_.might_have_observers()) {
191 ObserverListBase<aura::EventFilter>::Iterator it(filters_);
192 aura::EventFilter* filter;
193 while (!handled && (filter = it.GetNext()) != NULL)
194 handled = filter->PreHandleMouseEvent(target, event);
196 return handled;
199 ui::TouchStatus RootWindowEventFilter::FilterTouchEvent(
200 aura::Window* target,
201 aura::TouchEvent* event) {
202 ui::TouchStatus status = ui::TOUCH_STATUS_UNKNOWN;
203 if (filters_.might_have_observers()) {
204 ObserverListBase<aura::EventFilter>::Iterator it(filters_);
205 aura::EventFilter* filter;
206 while (status == ui::TOUCH_STATUS_UNKNOWN &&
207 (filter = it.GetNext()) != NULL) {
208 status = filter->PreHandleTouchEvent(target, event);
211 return status;
214 } // namespace internal
215 } // namespace ash