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 "chrome/browser/chromeos/kiosk_mode/kiosk_mode_idle_logout.h" 6 7#include "ash/shell.h" 8#include "base/bind.h" 9#include "base/lazy_instance.h" 10#include "base/logging.h" 11#include "base/message_loop/message_loop.h" 12#include "chrome/browser/chrome_notification_types.h" 13#include "chrome/browser/chromeos/kiosk_mode/kiosk_mode_settings.h" 14#include "chrome/browser/chromeos/login/users/user_manager.h" 15#include "chrome/browser/chromeos/ui/idle_logout_dialog_view.h" 16#include "content/public/browser/notification_observer.h" 17#include "content/public/browser/notification_registrar.h" 18#include "content/public/browser/notification_service.h" 19#include "ui/wm/core/user_activity_detector.h" 20 21namespace chromeos { 22 23namespace { 24 25static base::LazyInstance<KioskModeIdleLogout> 26 g_kiosk_mode_idle_logout = LAZY_INSTANCE_INITIALIZER; 27 28} // namespace 29 30// static 31void KioskModeIdleLogout::Initialize() { 32 g_kiosk_mode_idle_logout.Get(); 33} 34 35KioskModeIdleLogout::KioskModeIdleLogout() { 36 if (KioskModeSettings::Get()->is_initialized()) { 37 Setup(); 38 } else { 39 KioskModeSettings::Get()->Initialize(base::Bind(&KioskModeIdleLogout::Setup, 40 base::Unretained(this))); 41 } 42} 43 44KioskModeIdleLogout::~KioskModeIdleLogout() { 45 if (ash::Shell::HasInstance() && 46 ash::Shell::GetInstance()->user_activity_detector()->HasObserver(this)) 47 ash::Shell::GetInstance()->user_activity_detector()->RemoveObserver(this); 48} 49 50void KioskModeIdleLogout::Setup() { 51 if (UserManager::Get()->IsLoggedInAsDemoUser()) { 52 // This means that we're recovering from a crash. The user is already 53 // logged in, so go ahead and start the timer. 54 Start(); 55 } else { 56 registrar_.Add(this, chrome::NOTIFICATION_LOGIN_USER_CHANGED, 57 content::NotificationService::AllSources()); 58 } 59} 60 61void KioskModeIdleLogout::Observe( 62 int type, 63 const content::NotificationSource& source, 64 const content::NotificationDetails& details) { 65 if (type == chrome::NOTIFICATION_LOGIN_USER_CHANGED) { 66 Start(); 67 registrar_.RemoveAll(); 68 } 69} 70 71void KioskModeIdleLogout::OnUserActivity(const ui::Event* event) { 72 IdleLogoutDialogView::CloseDialog(); 73 ResetTimer(); 74} 75 76void KioskModeIdleLogout::Start() { 77 if (!ash::Shell::GetInstance()->user_activity_detector()->HasObserver(this)) 78 ash::Shell::GetInstance()->user_activity_detector()->AddObserver(this); 79 ResetTimer(); 80} 81 82void KioskModeIdleLogout::ResetTimer() { 83 if (timer_.IsRunning()) { 84 timer_.Reset(); 85 } else { 86 // OneShotTimer destroys the posted task after running it, so Reset() 87 // isn't safe to call on a timer that's already fired. 88 timer_.Start(FROM_HERE, KioskModeSettings::Get()->GetIdleLogoutTimeout(), 89 base::Bind(&KioskModeIdleLogout::OnTimeout, 90 base::Unretained(this))); 91 } 92} 93 94void KioskModeIdleLogout::OnTimeout() { 95 IdleLogoutDialogView::ShowDialog(); 96} 97 98} // namespace chromeos 99