OLD | NEW |
---|---|
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 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 "chrome/browser/chromeos/login/screen_locker.h" | 5 #include "chrome/browser/chromeos/login/screen_locker.h" |
6 | 6 |
7 #include <gdk/gdkkeysyms.h> | |
7 #include <gdk/gdkx.h> | 8 #include <gdk/gdkx.h> |
8 #include <string> | 9 #include <string> |
9 #include <vector> | 10 #include <vector> |
10 #include <X11/extensions/XTest.h> | 11 #include <X11/extensions/XTest.h> |
11 #include <X11/keysym.h> | 12 #include <X11/keysym.h> |
12 // Evil hack to undo X11 evil #define. See crosbug.com/ | 13 // Evil hack to undo X11 evil #define. See crosbug.com/ |
13 #undef Status | 14 #undef Status |
14 | 15 |
15 #include "app/l10n_util.h" | 16 #include "app/l10n_util.h" |
16 #include "base/command_line.h" | 17 #include "base/command_line.h" |
(...skipping 13 matching lines...) Expand all Loading... | |
30 #include "chrome/browser/chromeos/language_preferences.h" | 31 #include "chrome/browser/chromeos/language_preferences.h" |
31 #include "chrome/browser/chromeos/login/authenticator.h" | 32 #include "chrome/browser/chromeos/login/authenticator.h" |
32 #include "chrome/browser/chromeos/login/background_view.h" | 33 #include "chrome/browser/chromeos/login/background_view.h" |
33 #include "chrome/browser/chromeos/login/login_performer.h" | 34 #include "chrome/browser/chromeos/login/login_performer.h" |
34 #include "chrome/browser/chromeos/login/login_utils.h" | 35 #include "chrome/browser/chromeos/login/login_utils.h" |
35 #include "chrome/browser/chromeos/login/message_bubble.h" | 36 #include "chrome/browser/chromeos/login/message_bubble.h" |
36 #include "chrome/browser/chromeos/login/screen_lock_view.h" | 37 #include "chrome/browser/chromeos/login/screen_lock_view.h" |
37 #include "chrome/browser/chromeos/login/shutdown_button.h" | 38 #include "chrome/browser/chromeos/login/shutdown_button.h" |
38 #include "chrome/browser/chromeos/system_key_event_listener.h" | 39 #include "chrome/browser/chromeos/system_key_event_listener.h" |
39 #include "chrome/browser/chromeos/wm_ipc.h" | 40 #include "chrome/browser/chromeos/wm_ipc.h" |
41 #include "chrome/browser/chromeos/view_ids.h" | |
40 #include "chrome/browser/metrics/user_metrics.h" | 42 #include "chrome/browser/metrics/user_metrics.h" |
41 #include "chrome/browser/profiles/profile_manager.h" | 43 #include "chrome/browser/profiles/profile_manager.h" |
42 #include "chrome/browser/sync/profile_sync_service.h" | 44 #include "chrome/browser/sync/profile_sync_service.h" |
43 #include "chrome/browser/ui/browser.h" | 45 #include "chrome/browser/ui/browser.h" |
44 #include "chrome/common/chrome_switches.h" | 46 #include "chrome/common/chrome_switches.h" |
45 #include "chrome/common/notification_service.h" | 47 #include "chrome/common/notification_service.h" |
46 #include "googleurl/src/gurl.h" | 48 #include "googleurl/src/gurl.h" |
47 #include "grit/generated_resources.h" | 49 #include "grit/generated_resources.h" |
48 #include "grit/theme_resources.h" | 50 #include "grit/theme_resources.h" |
49 #include "third_party/cros/chromeos_wm_ipc_enums.h" | 51 #include "third_party/cros/chromeos_wm_ipc_enums.h" |
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
202 class LockWindow : public views::WidgetGtk { | 204 class LockWindow : public views::WidgetGtk { |
203 public: | 205 public: |
204 LockWindow() | 206 LockWindow() |
205 : views::WidgetGtk(views::WidgetGtk::TYPE_WINDOW), | 207 : views::WidgetGtk(views::WidgetGtk::TYPE_WINDOW), |
206 toplevel_focus_widget_(NULL) { | 208 toplevel_focus_widget_(NULL) { |
207 EnableDoubleBuffer(true); | 209 EnableDoubleBuffer(true); |
208 } | 210 } |
209 | 211 |
210 // GTK propagates key events from parents to children. | 212 // GTK propagates key events from parents to children. |
211 // Make sure LockWindow will never handle key events. | 213 // Make sure LockWindow will never handle key events. |
212 virtual gboolean OnKeyPress(GtkWidget* widget, GdkEventKey* event) { | 214 virtual gboolean OnKeyEvent(GtkWidget* widget, GdkEventKey* event) { |
213 // Don't handle key event in the lock window. | 215 // Don't handle key event in the lock window. |
214 return false; | 216 return false; |
215 } | 217 } |
216 | |
217 virtual gboolean OnKeyRelease(GtkWidget* widget, GdkEventKey* event) { | |
218 // Don't handle key event in the lock window. | |
219 return false; | |
220 } | |
221 | 218 |
222 virtual void OnDestroy(GtkWidget* object) { | 219 virtual void OnDestroy(GtkWidget* object) { |
223 VLOG(1) << "OnDestroy: LockWindow destroyed"; | 220 VLOG(1) << "OnDestroy: LockWindow destroyed"; |
224 views::WidgetGtk::OnDestroy(object); | 221 views::WidgetGtk::OnDestroy(object); |
225 } | 222 } |
226 | 223 |
227 virtual void ClearNativeFocus() { | 224 virtual void ClearNativeFocus() { |
228 DCHECK(toplevel_focus_widget_); | 225 DCHECK(toplevel_focus_widget_); |
229 gtk_widget_grab_focus(toplevel_focus_widget_); | 226 gtk_widget_grab_focus(toplevel_focus_widget_); |
230 } | 227 } |
(...skipping 59 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
290 | 287 |
291 // A child widget that grabs both keyboard and pointer input. | 288 // A child widget that grabs both keyboard and pointer input. |
292 class GrabWidget : public views::WidgetGtk { | 289 class GrabWidget : public views::WidgetGtk { |
293 public: | 290 public: |
294 explicit GrabWidget(chromeos::ScreenLocker* screen_locker) | 291 explicit GrabWidget(chromeos::ScreenLocker* screen_locker) |
295 : views::WidgetGtk(views::WidgetGtk::TYPE_CHILD), | 292 : views::WidgetGtk(views::WidgetGtk::TYPE_CHILD), |
296 screen_locker_(screen_locker), | 293 screen_locker_(screen_locker), |
297 ALLOW_THIS_IN_INITIALIZER_LIST(task_factory_(this)), | 294 ALLOW_THIS_IN_INITIALIZER_LIST(task_factory_(this)), |
298 grab_failure_count_(0), | 295 grab_failure_count_(0), |
299 kbd_grab_status_(GDK_GRAB_INVALID_TIME), | 296 kbd_grab_status_(GDK_GRAB_INVALID_TIME), |
300 mouse_grab_status_(GDK_GRAB_INVALID_TIME) { | 297 mouse_grab_status_(GDK_GRAB_INVALID_TIME), |
298 signout_link_(NULL), | |
299 shutdown_(NULL) { | |
301 } | 300 } |
302 | 301 |
303 virtual void Show() { | 302 virtual void Show() { |
304 views::WidgetGtk::Show(); | 303 views::WidgetGtk::Show(); |
304 signout_link_ = | |
305 screen_locker_->GetViewByID(VIEW_ID_SCREEN_LOCKER_SIGNOUT_LINK); | |
306 shutdown_ = screen_locker_->GetViewByID(VIEW_ID_SCREEN_LOCKER_SHUTDOWN); | |
307 // These can be null in guest mode. | |
305 } | 308 } |
306 | 309 |
307 void ClearGtkGrab() { | 310 void ClearGtkGrab() { |
308 GtkWidget* current_grab_window; | 311 GtkWidget* current_grab_window; |
309 // Grab gtk input first so that the menu holding gtk grab will | 312 // Grab gtk input first so that the menu holding gtk grab will |
310 // close itself. | 313 // close itself. |
311 gtk_grab_add(window_contents()); | 314 gtk_grab_add(window_contents()); |
312 | 315 |
313 // Make sure there is no gtk grab widget so that gtk simply propagates | 316 // Make sure there is no gtk grab widget so that gtk simply propagates |
314 // an event. This is necessary to allow message bubble and password | 317 // an event. This is necessary to allow message bubble and password |
315 // field, button to process events simultaneously. GTK | 318 // field, button to process events simultaneously. GTK |
316 // maintains grab widgets in a linked-list, so we need to remove | 319 // maintains grab widgets in a linked-list, so we need to remove |
317 // until it's empty. | 320 // until it's empty. |
318 while ((current_grab_window = gtk_grab_get_current()) != NULL) | 321 while ((current_grab_window = gtk_grab_get_current()) != NULL) |
319 gtk_grab_remove(current_grab_window); | 322 gtk_grab_remove(current_grab_window); |
320 } | 323 } |
321 | 324 |
325 virtual gboolean OnKeyEvent(GtkWidget* widget, GdkEventKey* event) { | |
326 views::KeyEvent key_event(event); | |
327 // This is a hack to workaround the issue crosbug.com/10655 due to | |
328 // the limitatino that a focus manager cannot handle views in | |
whywhat
2011/01/24 19:27:56
nit: limitatino -> limitation
oshima
2011/01/24 20:24:31
Done.
| |
329 // TYPE_CHILD WidgetGtk correctly. | |
whywhat
2011/01/24 19:27:56
Should we report a bug about that? Is there one al
oshima
2011/01/24 20:24:31
I believe this is by design. I'll task to Jay abou
| |
330 if (signout_link_ && | |
331 event->type == GDK_KEY_PRESS && | |
332 (event->keyval == GDK_Tab || | |
333 event->keyval == GDK_ISO_Left_Tab || | |
334 event->keyval == GDK_KP_Tab)) { | |
335 DCHECK(shutdown_); | |
336 bool reverse = event->state & GDK_SHIFT_MASK; | |
337 if (reverse && signout_link_->HasFocus()) { | |
whywhat
2011/01/24 19:27:56
Will pressing Tab cycle through the links? As I re
oshima
2011/01/24 20:24:31
It moves focus to shutdown if you press shift-tab
| |
338 shutdown_->RequestFocus(); | |
339 return true; | |
340 } | |
341 if (!reverse && shutdown_->HasFocus()) { | |
342 signout_link_->RequestFocus(); | |
343 return true; | |
344 } | |
345 } | |
346 return views::WidgetGtk::OnKeyEvent(widget, event); | |
347 } | |
348 | |
322 virtual gboolean OnButtonPress(GtkWidget* widget, GdkEventButton* event) { | 349 virtual gboolean OnButtonPress(GtkWidget* widget, GdkEventButton* event) { |
323 WidgetGtk::OnButtonPress(widget, event); | 350 WidgetGtk::OnButtonPress(widget, event); |
324 // Never propagate event to parent. | 351 // Never propagate event to parent. |
325 return true; | 352 return true; |
326 } | 353 } |
327 | 354 |
328 // Try to grab all inputs. It initiates another try if it fails to | 355 // Try to grab all inputs. It initiates another try if it fails to |
329 // grab and the retry count is within a limit, or fails with CHECK. | 356 // grab and the retry count is within a limit, or fails with CHECK. |
330 void TryGrabAllInputs(); | 357 void TryGrabAllInputs(); |
331 | 358 |
(...skipping 15 matching lines...) Expand all Loading... | |
347 | 374 |
348 chromeos::ScreenLocker* screen_locker_; | 375 chromeos::ScreenLocker* screen_locker_; |
349 ScopedRunnableMethodFactory<GrabWidget> task_factory_; | 376 ScopedRunnableMethodFactory<GrabWidget> task_factory_; |
350 | 377 |
351 // The number times the widget tried to grab all focus. | 378 // The number times the widget tried to grab all focus. |
352 int grab_failure_count_; | 379 int grab_failure_count_; |
353 // Status of keyboard and mouse grab. | 380 // Status of keyboard and mouse grab. |
354 GdkGrabStatus kbd_grab_status_; | 381 GdkGrabStatus kbd_grab_status_; |
355 GdkGrabStatus mouse_grab_status_; | 382 GdkGrabStatus mouse_grab_status_; |
356 | 383 |
384 views::View* signout_link_; | |
385 views::View* shutdown_; | |
386 | |
357 DISALLOW_COPY_AND_ASSIGN(GrabWidget); | 387 DISALLOW_COPY_AND_ASSIGN(GrabWidget); |
358 }; | 388 }; |
359 | 389 |
360 void GrabWidget::TryGrabAllInputs() { | 390 void GrabWidget::TryGrabAllInputs() { |
361 // Grab x server so that we can atomically grab and take | 391 // Grab x server so that we can atomically grab and take |
362 // action when grab fails. | 392 // action when grab fails. |
363 gdk_x11_grab_server(); | 393 gdk_x11_grab_server(); |
364 if (kbd_grab_status_ != GDK_GRAB_SUCCESS) { | 394 if (kbd_grab_status_ != GDK_GRAB_SUCCESS) { |
365 kbd_grab_status_ = gdk_keyboard_grab(window_contents()->window, FALSE, | 395 kbd_grab_status_ = gdk_keyboard_grab(window_contents()->window, FALSE, |
366 GDK_CURRENT_TIME); | 396 GDK_CURRENT_TIME); |
(...skipping 550 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
917 BubbleBorder::BOTTOM_RIGHT : BubbleBorder::BOTTOM_LEFT); | 947 BubbleBorder::BOTTOM_RIGHT : BubbleBorder::BOTTOM_LEFT); |
918 } | 948 } |
919 | 949 |
920 void ScreenLocker::OnGrabInputs() { | 950 void ScreenLocker::OnGrabInputs() { |
921 DVLOG(1) << "OnGrabInputs"; | 951 DVLOG(1) << "OnGrabInputs"; |
922 input_grabbed_ = true; | 952 input_grabbed_ = true; |
923 if (drawn_) | 953 if (drawn_) |
924 ScreenLockReady(); | 954 ScreenLockReady(); |
925 } | 955 } |
926 | 956 |
957 views::View* ScreenLocker::GetViewByID(int id) { | |
958 return lock_widget_->GetRootView()->GetViewByID(id); | |
959 } | |
960 | |
927 // static | 961 // static |
928 void ScreenLocker::Show() { | 962 void ScreenLocker::Show() { |
929 VLOG(1) << "In ScreenLocker::Show"; | 963 VLOG(1) << "In ScreenLocker::Show"; |
930 UserMetrics::RecordAction(UserMetricsAction("ScreenLocker_Show")); | 964 UserMetrics::RecordAction(UserMetricsAction("ScreenLocker_Show")); |
931 DCHECK(MessageLoop::current()->type() == MessageLoop::TYPE_UI); | 965 DCHECK(MessageLoop::current()->type() == MessageLoop::TYPE_UI); |
932 | 966 |
933 // Exit fullscreen. | 967 // Exit fullscreen. |
934 Browser* browser = BrowserList::GetLastActive(); | 968 Browser* browser = BrowserList::GetLastActive(); |
935 // browser can be NULL if we receive a lock request before the first browser | 969 // browser can be NULL if we receive a lock request before the first browser |
936 // window is shown. | 970 // window is shown. |
(...skipping 180 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1117 | 1151 |
1118 bool ScreenLocker::AcceleratorPressed(const views::Accelerator& accelerator) { | 1152 bool ScreenLocker::AcceleratorPressed(const views::Accelerator& accelerator) { |
1119 if (!background_view_->IsScreenSaverVisible()) { | 1153 if (!background_view_->IsScreenSaverVisible()) { |
1120 StartScreenSaver(); | 1154 StartScreenSaver(); |
1121 return true; | 1155 return true; |
1122 } | 1156 } |
1123 return false; | 1157 return false; |
1124 } | 1158 } |
1125 | 1159 |
1126 } // namespace chromeos | 1160 } // namespace chromeos |
OLD | NEW |