BookmarkManager: Fix 'new folder text field size changes on clicking it' issue.
[chromium-blink-merge.git] / chrome / browser / chromeos / preferences.cc
blobb6ed2db50f8b6c2fe58cad12a26d7d25feb168d1
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 "chrome/browser/chromeos/preferences.h"
7 #include <vector>
9 #include "ash/autoclick/autoclick_controller.h"
10 #include "ash/display/display_manager.h"
11 #include "ash/shell.h"
12 #include "base/command_line.h"
13 #include "base/i18n/time_formatting.h"
14 #include "base/metrics/histogram.h"
15 #include "base/prefs/pref_member.h"
16 #include "base/prefs/pref_registry_simple.h"
17 #include "base/prefs/scoped_user_pref_update.h"
18 #include "base/strings/string_split.h"
19 #include "base/strings/string_util.h"
20 #include "base/strings/utf_string_conversions.h"
21 #include "base/sys_info.h"
22 #include "chrome/browser/browser_process.h"
23 #include "chrome/browser/chrome_notification_types.h"
24 #include "chrome/browser/chromeos/accessibility/magnification_manager.h"
25 #include "chrome/browser/chromeos/drive/file_system_util.h"
26 #include "chrome/browser/chromeos/input_method/input_method_syncer.h"
27 #include "chrome/browser/chromeos/login/session/user_session_manager.h"
28 #include "chrome/browser/chromeos/net/wake_on_wifi_manager.h"
29 #include "chrome/browser/chromeos/system/input_device_settings.h"
30 #include "chrome/browser/download/download_prefs.h"
31 #include "chrome/browser/prefs/pref_service_syncable_util.h"
32 #include "chrome/common/chrome_switches.h"
33 #include "chrome/common/pref_names.h"
34 #include "chromeos/chromeos_switches.h"
35 #include "chromeos/system/statistics_provider.h"
36 #include "chromeos/timezone/timezone_resolver.h"
37 #include "components/drive/drive_pref_names.h"
38 #include "components/feedback/tracing_manager.h"
39 #include "components/pref_registry/pref_registry_syncable.h"
40 #include "components/syncable_prefs/pref_service_syncable.h"
41 #include "components/user_manager/user.h"
42 #include "content/public/browser/browser_thread.h"
43 #include "third_party/icu/source/i18n/unicode/timezone.h"
44 #include "ui/base/ime/chromeos/extension_ime_util.h"
45 #include "ui/base/ime/chromeos/ime_keyboard.h"
46 #include "ui/base/ime/chromeos/input_method_manager.h"
47 #include "ui/chromeos/accessibility_types.h"
48 #include "ui/events/event_constants.h"
49 #include "ui/events/event_utils.h"
50 #include "url/gurl.h"
52 namespace chromeos {
54 static const char kFallbackInputMethodLocale[] = "en-US";
56 Preferences::Preferences()
57 : prefs_(NULL),
58 input_method_manager_(input_method::InputMethodManager::Get()),
59 user_(NULL),
60 user_is_primary_(false) {
61 // Do not observe shell, if there is no shell instance; e.g., in some unit
62 // tests.
63 if (ash::Shell::HasInstance())
64 ash::Shell::GetInstance()->AddShellObserver(this);
67 Preferences::Preferences(input_method::InputMethodManager* input_method_manager)
68 : prefs_(NULL),
69 input_method_manager_(input_method_manager),
70 user_(NULL),
71 user_is_primary_(false) {
72 // Do not observe shell, if there is no shell instance; e.g., in some unit
73 // tests.
74 if (ash::Shell::HasInstance())
75 ash::Shell::GetInstance()->AddShellObserver(this);
78 Preferences::~Preferences() {
79 prefs_->RemoveObserver(this);
80 user_manager::UserManager::Get()->RemoveSessionStateObserver(this);
81 // If shell instance is destoryed before this preferences instance, there is
82 // no need to remove this shell observer.
83 if (ash::Shell::HasInstance())
84 ash::Shell::GetInstance()->RemoveShellObserver(this);
87 // static
88 void Preferences::RegisterPrefs(PrefRegistrySimple* registry) {
89 registry->RegisterBooleanPref(prefs::kOwnerPrimaryMouseButtonRight, false);
90 registry->RegisterBooleanPref(prefs::kOwnerTapToClickEnabled, true);
91 registry->RegisterBooleanPref(prefs::kAccessibilityVirtualKeyboardEnabled,
92 false);
93 registry->RegisterStringPref(prefs::kLogoutStartedLast, std::string());
94 registry->RegisterBooleanPref(prefs::kResolveDeviceTimezoneByGeolocation,
95 true);
98 // static
99 void Preferences::RegisterProfilePrefs(
100 user_prefs::PrefRegistrySyncable* registry) {
101 std::string hardware_keyboard_id;
102 // TODO(yusukes): Remove the runtime hack.
103 if (base::SysInfo::IsRunningOnChromeOS()) {
104 DCHECK(g_browser_process);
105 PrefService* local_state = g_browser_process->local_state();
106 DCHECK(local_state);
107 hardware_keyboard_id =
108 local_state->GetString(prefs::kHardwareKeyboardLayout);
109 } else {
110 hardware_keyboard_id = "xkb:us::eng"; // only for testing.
113 registry->RegisterBooleanPref(prefs::kPerformanceTracingEnabled, false);
115 registry->RegisterBooleanPref(
116 prefs::kTapToClickEnabled,
117 true,
118 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
119 registry->RegisterBooleanPref(
120 prefs::kTapDraggingEnabled,
121 false,
122 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
123 registry->RegisterBooleanPref(prefs::kEnableTouchpadThreeFingerClick, false);
124 // This preference can only be set to true by policy or command_line flag
125 // and it should not carry over to sessions were neither of these is set.
126 registry->RegisterBooleanPref(prefs::kUnifiedDesktopEnabledByDefault, false,
127 PrefRegistry::NO_REGISTRATION_FLAGS);
128 registry->RegisterBooleanPref(
129 prefs::kNaturalScroll, base::CommandLine::ForCurrentProcess()->HasSwitch(
130 switches::kNaturalScrollDefault),
131 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
132 registry->RegisterBooleanPref(
133 prefs::kPrimaryMouseButtonRight,
134 false,
135 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
136 registry->RegisterBooleanPref(prefs::kLabsMediaplayerEnabled, false);
137 registry->RegisterBooleanPref(prefs::kLabsAdvancedFilesystemEnabled, false);
138 registry->RegisterBooleanPref(
139 prefs::kAccessibilityStickyKeysEnabled,
140 false,
141 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
142 registry->RegisterBooleanPref(
143 prefs::kAccessibilityLargeCursorEnabled,
144 false,
145 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
146 registry->RegisterBooleanPref(prefs::kAccessibilitySpokenFeedbackEnabled,
147 false);
148 registry->RegisterBooleanPref(
149 prefs::kAccessibilityHighContrastEnabled,
150 false,
151 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
152 registry->RegisterBooleanPref(
153 prefs::kAccessibilityScreenMagnifierCenterFocus,
154 true,
155 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
156 registry->RegisterBooleanPref(
157 prefs::kAccessibilityScreenMagnifierEnabled, false,
158 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
159 registry->RegisterIntegerPref(
160 prefs::kAccessibilityScreenMagnifierType,
161 ui::kDefaultMagnifierType,
162 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
163 registry->RegisterDoublePref(prefs::kAccessibilityScreenMagnifierScale,
164 std::numeric_limits<double>::min());
165 registry->RegisterBooleanPref(
166 prefs::kAccessibilityAutoclickEnabled,
167 false,
168 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
169 registry->RegisterIntegerPref(
170 prefs::kAccessibilityAutoclickDelayMs,
171 ash::AutoclickController::kDefaultAutoclickDelayMs,
172 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
173 registry->RegisterBooleanPref(
174 prefs::kAccessibilityVirtualKeyboardEnabled,
175 false,
176 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
177 registry->RegisterBooleanPref(
178 prefs::kShouldAlwaysShowAccessibilityMenu,
179 false,
180 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
181 registry->RegisterIntegerPref(
182 prefs::kMouseSensitivity,
184 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
185 registry->RegisterIntegerPref(
186 prefs::kTouchpadSensitivity,
188 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
189 registry->RegisterBooleanPref(
190 prefs::kUse24HourClock,
191 base::GetHourClockType() == base::k24HourClock,
192 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
193 registry->RegisterBooleanPref(
194 drive::prefs::kDisableDrive, false,
195 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
196 registry->RegisterBooleanPref(
197 drive::prefs::kDisableDriveOverCellular, true,
198 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
199 registry->RegisterBooleanPref(
200 drive::prefs::kDisableDriveHostedFiles, false,
201 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
202 // We don't sync prefs::kLanguageCurrentInputMethod and PreviousInputMethod
203 // because they're just used to track the logout state of the device.
204 registry->RegisterStringPref(prefs::kLanguageCurrentInputMethod, "");
205 registry->RegisterStringPref(prefs::kLanguagePreviousInputMethod, "");
206 registry->RegisterStringPref(prefs::kLanguagePreferredLanguages,
207 kFallbackInputMethodLocale);
208 registry->RegisterStringPref(prefs::kLanguagePreloadEngines,
209 hardware_keyboard_id);
210 registry->RegisterStringPref(prefs::kLanguageEnabledExtensionImes, "");
212 registry->RegisterIntegerPref(
213 prefs::kLanguageRemapSearchKeyTo,
214 input_method::kSearchKey,
215 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
216 registry->RegisterIntegerPref(
217 prefs::kLanguageRemapControlKeyTo,
218 input_method::kControlKey,
219 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
220 registry->RegisterIntegerPref(
221 prefs::kLanguageRemapAltKeyTo,
222 input_method::kAltKey,
223 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
224 // We don't sync the CapsLock remapping pref, since the UI hides this pref
225 // on certain devices, so syncing a non-default value to a device that
226 // doesn't allow changing the pref would be odd. http://crbug.com/167237
227 registry->RegisterIntegerPref(prefs::kLanguageRemapCapsLockKeyTo,
228 input_method::kCapsLockKey);
229 registry->RegisterIntegerPref(
230 prefs::kLanguageRemapDiamondKeyTo,
231 input_method::kControlKey,
232 user_prefs::PrefRegistrySyncable::SYNCABLE_PRIORITY_PREF);
233 // The following pref isn't synced since the user may desire a different value
234 // depending on whether an external keyboard is attached to a particular
235 // device.
236 registry->RegisterBooleanPref(prefs::kLanguageSendFunctionKeys, false);
237 registry->RegisterBooleanPref(
238 prefs::kLanguageXkbAutoRepeatEnabled,
239 true,
240 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
241 registry->RegisterIntegerPref(
242 prefs::kLanguageXkbAutoRepeatDelay,
243 language_prefs::kXkbAutoRepeatDelayInMs,
244 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
245 registry->RegisterIntegerPref(
246 prefs::kLanguageXkbAutoRepeatInterval,
247 language_prefs::kXkbAutoRepeatIntervalInMs,
248 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
250 // We don't sync wake-on-wifi related prefs because they are device specific.
251 registry->RegisterBooleanPref(prefs::kWakeOnWifiSsid, true);
253 // 3G first-time usage promo will be shown at least once.
254 registry->RegisterBooleanPref(prefs::kShow3gPromoNotification, true);
256 // Number of times Data Saver prompt has been shown on 3G data network.
257 registry->RegisterIntegerPref(
258 prefs::kDataSaverPromptsShown,
260 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
262 // Initially all existing users would see "What's new" for current version
263 // after update.
264 registry->RegisterStringPref(prefs::kChromeOSReleaseNotesVersion,
265 "0.0.0.0",
266 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
268 registry->RegisterBooleanPref(prefs::kExternalStorageDisabled, false);
270 registry->RegisterStringPref(prefs::kTermsOfServiceURL, "");
272 registry->RegisterBooleanPref(prefs::kTouchHudProjectionEnabled, false);
274 registry->RegisterBooleanPref(prefs::kTouchVirtualKeyboardEnabled, false);
276 input_method::InputMethodSyncer::RegisterProfilePrefs(registry);
278 registry->RegisterBooleanPref(
279 prefs::kResolveTimezoneByGeolocation, true,
280 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF);
282 registry->RegisterBooleanPref(prefs::kCaptivePortalAuthenticationIgnoresProxy,
283 true);
285 registry->RegisterBooleanPref(prefs::kForceMaximizeOnFirstRun, false);
288 void Preferences::InitUserPrefs(syncable_prefs::PrefServiceSyncable* prefs) {
289 prefs_ = prefs;
291 BooleanPrefMember::NamedChangeCallback callback =
292 base::Bind(&Preferences::OnPreferenceChanged, base::Unretained(this));
294 performance_tracing_enabled_.Init(prefs::kPerformanceTracingEnabled,
295 prefs, callback);
296 tap_to_click_enabled_.Init(prefs::kTapToClickEnabled, prefs, callback);
297 tap_dragging_enabled_.Init(prefs::kTapDraggingEnabled, prefs, callback);
298 three_finger_click_enabled_.Init(prefs::kEnableTouchpadThreeFingerClick,
299 prefs, callback);
300 unified_desktop_enabled_by_default_.Init(
301 prefs::kUnifiedDesktopEnabledByDefault, prefs, callback);
302 natural_scroll_.Init(prefs::kNaturalScroll, prefs, callback);
303 mouse_sensitivity_.Init(prefs::kMouseSensitivity, prefs, callback);
304 touchpad_sensitivity_.Init(prefs::kTouchpadSensitivity, prefs, callback);
305 primary_mouse_button_right_.Init(prefs::kPrimaryMouseButtonRight,
306 prefs, callback);
307 download_default_directory_.Init(prefs::kDownloadDefaultDirectory,
308 prefs, callback);
309 touch_hud_projection_enabled_.Init(prefs::kTouchHudProjectionEnabled,
310 prefs, callback);
311 preload_engines_.Init(prefs::kLanguagePreloadEngines, prefs, callback);
312 enabled_extension_imes_.Init(prefs::kLanguageEnabledExtensionImes,
313 prefs, callback);
314 current_input_method_.Init(prefs::kLanguageCurrentInputMethod,
315 prefs, callback);
316 previous_input_method_.Init(prefs::kLanguagePreviousInputMethod,
317 prefs, callback);
319 xkb_auto_repeat_enabled_.Init(
320 prefs::kLanguageXkbAutoRepeatEnabled, prefs, callback);
321 xkb_auto_repeat_delay_pref_.Init(
322 prefs::kLanguageXkbAutoRepeatDelay, prefs, callback);
323 xkb_auto_repeat_interval_pref_.Init(
324 prefs::kLanguageXkbAutoRepeatInterval, prefs, callback);
326 wake_on_wifi_ssid_.Init(prefs::kWakeOnWifiSsid, prefs, callback);
328 pref_change_registrar_.Init(prefs);
329 pref_change_registrar_.Add(prefs::kResolveTimezoneByGeolocation, callback);
330 pref_change_registrar_.Add(prefs::kUse24HourClock, callback);
333 void Preferences::Init(Profile* profile, const user_manager::User* user) {
334 DCHECK(profile);
335 DCHECK(user);
336 syncable_prefs::PrefServiceSyncable* prefs =
337 PrefServiceSyncableFromProfile(profile);
338 // This causes OnIsSyncingChanged to be called when the value of
339 // PrefService::IsSyncing() changes.
340 prefs->AddObserver(this);
341 user_ = user;
342 user_is_primary_ =
343 user_manager::UserManager::Get()->GetPrimaryUser() == user_;
344 InitUserPrefs(prefs);
346 user_manager::UserManager::Get()->AddSessionStateObserver(this);
348 UserSessionManager* session_manager = UserSessionManager::GetInstance();
349 DCHECK(session_manager);
350 ime_state_ = session_manager->GetDefaultIMEState(profile);
352 // Initialize preferences to currently saved state.
353 ApplyPreferences(REASON_INITIALIZATION, "");
355 // Note that |ime_state_| was modified by ApplyPreferences(), and
356 // SetState() is modifying |current_input_method_| (via
357 // PersistUserInputMethod() ). This way SetState() here may be called only
358 // after ApplyPreferences().
359 input_method_manager_->SetState(ime_state_);
361 input_method_syncer_.reset(
362 new input_method::InputMethodSyncer(prefs, ime_state_));
363 input_method_syncer_->Initialize();
365 // If a guest is logged in, initialize the prefs as if this is the first
366 // login. For a regular user this is done in
367 // UserSessionManager::InitProfilePreferences().
368 if (base::CommandLine::ForCurrentProcess()->HasSwitch(
369 switches::kGuestSession))
370 session_manager->SetFirstLoginPrefs(profile, std::string(), std::string());
373 void Preferences::InitUserPrefsForTesting(
374 syncable_prefs::PrefServiceSyncable* prefs,
375 const user_manager::User* user,
376 scoped_refptr<input_method::InputMethodManager::State> ime_state) {
377 user_ = user;
378 ime_state_ = ime_state;
380 if (ime_state.get())
381 input_method_manager_->SetState(ime_state);
383 InitUserPrefs(prefs);
385 input_method_syncer_.reset(
386 new input_method::InputMethodSyncer(prefs, ime_state_));
387 input_method_syncer_->Initialize();
390 void Preferences::SetInputMethodListForTesting() {
391 SetInputMethodList();
394 void Preferences::OnPreferenceChanged(const std::string& pref_name) {
395 ApplyPreferences(REASON_PREF_CHANGED, pref_name);
398 void Preferences::ApplyPreferences(ApplyReason reason,
399 const std::string& pref_name) {
400 DCHECK(reason != REASON_PREF_CHANGED || !pref_name.empty());
401 const bool user_is_owner =
402 user_manager::UserManager::Get()->GetOwnerEmail() == user_->email();
403 const bool user_is_active = user_->is_active();
405 system::TouchpadSettings touchpad_settings;
406 system::MouseSettings mouse_settings;
408 if (user_is_primary_ && (reason == REASON_INITIALIZATION ||
409 pref_name == prefs::kPerformanceTracingEnabled)) {
410 const bool enabled = performance_tracing_enabled_.GetValue();
411 if (enabled)
412 tracing_manager_ = TracingManager::Create();
413 else
414 tracing_manager_.reset();
416 if (reason != REASON_PREF_CHANGED || pref_name == prefs::kTapToClickEnabled) {
417 const bool enabled = tap_to_click_enabled_.GetValue();
418 if (user_is_active)
419 touchpad_settings.SetTapToClick(enabled);
420 if (reason == REASON_PREF_CHANGED)
421 UMA_HISTOGRAM_BOOLEAN("Touchpad.TapToClick.Changed", enabled);
422 else if (reason == REASON_INITIALIZATION)
423 UMA_HISTOGRAM_BOOLEAN("Touchpad.TapToClick.Started", enabled);
425 // Save owner preference in local state to use on login screen.
426 if (user_is_owner) {
427 PrefService* prefs = g_browser_process->local_state();
428 if (prefs->GetBoolean(prefs::kOwnerTapToClickEnabled) != enabled)
429 prefs->SetBoolean(prefs::kOwnerTapToClickEnabled, enabled);
432 if (reason != REASON_PREF_CHANGED ||
433 pref_name == prefs::kTapDraggingEnabled) {
434 const bool enabled = tap_dragging_enabled_.GetValue();
435 if (user_is_active)
436 touchpad_settings.SetTapDragging(enabled);
437 if (reason == REASON_PREF_CHANGED)
438 UMA_HISTOGRAM_BOOLEAN("Touchpad.TapDragging.Changed", enabled);
439 else if (reason == REASON_INITIALIZATION)
440 UMA_HISTOGRAM_BOOLEAN("Touchpad.TapDragging.Started", enabled);
442 if (reason != REASON_PREF_CHANGED ||
443 pref_name == prefs::kEnableTouchpadThreeFingerClick) {
444 const bool enabled = three_finger_click_enabled_.GetValue();
445 if (user_is_active)
446 touchpad_settings.SetThreeFingerClick(enabled);
447 if (reason == REASON_PREF_CHANGED)
448 UMA_HISTOGRAM_BOOLEAN("Touchpad.ThreeFingerClick.Changed", enabled);
449 else if (reason == REASON_INITIALIZATION)
450 UMA_HISTOGRAM_BOOLEAN("Touchpad.ThreeFingerClick.Started", enabled);
452 if (reason != REASON_PREF_CHANGED ||
453 pref_name == prefs::kUnifiedDesktopEnabledByDefault) {
454 const bool enabled = unified_desktop_enabled_by_default_.GetValue();
455 if (ash::Shell::HasInstance()) {
456 ash::Shell::GetInstance()->display_manager()
457 ->SetUnifiedDesktopEnabled(enabled);
460 if (reason != REASON_PREF_CHANGED || pref_name == prefs::kNaturalScroll) {
461 // Force natural scroll default if we've sync'd and if the cmd line arg is
462 // set.
463 ForceNaturalScrollDefault();
465 const bool enabled = natural_scroll_.GetValue();
466 DVLOG(1) << "Natural scroll set to " << enabled;
467 if (user_is_active)
468 touchpad_settings.SetNaturalScroll(enabled);
469 if (reason == REASON_PREF_CHANGED)
470 UMA_HISTOGRAM_BOOLEAN("Touchpad.NaturalScroll.Changed", enabled);
471 else if (reason == REASON_INITIALIZATION)
472 UMA_HISTOGRAM_BOOLEAN("Touchpad.NaturalScroll.Started", enabled);
474 if (reason != REASON_PREF_CHANGED || pref_name == prefs::kMouseSensitivity) {
475 const int sensitivity = mouse_sensitivity_.GetValue();
476 if (user_is_active)
477 mouse_settings.SetSensitivity(sensitivity);
478 if (reason == REASON_PREF_CHANGED) {
479 UMA_HISTOGRAM_ENUMERATION("Mouse.PointerSensitivity.Changed",
480 sensitivity,
481 system::kMaxPointerSensitivity + 1);
482 } else if (reason == REASON_INITIALIZATION) {
483 UMA_HISTOGRAM_ENUMERATION("Mouse.PointerSensitivity.Started",
484 sensitivity,
485 system::kMaxPointerSensitivity + 1);
488 if (reason != REASON_PREF_CHANGED ||
489 pref_name == prefs::kTouchpadSensitivity) {
490 const int sensitivity = touchpad_sensitivity_.GetValue();
491 if (user_is_active)
492 touchpad_settings.SetSensitivity(sensitivity);
493 if (reason == REASON_PREF_CHANGED) {
494 UMA_HISTOGRAM_ENUMERATION("Touchpad.PointerSensitivity.Changed",
495 sensitivity,
496 system::kMaxPointerSensitivity + 1);
497 } else if (reason == REASON_INITIALIZATION) {
498 UMA_HISTOGRAM_ENUMERATION("Touchpad.PointerSensitivity.Started",
499 sensitivity,
500 system::kMaxPointerSensitivity + 1);
503 if (reason != REASON_PREF_CHANGED ||
504 pref_name == prefs::kPrimaryMouseButtonRight) {
505 const bool right = primary_mouse_button_right_.GetValue();
506 if (user_is_active)
507 mouse_settings.SetPrimaryButtonRight(right);
508 if (reason == REASON_PREF_CHANGED)
509 UMA_HISTOGRAM_BOOLEAN("Mouse.PrimaryButtonRight.Changed", right);
510 else if (reason == REASON_INITIALIZATION)
511 UMA_HISTOGRAM_BOOLEAN("Mouse.PrimaryButtonRight.Started", right);
512 // Save owner preference in local state to use on login screen.
513 if (user_is_owner) {
514 PrefService* prefs = g_browser_process->local_state();
515 if (prefs->GetBoolean(prefs::kOwnerPrimaryMouseButtonRight) != right)
516 prefs->SetBoolean(prefs::kOwnerPrimaryMouseButtonRight, right);
519 if (reason != REASON_PREF_CHANGED ||
520 pref_name == prefs::kDownloadDefaultDirectory) {
521 const bool default_download_to_drive = drive::util::IsUnderDriveMountPoint(
522 download_default_directory_.GetValue());
523 if (reason == REASON_PREF_CHANGED)
524 UMA_HISTOGRAM_BOOLEAN(
525 "FileBrowser.DownloadDestination.IsGoogleDrive.Changed",
526 default_download_to_drive);
527 else if (reason == REASON_INITIALIZATION)
528 UMA_HISTOGRAM_BOOLEAN(
529 "FileBrowser.DownloadDestination.IsGoogleDrive.Started",
530 default_download_to_drive);
532 if (reason != REASON_PREF_CHANGED ||
533 pref_name == prefs::kTouchHudProjectionEnabled) {
534 if (user_is_active) {
535 const bool enabled = touch_hud_projection_enabled_.GetValue();
536 // There may not be a shell, e.g., in some unit tests.
537 if (ash::Shell::HasInstance())
538 ash::Shell::GetInstance()->SetTouchHudProjectionEnabled(enabled);
542 if (reason != REASON_PREF_CHANGED ||
543 pref_name == prefs::kLanguageXkbAutoRepeatEnabled) {
544 if (user_is_active) {
545 const bool enabled = xkb_auto_repeat_enabled_.GetValue();
546 input_method::InputMethodManager::Get()
547 ->GetImeKeyboard()
548 ->SetAutoRepeatEnabled(enabled);
551 if (reason != REASON_PREF_CHANGED ||
552 pref_name == prefs::kLanguageXkbAutoRepeatDelay ||
553 pref_name == prefs::kLanguageXkbAutoRepeatInterval) {
554 if (user_is_active)
555 UpdateAutoRepeatRate();
558 if (reason == REASON_INITIALIZATION)
559 SetInputMethodList();
561 if (pref_name == prefs::kLanguagePreloadEngines &&
562 reason == REASON_PREF_CHANGED) {
563 SetLanguageConfigStringListAsCSV(language_prefs::kGeneralSectionName,
564 language_prefs::kPreloadEnginesConfigName,
565 preload_engines_.GetValue());
568 if ((reason == REASON_INITIALIZATION) ||
569 (pref_name == prefs::kLanguageEnabledExtensionImes &&
570 reason == REASON_PREF_CHANGED)) {
571 std::string value(enabled_extension_imes_.GetValue());
573 std::vector<std::string> split_values;
574 if (!value.empty()) {
575 split_values = base::SplitString(value, ",", base::TRIM_WHITESPACE,
576 base::SPLIT_WANT_ALL);
578 ime_state_->SetEnabledExtensionImes(&split_values);
581 if (user_is_active) {
582 system::InputDeviceSettings::Get()->UpdateTouchpadSettings(
583 touchpad_settings);
584 system::InputDeviceSettings::Get()->UpdateMouseSettings(mouse_settings);
587 if (user_is_primary_ && (reason != REASON_PREF_CHANGED ||
588 pref_name == prefs::kWakeOnWifiSsid)) {
589 int features = wake_on_wifi_ssid_.GetValue() ?
590 WakeOnWifiManager::WAKE_ON_SSID : WakeOnWifiManager::WAKE_ON_NONE;
591 // The flag enables wake on packets but doesn't update a preference.
592 if (base::CommandLine::ForCurrentProcess()->
593 HasSwitch(switches::kWakeOnPackets)) {
594 features |= WakeOnWifiManager::WAKE_ON_PACKET;
596 WakeOnWifiManager::Get()->OnPreferenceChanged(
597 static_cast<WakeOnWifiManager::WakeOnWifiFeature>(features));
600 if (pref_name == prefs::kResolveTimezoneByGeolocation &&
601 reason != REASON_ACTIVE_USER_CHANGED) {
602 const bool value = prefs_->GetBoolean(prefs::kResolveTimezoneByGeolocation);
603 if (user_is_owner) {
604 g_browser_process->local_state()->SetBoolean(
605 prefs::kResolveDeviceTimezoneByGeolocation, value);
607 if (user_is_primary_) {
608 if (value) {
609 g_browser_process->platform_part()->GetTimezoneResolver()->Start();
610 } else {
611 g_browser_process->platform_part()->GetTimezoneResolver()->Stop();
612 if (reason == REASON_PREF_CHANGED) {
613 // Allow immediate timezone update on Stop + Start.
614 g_browser_process->local_state()->ClearPref(
615 TimeZoneResolver::kLastTimeZoneRefreshTime);
621 if (pref_name == prefs::kUse24HourClock ||
622 reason != REASON_ACTIVE_USER_CHANGED) {
623 const bool value = prefs_->GetBoolean(prefs::kUse24HourClock);
624 user_manager::UserManager::Get()->SetKnownUserBooleanPref(
625 user_->GetUserID(), prefs::kUse24HourClock, value);
629 void Preferences::OnIsSyncingChanged() {
630 DVLOG(1) << "OnIsSyncingChanged";
631 ForceNaturalScrollDefault();
634 void Preferences::ForceNaturalScrollDefault() {
635 DVLOG(1) << "ForceNaturalScrollDefault";
636 if (base::CommandLine::ForCurrentProcess()->HasSwitch(
637 switches::kNaturalScrollDefault) &&
638 prefs_->IsSyncing() && !prefs_->GetUserPrefValue(prefs::kNaturalScroll)) {
639 DVLOG(1) << "Natural scroll forced to true";
640 natural_scroll_.SetValue(true);
641 UMA_HISTOGRAM_BOOLEAN("Touchpad.NaturalScroll.Forced", true);
645 void Preferences::SetLanguageConfigStringListAsCSV(const char* section,
646 const char* name,
647 const std::string& value) {
648 VLOG(1) << "Setting " << name << " to '" << value << "'";
650 std::vector<std::string> split_values;
651 if (!value.empty()) {
652 split_values = base::SplitString(value, ",", base::TRIM_WHITESPACE,
653 base::SPLIT_WANT_ALL);
656 // Transfers the xkb id to extension-xkb id.
657 if (input_method_manager_->MigrateInputMethods(&split_values))
658 preload_engines_.SetValue(base::JoinString(split_values, ","));
660 if (section == std::string(language_prefs::kGeneralSectionName) &&
661 name == std::string(language_prefs::kPreloadEnginesConfigName)) {
662 ime_state_->ReplaceEnabledInputMethods(split_values);
663 return;
667 void Preferences::SetInputMethodList() {
668 // When |preload_engines_| are set, InputMethodManager::ChangeInputMethod()
669 // might be called to change the current input method to the first one in the
670 // |preload_engines_| list. This also updates previous/current input method
671 // prefs. That's why GetValue() calls are placed before the
672 // SetLanguageConfigStringListAsCSV() call below.
673 const std::string previous_input_method_id =
674 previous_input_method_.GetValue();
675 const std::string current_input_method_id = current_input_method_.GetValue();
676 SetLanguageConfigStringListAsCSV(language_prefs::kGeneralSectionName,
677 language_prefs::kPreloadEnginesConfigName,
678 preload_engines_.GetValue());
680 // ChangeInputMethod() has to be called AFTER the value of |preload_engines_|
681 // is sent to the InputMethodManager. Otherwise, the ChangeInputMethod request
682 // might be ignored as an invalid input method ID. The ChangeInputMethod()
683 // calls are also necessary to restore the previous/current input method prefs
684 // which could have been modified by the SetLanguageConfigStringListAsCSV call
685 // above to the original state.
686 if (!previous_input_method_id.empty())
687 ime_state_->ChangeInputMethod(previous_input_method_id,
688 false /* show_message */);
689 if (!current_input_method_id.empty())
690 ime_state_->ChangeInputMethod(current_input_method_id,
691 false /* show_message */);
694 void Preferences::UpdateAutoRepeatRate() {
695 input_method::AutoRepeatRate rate;
696 rate.initial_delay_in_ms = xkb_auto_repeat_delay_pref_.GetValue();
697 rate.repeat_interval_in_ms = xkb_auto_repeat_interval_pref_.GetValue();
698 DCHECK(rate.initial_delay_in_ms > 0);
699 DCHECK(rate.repeat_interval_in_ms > 0);
700 input_method::InputMethodManager::Get()
701 ->GetImeKeyboard()
702 ->SetAutoRepeatRate(rate);
705 void Preferences::OnTouchHudProjectionToggled(bool enabled) {
706 if (touch_hud_projection_enabled_.GetValue() == enabled)
707 return;
708 if (!user_->is_active())
709 return;
710 touch_hud_projection_enabled_.SetValue(enabled);
713 void Preferences::ActiveUserChanged(const user_manager::User* active_user) {
714 if (active_user != user_)
715 return;
716 ApplyPreferences(REASON_ACTIVE_USER_CHANGED, "");
719 } // namespace chromeos