| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "remoting/host/local_input_monitor.h" | 5 #include "remoting/host/local_input_monitor.h" |
| 6 | 6 |
| 7 #import <AppKit/AppKit.h> | 7 #import <AppKit/AppKit.h> |
| 8 #include <set> | 8 #include <set> |
| 9 | 9 |
| 10 #include "base/bind.h" | 10 #include "base/bind.h" |
| 11 #include "base/compiler_specific.h" | 11 #include "base/compiler_specific.h" |
| 12 #include "base/location.h" | 12 #include "base/location.h" |
| 13 #include "base/logging.h" | 13 #include "base/logging.h" |
| 14 #include "base/mac/scoped_cftyperef.h" | 14 #include "base/mac/scoped_cftyperef.h" |
| 15 #include "base/memory/ref_counted.h" | 15 #include "base/memory/ref_counted.h" |
| 16 #include "base/single_thread_task_runner.h" | 16 #include "base/single_thread_task_runner.h" |
| 17 #include "base/synchronization/lock.h" | 17 #include "base/synchronization/lock.h" |
| 18 #include "remoting/host/mouse_move_observer.h" | 18 #include "base/threading/non_thread_safe.h" |
| 19 #include "third_party/skia/include/core/SkPoint.h" | 19 #include "third_party/skia/include/core/SkPoint.h" |
| 20 #import "third_party/GTM/AppKit/GTMCarbonEvent.h" | 20 #import "third_party/GTM/AppKit/GTMCarbonEvent.h" |
| 21 | 21 |
| 22 // Esc Key Code is 53. | 22 // Esc Key Code is 53. |
| 23 // http://boredzo.org/blog/wp-content/uploads/2007/05/IMTx-virtual-keycodes.pdf | 23 // http://boredzo.org/blog/wp-content/uploads/2007/05/IMTx-virtual-keycodes.pdf |
| 24 static const NSUInteger kEscKeyCode = 53; | 24 static const NSUInteger kEscKeyCode = 53; |
| 25 | 25 |
| 26 namespace remoting { | 26 namespace remoting { |
| 27 namespace { | 27 namespace { |
| 28 | 28 |
| 29 class LocalInputMonitorMac : public LocalInputMonitor { | 29 class LocalInputMonitorMac : public base::NonThreadSafe, |
| 30 public LocalInputMonitor { |
| 30 public: | 31 public: |
| 31 // Invoked by LocalInputMonitorManager. | 32 // Invoked by LocalInputMonitorManager. |
| 32 class EventHandler { | 33 class EventHandler { |
| 33 public: | 34 public: |
| 34 virtual ~EventHandler() {} | 35 virtual ~EventHandler() {} |
| 35 | 36 |
| 36 virtual void OnLocalMouseMoved(const SkIPoint& position) = 0; | 37 virtual void OnLocalMouseMoved(const SkIPoint& position) = 0; |
| 37 virtual void OnDisconnectShortcut() = 0; | 38 virtual void OnDisconnectShortcut() = 0; |
| 38 }; | 39 }; |
| 39 | 40 |
| 40 LocalInputMonitorMac( | 41 LocalInputMonitorMac( |
| 41 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, | 42 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, |
| 42 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner); | 43 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner, |
| 44 SessionController::Delegate* delegate); |
| 43 virtual ~LocalInputMonitorMac(); | 45 virtual ~LocalInputMonitorMac(); |
| 44 | 46 |
| 45 virtual void Start(MouseMoveObserver* mouse_move_observer, | |
| 46 const base::Closure& disconnect_callback) OVERRIDE; | |
| 47 virtual void Stop() OVERRIDE; | |
| 48 | |
| 49 private: | 47 private: |
| 50 // The actual implementation resides in LocalInputMonitorMac::Core class. | 48 // The actual implementation resides in LocalInputMonitorMac::Core class. |
| 51 class Core; | 49 class Core; |
| 52 scoped_refptr<Core> core_; | 50 scoped_refptr<Core> core_; |
| 53 | 51 |
| 54 DISALLOW_COPY_AND_ASSIGN(LocalInputMonitorMac); | 52 DISALLOW_COPY_AND_ASSIGN(LocalInputMonitorMac); |
| 55 }; | 53 }; |
| 56 | 54 |
| 57 } // namespace | 55 } // namespace |
| 58 } // namespace remoting | 56 } // namespace remoting |
| (...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 154 @end | 152 @end |
| 155 | 153 |
| 156 namespace remoting { | 154 namespace remoting { |
| 157 namespace { | 155 namespace { |
| 158 | 156 |
| 159 class LocalInputMonitorMac::Core | 157 class LocalInputMonitorMac::Core |
| 160 : public base::RefCountedThreadSafe<Core>, | 158 : public base::RefCountedThreadSafe<Core>, |
| 161 public EventHandler { | 159 public EventHandler { |
| 162 public: | 160 public: |
| 163 Core(scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, | 161 Core(scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, |
| 164 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner); | 162 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner, |
| 163 SessionController::Delegate* delegate); |
| 165 | 164 |
| 166 void Start(MouseMoveObserver* mouse_move_observer, | 165 void Start(); |
| 167 const base::Closure& disconnect_callback); | |
| 168 void Stop(); | 166 void Stop(); |
| 169 | 167 |
| 170 private: | 168 private: |
| 171 friend class base::RefCountedThreadSafe<Core>; | 169 friend class base::RefCountedThreadSafe<Core>; |
| 172 virtual ~Core(); | 170 virtual ~Core(); |
| 173 | 171 |
| 174 void StartOnUiThread(); | 172 void StartOnUiThread(); |
| 175 void StopOnUiThread(); | 173 void StopOnUiThread(); |
| 176 | 174 |
| 177 // EventHandler interface. | 175 // EventHandler interface. |
| 178 virtual void OnLocalMouseMoved(const SkIPoint& position) OVERRIDE; | 176 virtual void OnLocalMouseMoved(const SkIPoint& position) OVERRIDE; |
| 179 virtual void OnDisconnectShortcut() OVERRIDE; | 177 virtual void OnDisconnectShortcut() OVERRIDE; |
| 180 | 178 |
| 181 // Task runner on which public methods of this class must be called. | 179 // Task runner on which public methods of this class must be called. |
| 182 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner_; | 180 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner_; |
| 183 | 181 |
| 184 // Task runner on which |window_| is created. | 182 // Task runner on which |window_| is created. |
| 185 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner_; | 183 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner_; |
| 186 | 184 |
| 187 LocalInputMonitorManager* manager_; | 185 LocalInputMonitorManager* manager_; |
| 188 | 186 |
| 189 // Invoked in the |caller_task_runner_| thread to report local mouse events. | 187 // Invoked in the |caller_task_runner_| thread to report local mouse events |
| 190 MouseMoveObserver* mouse_move_observer_; | 188 // and session disconnect requests. |
| 191 | 189 SessionController::Delegate* delegate_; |
| 192 // Posted to the |caller_task_runner_| thread every time the disconnect key | |
| 193 // combination is pressed. | |
| 194 base::Closure disconnect_callback_; | |
| 195 | 190 |
| 196 DISALLOW_COPY_AND_ASSIGN(Core); | 191 DISALLOW_COPY_AND_ASSIGN(Core); |
| 197 }; | 192 }; |
| 198 | 193 |
| 199 LocalInputMonitorMac::LocalInputMonitorMac( | 194 LocalInputMonitorMac::LocalInputMonitorMac( |
| 200 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, | 195 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, |
| 201 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner) | 196 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner, |
| 202 : core_(new Core(caller_task_runner, ui_task_runner)) { | 197 SessionController::Delegate* delegate) |
| 198 : core_(new Core(caller_task_runner, ui_task_runner, delegate)) { |
| 199 core_->Start(); |
| 203 } | 200 } |
| 204 | 201 |
| 205 LocalInputMonitorMac::~LocalInputMonitorMac() { | 202 LocalInputMonitorMac::~LocalInputMonitorMac() { |
| 206 } | |
| 207 | |
| 208 void LocalInputMonitorMac::Start(MouseMoveObserver* mouse_move_observer, | |
| 209 const base::Closure& disconnect_callback) { | |
| 210 core_->Start(mouse_move_observer, disconnect_callback); | |
| 211 } | |
| 212 | |
| 213 void LocalInputMonitorMac::Stop() { | |
| 214 core_->Stop(); | 203 core_->Stop(); |
| 215 } | 204 } |
| 216 | 205 |
| 217 LocalInputMonitorMac::Core::Core( | 206 LocalInputMonitorMac::Core::Core( |
| 218 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, | 207 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, |
| 219 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner) | 208 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner, |
| 209 SessionController::Delegate* delegate) |
| 220 : caller_task_runner_(caller_task_runner), | 210 : caller_task_runner_(caller_task_runner), |
| 221 ui_task_runner_(ui_task_runner), | 211 ui_task_runner_(ui_task_runner), |
| 222 manager_(nil), | 212 manager_(nil), |
| 223 mouse_move_observer_(NULL) { | 213 delegate_(delegate) { |
| 214 DCHECK(delegate_); |
| 224 } | 215 } |
| 225 | 216 |
| 226 void LocalInputMonitorMac::Core::Start( | 217 void LocalInputMonitorMac::Core::Start() { |
| 227 MouseMoveObserver* mouse_move_observer, | |
| 228 const base::Closure& disconnect_callback) { | |
| 229 DCHECK(caller_task_runner_->BelongsToCurrentThread()); | 218 DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
| 230 DCHECK(disconnect_callback_.is_null()); | |
| 231 DCHECK(!disconnect_callback.is_null()); | |
| 232 DCHECK(!mouse_move_observer_); | |
| 233 DCHECK(mouse_move_observer); | |
| 234 | 219 |
| 235 disconnect_callback_ = disconnect_callback; | |
| 236 mouse_move_observer_ = mouse_move_observer; | |
| 237 ui_task_runner_->PostTask(FROM_HERE, | 220 ui_task_runner_->PostTask(FROM_HERE, |
| 238 base::Bind(&Core::StartOnUiThread, this)); | 221 base::Bind(&Core::StartOnUiThread, this)); |
| 239 } | 222 } |
| 240 | 223 |
| 241 void LocalInputMonitorMac::Core::Stop() { | 224 void LocalInputMonitorMac::Core::Stop() { |
| 242 DCHECK(caller_task_runner_->BelongsToCurrentThread()); | 225 DCHECK(caller_task_runner_->BelongsToCurrentThread()); |
| 243 | 226 |
| 244 mouse_move_observer_ = NULL; | 227 delegate_ = NULL; |
| 245 disconnect_callback_.Reset(); | |
| 246 ui_task_runner_->PostTask(FROM_HERE, base::Bind(&Core::StopOnUiThread, this)); | 228 ui_task_runner_->PostTask(FROM_HERE, base::Bind(&Core::StopOnUiThread, this)); |
| 247 } | 229 } |
| 248 | 230 |
| 249 LocalInputMonitorMac::Core::~Core() { | 231 LocalInputMonitorMac::Core::~Core() { |
| 250 DCHECK(manager_ == nil); | 232 DCHECK(manager_ == nil); |
| 251 DCHECK(disconnect_callback_.is_null()); | 233 DCHECK(!delegate_); |
| 252 DCHECK(!mouse_move_observer_); | |
| 253 } | 234 } |
| 254 | 235 |
| 255 void LocalInputMonitorMac::Core::StartOnUiThread() { | 236 void LocalInputMonitorMac::Core::StartOnUiThread() { |
| 256 DCHECK(ui_task_runner_->BelongsToCurrentThread()); | 237 DCHECK(ui_task_runner_->BelongsToCurrentThread()); |
| 257 | 238 |
| 258 manager_ = [[LocalInputMonitorManager alloc] initWithMonitor:this]; | 239 manager_ = [[LocalInputMonitorManager alloc] initWithMonitor:this]; |
| 259 } | 240 } |
| 260 | 241 |
| 261 void LocalInputMonitorMac::Core::StopOnUiThread() { | 242 void LocalInputMonitorMac::Core::StopOnUiThread() { |
| 262 DCHECK(ui_task_runner_->BelongsToCurrentThread()); | 243 DCHECK(ui_task_runner_->BelongsToCurrentThread()); |
| 263 | 244 |
| 264 [manager_ invalidate]; | 245 [manager_ invalidate]; |
| 265 [manager_ release]; | 246 [manager_ release]; |
| 266 manager_ = nil; | 247 manager_ = nil; |
| 267 } | 248 } |
| 268 | 249 |
| 269 void LocalInputMonitorMac::Core::OnLocalMouseMoved(const SkIPoint& position) { | 250 void LocalInputMonitorMac::Core::OnLocalMouseMoved(const SkIPoint& position) { |
| 270 if (!caller_task_runner_->BelongsToCurrentThread()) { | 251 if (!caller_task_runner_->BelongsToCurrentThread()) { |
| 271 caller_task_runner_->PostTask( | 252 caller_task_runner_->PostTask( |
| 272 FROM_HERE, base::Bind(&Core::OnLocalMouseMoved, this, position)); | 253 FROM_HERE, base::Bind(&Core::OnLocalMouseMoved, this, position)); |
| 273 return; | 254 return; |
| 274 } | 255 } |
| 275 | 256 |
| 276 if (mouse_move_observer_) | 257 if (delegate_) |
| 277 mouse_move_observer_->OnLocalMouseMoved(position); | 258 delegate_->OnLocalMouseMoved(position); |
| 278 } | 259 } |
| 279 | 260 |
| 280 void LocalInputMonitorMac::Core::OnDisconnectShortcut() { | 261 void LocalInputMonitorMac::Core::OnDisconnectShortcut() { |
| 281 if (!caller_task_runner_->BelongsToCurrentThread()) { | 262 if (!caller_task_runner_->BelongsToCurrentThread()) { |
| 282 caller_task_runner_->PostTask( | 263 caller_task_runner_->PostTask( |
| 283 FROM_HERE, base::Bind(&Core::OnDisconnectShortcut, this)); | 264 FROM_HERE, base::Bind(&Core::OnDisconnectShortcut, this)); |
| 284 return; | 265 return; |
| 285 } | 266 } |
| 286 | 267 |
| 287 if (!disconnect_callback_.is_null()) | 268 if (delegate_) |
| 288 disconnect_callback_.Run(); | 269 delegate_->DisconnectSession(); |
| 289 } | 270 } |
| 290 | 271 |
| 291 } // namespace | 272 } // namespace |
| 292 | 273 |
| 293 scoped_ptr<LocalInputMonitor> LocalInputMonitor::Create( | 274 scoped_ptr<LocalInputMonitor> LocalInputMonitor::Create( |
| 294 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, | 275 scoped_refptr<base::SingleThreadTaskRunner> caller_task_runner, |
| 295 scoped_refptr<base::SingleThreadTaskRunner> input_task_runner, | 276 scoped_refptr<base::SingleThreadTaskRunner> input_task_runner, |
| 296 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner) { | 277 scoped_refptr<base::SingleThreadTaskRunner> ui_task_runner, |
| 278 SessionController::Delegate* delegate) { |
| 297 return scoped_ptr<LocalInputMonitor>( | 279 return scoped_ptr<LocalInputMonitor>( |
| 298 new LocalInputMonitorMac(caller_task_runner, ui_task_runner)); | 280 new LocalInputMonitorMac(caller_task_runner, ui_task_runner, delegate)); |
| 299 } | 281 } |
| 300 | 282 |
| 301 } // namespace remoting | 283 } // namespace remoting |
| OLD | NEW |