Upstream version 5.34.104.0
[platform/framework/web/crosswalk.git] / src / chrome / browser / ui / webui / options / browser_options_handler.cc
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/ui/webui/options/browser_options_handler.h"
6
7 #include <string>
8 #include <vector>
9
10 #include "apps/app_window.h"
11 #include "apps/app_window_registry.h"
12 #include "base/bind.h"
13 #include "base/bind_helpers.h"
14 #include "base/command_line.h"
15 #include "base/memory/singleton.h"
16 #include "base/metrics/field_trial.h"
17 #include "base/metrics/histogram.h"
18 #include "base/path_service.h"
19 #include "base/prefs/pref_service.h"
20 #include "base/prefs/scoped_user_pref_update.h"
21 #include "base/stl_util.h"
22 #include "base/strings/string_number_conversions.h"
23 #include "base/strings/utf_string_conversions.h"
24 #include "base/value_conversions.h"
25 #include "base/values.h"
26 #include "chrome/browser/auto_launch_trial.h"
27 #include "chrome/browser/browser_process.h"
28 #include "chrome/browser/chrome_notification_types.h"
29 #include "chrome/browser/chrome_page_zoom.h"
30 #include "chrome/browser/custom_home_pages_table_model.h"
31 #include "chrome/browser/download/download_prefs.h"
32 #include "chrome/browser/gpu/gpu_mode_manager.h"
33 #include "chrome/browser/lifetime/application_lifetime.h"
34 #include "chrome/browser/prefs/session_startup_pref.h"
35 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service.h"
36 #include "chrome/browser/printing/cloud_print/cloud_print_proxy_service_factory.h"
37 #include "chrome/browser/printing/cloud_print/cloud_print_url.h"
38 #include "chrome/browser/profile_resetter/automatic_profile_resetter.h"
39 #include "chrome/browser/profile_resetter/automatic_profile_resetter_factory.h"
40 #include "chrome/browser/profiles/profile.h"
41 #include "chrome/browser/profiles/profile_info_cache.h"
42 #include "chrome/browser/profiles/profile_info_util.h"
43 #include "chrome/browser/profiles/profile_manager.h"
44 #include "chrome/browser/profiles/profile_metrics.h"
45 #include "chrome/browser/profiles/profile_shortcut_manager.h"
46 #include "chrome/browser/profiles/profile_window.h"
47 #include "chrome/browser/profiles/profiles_state.h"
48 #include "chrome/browser/search/hotword_service.h"
49 #include "chrome/browser/search/hotword_service_factory.h"
50 #include "chrome/browser/search/search.h"
51 #include "chrome/browser/search_engines/template_url.h"
52 #include "chrome/browser/search_engines/template_url_service.h"
53 #include "chrome/browser/search_engines/template_url_service_factory.h"
54 #include "chrome/browser/signin/signin_manager.h"
55 #include "chrome/browser/signin/signin_manager_factory.h"
56 #include "chrome/browser/sync/profile_sync_service.h"
57 #include "chrome/browser/sync/profile_sync_service_factory.h"
58 #include "chrome/browser/sync/sync_ui_util.h"
59 #include "chrome/browser/themes/theme_service.h"
60 #include "chrome/browser/themes/theme_service_factory.h"
61 #include "chrome/browser/ui/browser_finder.h"
62 #include "chrome/browser/ui/chrome_select_file_policy.h"
63 #include "chrome/browser/ui/host_desktop.h"
64 #include "chrome/browser/ui/options/options_util.h"
65 #include "chrome/browser/ui/webui/favicon_source.h"
66 #include "chrome/browser/ui/webui/options/options_handlers_helper.h"
67 #include "chrome/common/chrome_constants.h"
68 #include "chrome/common/chrome_paths.h"
69 #include "chrome/common/chrome_switches.h"
70 #include "chrome/common/net/url_fixer_upper.h"
71 #include "chrome/common/pref_names.h"
72 #include "chrome/common/url_constants.h"
73 #include "chromeos/chromeos_switches.h"
74 #include "content/public/browser/browser_thread.h"
75 #include "content/public/browser/download_manager.h"
76 #include "content/public/browser/navigation_controller.h"
77 #include "content/public/browser/notification_details.h"
78 #include "content/public/browser/notification_service.h"
79 #include "content/public/browser/notification_source.h"
80 #include "content/public/browser/notification_types.h"
81 #include "content/public/browser/url_data_source.h"
82 #include "content/public/browser/user_metrics.h"
83 #include "content/public/browser/web_contents.h"
84 #include "content/public/browser/web_contents_view.h"
85 #include "content/public/common/page_zoom.h"
86 #include "google_apis/gaia/gaia_auth_util.h"
87 #include "google_apis/gaia/google_service_auth_error.h"
88 #include "grit/chromium_strings.h"
89 #include "grit/generated_resources.h"
90 #include "grit/locale_settings.h"
91 #include "grit/theme_resources.h"
92 #include "third_party/skia/include/core/SkBitmap.h"
93 #include "ui/base/l10n/l10n_util.h"
94 #include "ui/base/webui/web_ui_util.h"
95
96 #if !defined(OS_CHROMEOS)
97 #include "chrome/browser/ui/webui/options/advanced_options_utils.h"
98 #endif
99
100 #if defined(OS_CHROMEOS)
101 #include "ash/ash_switches.h"
102 #include "ash/magnifier/magnifier_constants.h"
103 #include "chrome/browser/chromeos/accessibility/accessibility_util.h"
104 #include "chrome/browser/chromeos/extensions/wallpaper_manager_util.h"
105 #include "chrome/browser/chromeos/login/user.h"
106 #include "chrome/browser/chromeos/login/user_manager.h"
107 #include "chrome/browser/chromeos/policy/browser_policy_connector_chromeos.h"
108 #include "chrome/browser/chromeos/settings/cros_settings.h"
109 #include "chrome/browser/chromeos/system/timezone_util.h"
110 #include "chrome/browser/policy/profile_policy_connector.h"
111 #include "chrome/browser/policy/profile_policy_connector_factory.h"
112 #include "chrome/browser/ui/browser_window.h"
113 #include "chromeos/dbus/dbus_thread_manager.h"
114 #include "chromeos/dbus/power_manager_client.h"
115 #include "components/policy/core/common/policy_map.h"
116 #include "components/policy/core/common/policy_namespace.h"
117 #include "components/policy/core/common/policy_service.h"
118 #include "policy/policy_constants.h"
119 #include "ui/gfx/image/image_skia.h"
120 #endif  // defined(OS_CHROMEOS)
121
122 #if defined(OS_WIN)
123 #include "chrome/installer/util/auto_launch_util.h"
124 #endif  // defined(OS_WIN)
125
126 #if defined(ENABLE_MDNS)
127 #include "chrome/browser/local_discovery/privet_notifications.h"
128 #endif
129
130 using base::UserMetricsAction;
131 using content::BrowserContext;
132 using content::BrowserThread;
133 using content::DownloadManager;
134 using content::OpenURLParams;
135 using content::Referrer;
136
137 namespace options {
138
139 BrowserOptionsHandler::BrowserOptionsHandler()
140     : page_initialized_(false),
141       template_url_service_(NULL),
142       cloud_print_mdns_ui_enabled_(false),
143       weak_ptr_factory_(this) {
144 #if !defined(OS_MACOSX)
145   default_browser_worker_ = new ShellIntegration::DefaultBrowserWorker(this);
146 #endif
147
148 #if defined(ENABLE_FULL_PRINTING)
149 #if !defined(GOOGLE_CHROME_BUILD) && defined(OS_WIN)
150   // On Windows, we need the PDF plugin which is only guaranteed to exist on
151   // Google Chrome builds. Use a command-line switch for Windows non-Google
152   //  Chrome builds.
153   cloud_print_connector_ui_enabled_ =
154       CommandLine::ForCurrentProcess()->HasSwitch(
155       switches::kEnableCloudPrintProxy);
156 #elif !defined(OS_CHROMEOS)
157   // Always enabled for Mac, Linux and Google Chrome Windows builds.
158   // Never enabled for Chrome OS, we don't even need to indicate it.
159   cloud_print_connector_ui_enabled_ = true;
160 #endif
161 #endif  // defined(ENABLE_FULL_PRINTING)
162
163 #if defined(ENABLE_MDNS)
164   cloud_print_mdns_ui_enabled_ = !CommandLine::ForCurrentProcess()->HasSwitch(
165         switches::kDisableDeviceDiscovery);
166 #endif  // defined(ENABLE_MDNS)
167 }
168
169 BrowserOptionsHandler::~BrowserOptionsHandler() {
170   ProfileSyncService* sync_service(ProfileSyncServiceFactory::
171       GetInstance()->GetForProfile(Profile::FromWebUI(web_ui())));
172   if (sync_service)
173     sync_service->RemoveObserver(this);
174
175   if (default_browser_worker_.get())
176     default_browser_worker_->ObserverDestroyed();
177   if (template_url_service_)
178     template_url_service_->RemoveObserver(this);
179   // There may be pending file dialogs, we need to tell them that we've gone
180   // away so they don't try and call back to us.
181   if (select_folder_dialog_.get())
182     select_folder_dialog_->ListenerDestroyed();
183 }
184
185 void BrowserOptionsHandler::GetLocalizedValues(base::DictionaryValue* values) {
186   DCHECK(values);
187
188   static OptionsStringResource resources[] = {
189     { "advancedSectionTitleCloudPrint", IDS_GOOGLE_CLOUD_PRINT },
190     { "currentUserOnly", IDS_OPTIONS_CURRENT_USER_ONLY },
191     { "advancedSectionTitleContent",
192       IDS_OPTIONS_ADVANCED_SECTION_TITLE_CONTENT },
193     { "advancedSectionTitleLanguages",
194       IDS_OPTIONS_ADVANCED_SECTION_TITLE_LANGUAGES },
195     { "advancedSectionTitleNetwork",
196       IDS_OPTIONS_ADVANCED_SECTION_TITLE_NETWORK },
197     { "advancedSectionTitlePrivacy",
198       IDS_OPTIONS_ADVANCED_SECTION_TITLE_PRIVACY },
199     { "advancedSectionTitleSecurity",
200       IDS_OPTIONS_ADVANCED_SECTION_TITLE_SECURITY },
201     { "autofillEnabled", IDS_OPTIONS_AUTOFILL_ENABLE },
202     { "autologinEnabled", IDS_OPTIONS_PASSWORDS_AUTOLOGIN },
203     { "autoOpenFileTypesInfo", IDS_OPTIONS_OPEN_FILE_TYPES_AUTOMATICALLY },
204     { "autoOpenFileTypesResetToDefault",
205       IDS_OPTIONS_AUTOOPENFILETYPES_RESETTODEFAULT },
206     { "changeHomePage", IDS_OPTIONS_CHANGE_HOME_PAGE },
207     { "certificatesManageButton", IDS_OPTIONS_CERTIFICATES_MANAGE_BUTTON },
208     { "customizeSync", IDS_OPTIONS_CUSTOMIZE_SYNC_BUTTON_LABEL },
209     { "defaultFontSizeLabel", IDS_OPTIONS_DEFAULT_FONT_SIZE_LABEL },
210     { "defaultSearchManageEngines", IDS_OPTIONS_DEFAULTSEARCH_MANAGE_ENGINES },
211     { "defaultZoomFactorLabel", IDS_OPTIONS_DEFAULT_ZOOM_LEVEL_LABEL },
212 #if defined(OS_CHROMEOS)
213     { "disableGData", IDS_OPTIONS_DISABLE_GDATA },
214 #endif
215     { "disableWebServices", IDS_OPTIONS_DISABLE_WEB_SERVICES },
216 #if defined(OS_CHROMEOS)
217     { "displayOptions",
218       IDS_OPTIONS_SETTINGS_DISPLAY_OPTIONS_BUTTON_LABEL },
219 #endif
220     { "doNotTrack", IDS_OPTIONS_ENABLE_DO_NOT_TRACK },
221     { "doNotTrackConfirmMessage", IDS_OPTIONS_ENABLE_DO_NOT_TRACK_BUBBLE_TEXT },
222     { "doNotTrackConfirmEnable",
223        IDS_OPTIONS_ENABLE_DO_NOT_TRACK_BUBBLE_ENABLE },
224     { "doNotTrackConfirmDisable",
225        IDS_OPTIONS_ENABLE_DO_NOT_TRACK_BUBBLE_DISABLE },
226     { "downloadLocationAskForSaveLocation",
227       IDS_OPTIONS_DOWNLOADLOCATION_ASKFORSAVELOCATION },
228     { "downloadLocationBrowseTitle",
229       IDS_OPTIONS_DOWNLOADLOCATION_BROWSE_TITLE },
230     { "downloadLocationChangeButton",
231       IDS_OPTIONS_DOWNLOADLOCATION_CHANGE_BUTTON },
232     { "downloadLocationGroupName", IDS_OPTIONS_DOWNLOADLOCATION_GROUP_NAME },
233     { "enableLogging", IDS_OPTIONS_ENABLE_LOGGING },
234     { "fontSettingsCustomizeFontsButton",
235       IDS_OPTIONS_FONTSETTINGS_CUSTOMIZE_FONTS_BUTTON },
236     { "fontSizeLabelCustom", IDS_OPTIONS_FONT_SIZE_LABEL_CUSTOM },
237     { "fontSizeLabelLarge", IDS_OPTIONS_FONT_SIZE_LABEL_LARGE },
238     { "fontSizeLabelMedium", IDS_OPTIONS_FONT_SIZE_LABEL_MEDIUM },
239     { "fontSizeLabelSmall", IDS_OPTIONS_FONT_SIZE_LABEL_SMALL },
240     { "fontSizeLabelVeryLarge", IDS_OPTIONS_FONT_SIZE_LABEL_VERY_LARGE },
241     { "fontSizeLabelVerySmall", IDS_OPTIONS_FONT_SIZE_LABEL_VERY_SMALL },
242     { "hideAdvancedSettings", IDS_SETTINGS_HIDE_ADVANCED_SETTINGS },
243     { "homePageNtp", IDS_OPTIONS_HOMEPAGE_NTP },
244     { "homePageShowHomeButton", IDS_OPTIONS_TOOLBAR_SHOW_HOME_BUTTON },
245     { "homePageUseNewTab", IDS_OPTIONS_HOMEPAGE_USE_NEWTAB },
246     { "homePageUseURL", IDS_OPTIONS_HOMEPAGE_USE_URL },
247     { "hotwordSearchEnable", IDS_HOTWORD_SEARCH_PREF_CHKBOX },
248     { "hotwordConfirmEnable", IDS_HOTWORD_CONFIRM_BUBBLE_ENABLE },
249     { "hotwordConfirmDisable", IDS_HOTWORD_CONFIRM_BUBBLE_DISABLE },
250     { "hotwordConfirmMessage", IDS_HOTWORD_SEARCH_PREF_DESCRIPTION },
251     { "importData", IDS_OPTIONS_IMPORT_DATA_BUTTON },
252     { "improveBrowsingExperience", IDS_OPTIONS_IMPROVE_BROWSING_EXPERIENCE },
253     { "languageAndSpellCheckSettingsButton",
254       IDS_OPTIONS_SETTINGS_LANGUAGE_AND_INPUT_SETTINGS },
255     { "linkDoctorPref", IDS_OPTIONS_LINKDOCTOR_PREF },
256     { "manageAutofillSettings", IDS_OPTIONS_MANAGE_AUTOFILL_SETTINGS_LINK },
257     { "manageLanguages", IDS_OPTIONS_TRANSLATE_MANAGE_LANGUAGES },
258     { "managePasswords", IDS_OPTIONS_PASSWORDS_MANAGE_PASSWORDS_LINK },
259     { "networkPredictionEnabledDescription",
260       IDS_NETWORK_PREDICTION_ENABLED_DESCRIPTION },
261     { "passwordsAndAutofillGroupName",
262       IDS_OPTIONS_PASSWORDS_AND_FORMS_GROUP_NAME },
263     { "passwordManagerEnabled", IDS_OPTIONS_PASSWORD_MANAGER_ENABLE },
264     { "privacyClearDataButton", IDS_OPTIONS_PRIVACY_CLEAR_DATA_BUTTON },
265     { "privacyContentSettingsButton",
266       IDS_OPTIONS_PRIVACY_CONTENT_SETTINGS_BUTTON },
267     { "profilesCreate", IDS_PROFILES_CREATE_BUTTON_LABEL },
268     { "profilesDelete", IDS_PROFILES_DELETE_BUTTON_LABEL },
269     { "profilesDeleteSingle", IDS_PROFILES_DELETE_SINGLE_BUTTON_LABEL },
270     { "profilesListItemCurrent", IDS_PROFILES_LIST_ITEM_CURRENT },
271     { "profilesManage", IDS_PROFILES_MANAGE_BUTTON_LABEL },
272     { "profilesSupervisedDashboardTip",
273       IDS_PROFILES_SUPERVISED_USER_DASHBOARD_TIP },
274 #if defined(ENABLE_SETTINGS_APP)
275     { "profilesAppListSwitch", IDS_SETTINGS_APP_PROFILES_SWITCH_BUTTON_LABEL },
276 #endif
277     { "proxiesLabelExtension", IDS_OPTIONS_EXTENSION_PROXIES_LABEL },
278     { "proxiesLabelSystem", IDS_OPTIONS_SYSTEM_PROXIES_LABEL,
279       IDS_PRODUCT_NAME },
280     { "resetProfileSettings", IDS_RESET_PROFILE_SETTINGS_BUTTON },
281     { "resetProfileSettingsDescription",
282       IDS_RESET_PROFILE_SETTINGS_DESCRIPTION },
283     { "resetProfileSettingsSectionTitle",
284       IDS_RESET_PROFILE_SETTINGS_SECTION_TITLE },
285     { "safeBrowsingEnableProtection",
286       IDS_OPTIONS_SAFEBROWSING_ENABLEPROTECTION },
287     { "safeBrowsingEnableDownloadFeedback",
288       IDS_OPTIONS_SAFEBROWSING_ENABLEDOWNLOADFEEDBACK },
289     { "sectionTitleAppearance", IDS_APPEARANCE_GROUP_NAME },
290     { "sectionTitleDefaultBrowser", IDS_OPTIONS_DEFAULTBROWSER_GROUP_NAME },
291     { "sectionTitleUsers", IDS_PROFILES_OPTIONS_GROUP_NAME },
292     { "sectionTitleSearch", IDS_OPTIONS_DEFAULTSEARCH_GROUP_NAME },
293     { "sectionTitleStartup", IDS_OPTIONS_STARTUP_GROUP_NAME },
294     { "sectionTitleSync", IDS_SYNC_OPTIONS_GROUP_NAME },
295     { "spellingConfirmMessage", IDS_CONTENT_CONTEXT_SPELLING_BUBBLE_TEXT },
296     { "spellingConfirmEnable", IDS_CONTENT_CONTEXT_SPELLING_BUBBLE_ENABLE },
297     { "spellingConfirmDisable", IDS_CONTENT_CONTEXT_SPELLING_BUBBLE_DISABLE },
298     { "spellingPref", IDS_OPTIONS_SPELLING_PREF },
299     { "startupRestoreLastSession", IDS_OPTIONS_STARTUP_RESTORE_LAST_SESSION },
300     { "settingsTitle", IDS_SETTINGS_TITLE },
301     { "showAdvancedSettings", IDS_SETTINGS_SHOW_ADVANCED_SETTINGS },
302     { "sslCheckRevocation", IDS_OPTIONS_SSL_CHECKREVOCATION },
303     { "startupSetPages", IDS_OPTIONS_STARTUP_SET_PAGES },
304     { "startupShowNewTab", IDS_OPTIONS_STARTUP_SHOW_NEWTAB },
305     { "startupShowPages", IDS_OPTIONS_STARTUP_SHOW_PAGES },
306     { "suggestPref", IDS_OPTIONS_SUGGEST_PREF },
307     { "syncButtonTextInProgress", IDS_SYNC_NTP_SETUP_IN_PROGRESS },
308     { "syncButtonTextStop", IDS_SYNC_STOP_SYNCING_BUTTON_LABEL },
309     { "themesGallery", IDS_THEMES_GALLERY_BUTTON },
310     { "themesGalleryURL", IDS_THEMES_GALLERY_URL },
311     { "tabsToLinksPref", IDS_OPTIONS_TABS_TO_LINKS_PREF },
312     { "toolbarShowBookmarksBar", IDS_OPTIONS_TOOLBAR_SHOW_BOOKMARKS_BAR },
313     { "toolbarShowHomeButton", IDS_OPTIONS_TOOLBAR_SHOW_HOME_BUTTON },
314     { "translateEnableTranslate",
315       IDS_OPTIONS_TRANSLATE_ENABLE_TRANSLATE },
316 #if defined(OS_LINUX) && !defined(OS_CHROMEOS)
317     { "showWindowDecorations", IDS_SHOW_WINDOW_DECORATIONS },
318     { "themesNativeButton", IDS_THEMES_GTK_BUTTON },
319     { "themesSetClassic", IDS_THEMES_SET_CLASSIC },
320 #else
321     { "themes", IDS_THEMES_GROUP_NAME },
322 #endif
323     { "themesReset", IDS_THEMES_RESET_BUTTON },
324 #if defined(OS_CHROMEOS)
325     { "accessibilityExplanation",
326       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_EXPLANATION },
327     { "accessibilitySettings",
328       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SETTINGS },
329     { "accessibilityHighContrast",
330       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_HIGH_CONTRAST_DESCRIPTION },
331     { "accessibilityScreenMagnifier",
332       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SCREEN_MAGNIFIER_DESCRIPTION },
333     { "accessibilityTapDragging",
334       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_TOUCHPAD_TAP_DRAGGING_DESCRIPTION },
335     { "accessibilityScreenMagnifierOff",
336       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SCREEN_MAGNIFIER_OFF },
337     { "accessibilityScreenMagnifierFull",
338       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SCREEN_MAGNIFIER_FULL },
339     { "accessibilityScreenMagnifierPartial",
340       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SCREEN_MAGNIFIER_PARTIAL },
341     { "accessibilityLargeCursor",
342       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_LARGE_CURSOR_DESCRIPTION },
343     { "accessibilityStickyKeys",
344       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_STICKY_KEYS_DESCRIPTION },
345     { "accessibilitySpokenFeedback",
346       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SPOKEN_FEEDBACK_DESCRIPTION },
347     { "accessibilityTitle",
348       IDS_OPTIONS_SETTINGS_SECTION_TITLE_ACCESSIBILITY },
349     { "accessibilityVirtualKeyboard",
350       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_VIRTUAL_KEYBOARD_DESCRIPTION },
351     { "accessibilityAlwaysShowMenu",
352       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SHOULD_ALWAYS_SHOW_MENU },
353     { "accessibilityAutoclick",
354       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DESCRIPTION },
355     { "accessibilityAutoclickDropdown",
356       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DROPDOWN_DESCRIPTION },
357     { "autoclickDelayExtremelyShort",
358       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DELAY_EXTREMELY_SHORT },
359     { "autoclickDelayVeryShort",
360       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DELAY_VERY_SHORT },
361     { "autoclickDelayShort",
362       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DELAY_SHORT },
363     { "autoclickDelayLong",
364       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DELAY_LONG },
365     { "autoclickDelayVeryLong",
366       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_AUTOCLICK_DELAY_VERY_LONG },
367     { "enableContentProtectionAttestation",
368       IDS_OPTIONS_ENABLE_CONTENT_PROTECTION_ATTESTATION },
369     { "factoryResetHeading", IDS_OPTIONS_FACTORY_RESET_HEADING },
370     { "factoryResetTitle", IDS_OPTIONS_FACTORY_RESET },
371     { "factoryResetRestart", IDS_OPTIONS_FACTORY_RESET_BUTTON },
372     { "factoryResetDataRestart", IDS_RELAUNCH_BUTTON },
373     { "factoryResetWarning", IDS_OPTIONS_FACTORY_RESET_WARNING },
374     { "factoryResetHelpUrl", IDS_FACTORY_RESET_HELP_URL },
375     { "changePicture", IDS_OPTIONS_CHANGE_PICTURE },
376     { "changePictureCaption", IDS_OPTIONS_CHANGE_PICTURE_CAPTION },
377     { "datetimeTitle", IDS_OPTIONS_SETTINGS_SECTION_TITLE_DATETIME },
378     { "deviceGroupDescription", IDS_OPTIONS_DEVICE_GROUP_DESCRIPTION },
379     { "deviceGroupPointer", IDS_OPTIONS_DEVICE_GROUP_POINTER_SECTION },
380     { "mouseSpeed", IDS_OPTIONS_SETTINGS_MOUSE_SPEED_DESCRIPTION },
381     { "touchpadSpeed", IDS_OPTIONS_SETTINGS_TOUCHPAD_SPEED_DESCRIPTION },
382     { "enableScreenlock", IDS_OPTIONS_ENABLE_SCREENLOCKER_CHECKBOX },
383     { "internetOptionsButtonTitle", IDS_OPTIONS_INTERNET_OPTIONS_BUTTON_TITLE },
384     { "keyboardSettingsButtonTitle",
385       IDS_OPTIONS_DEVICE_GROUP_KEYBOARD_SETTINGS_BUTTON_TITLE },
386     { "manageAccountsButtonTitle", IDS_OPTIONS_ACCOUNTS_BUTTON_TITLE },
387     { "noPointingDevices", IDS_OPTIONS_NO_POINTING_DEVICES },
388     { "sectionTitleDevice", IDS_OPTIONS_DEVICE_GROUP_NAME },
389     { "sectionTitleInternet", IDS_OPTIONS_INTERNET_OPTIONS_GROUP_LABEL },
390     { "syncOverview", IDS_SYNC_OVERVIEW },
391     { "syncButtonTextStart", IDS_SYNC_SETUP_BUTTON_LABEL },
392     { "timezone", IDS_OPTIONS_SETTINGS_TIMEZONE_DESCRIPTION },
393     { "use24HourClock", IDS_OPTIONS_SETTINGS_USE_24HOUR_CLOCK_DESCRIPTION },
394 #else
395     { "cloudPrintManageButton",
396       IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_ENABLED_MANAGE_BUTTON},
397     { "cloudPrintConnectorEnablingButton",
398       IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_ENABLING_BUTTON },
399     { "proxiesConfigureButton", IDS_OPTIONS_PROXIES_CONFIGURE_BUTTON },
400 #endif
401 #if defined(OS_CHROMEOS) && defined(USE_ASH)
402     { "setWallpaper", IDS_SET_WALLPAPER_BUTTON },
403 #endif
404     { "advancedSectionTitleSystem",
405       IDS_OPTIONS_ADVANCED_SECTION_TITLE_SYSTEM },
406 #if !defined(OS_MACOSX) && !defined(OS_CHROMEOS)
407     { "backgroundModeCheckbox", IDS_OPTIONS_SYSTEM_ENABLE_BACKGROUND_MODE },
408 #endif
409 #if !defined(OS_CHROMEOS)
410     { "gpuModeCheckbox",
411       IDS_OPTIONS_SYSTEM_ENABLE_HARDWARE_ACCELERATION_MODE },
412     { "gpuModeResetRestart",
413       IDS_OPTIONS_SYSTEM_ENABLE_HARDWARE_ACCELERATION_MODE_RESTART },
414     // Strings with product-name substitutions.
415     { "syncOverview", IDS_SYNC_OVERVIEW, IDS_PRODUCT_NAME },
416     { "syncButtonTextStart", IDS_SYNC_SETUP_BUTTON_LABEL },
417 #endif
418     { "syncButtonTextSignIn", IDS_SYNC_START_SYNC_BUTTON_LABEL,
419       IDS_SHORT_PRODUCT_NAME },
420     { "profilesSingleUser", IDS_PROFILES_SINGLE_USER_MESSAGE,
421       IDS_PRODUCT_NAME },
422     { "defaultBrowserUnknown", IDS_OPTIONS_DEFAULTBROWSER_UNKNOWN,
423       IDS_PRODUCT_NAME },
424     { "defaultBrowserUseAsDefault", IDS_OPTIONS_DEFAULTBROWSER_USEASDEFAULT },
425     { "autoLaunchText", IDS_AUTOLAUNCH_TEXT },
426 #if defined(OS_CHROMEOS)
427     { "factoryResetDescription", IDS_OPTIONS_FACTORY_RESET_DESCRIPTION,
428       IDS_SHORT_PRODUCT_NAME },
429 #endif
430     { "languageSectionLabel", IDS_OPTIONS_ADVANCED_LANGUAGE_LABEL,
431       IDS_SHORT_PRODUCT_NAME },
432 #if defined(ENABLE_MDNS)
433     { "cloudPrintDevicesPageButton", IDS_LOCAL_DISCOVERY_DEVICES_PAGE_BUTTON },
434     { "cloudPrintEnableNotificationsLabel",
435       IDS_LOCAL_DISCOVERY_NOTIFICATIONS_ENABLE_CHECKBOX_LABEL },
436 #endif
437   };
438
439 #if defined(ENABLE_SETTINGS_APP)
440   static OptionsStringResource app_resources[] = {
441     { "syncOverview", IDS_SETTINGS_APP_SYNC_OVERVIEW },
442     { "syncButtonTextStart", IDS_SYNC_START_SYNC_BUTTON_LABEL,
443       IDS_SETTINGS_APP_LAUNCHER_PRODUCT_NAME },
444     { "profilesSingleUser", IDS_PROFILES_SINGLE_USER_MESSAGE,
445       IDS_SETTINGS_APP_LAUNCHER_PRODUCT_NAME },
446     { "languageSectionLabel", IDS_OPTIONS_ADVANCED_LANGUAGE_LABEL,
447       IDS_SETTINGS_APP_LAUNCHER_PRODUCT_NAME },
448     { "proxiesLabelSystem", IDS_OPTIONS_SYSTEM_PROXIES_LABEL,
449       IDS_SETTINGS_APP_LAUNCHER_PRODUCT_NAME },
450   };
451   base::DictionaryValue* app_values = NULL;
452   CHECK(values->GetDictionary(kSettingsAppKey, &app_values));
453   RegisterStrings(app_values, app_resources, arraysize(app_resources));
454 #endif
455
456   RegisterStrings(values, resources, arraysize(resources));
457   RegisterTitle(values, "doNotTrackConfirmOverlay",
458                 IDS_OPTIONS_ENABLE_DO_NOT_TRACK_BUBBLE_TITLE);
459   RegisterTitle(values, "spellingConfirmOverlay",
460                 IDS_CONTENT_CONTEXT_SPELLING_ASK_GOOGLE);
461 #if defined(ENABLE_FULL_PRINTING)
462   RegisterCloudPrintValues(values);
463 #endif
464
465   values->SetString("syncLearnMoreURL", chrome::kSyncLearnMoreURL);
466   base::string16 omnibox_url = base::ASCIIToUTF16(chrome::kOmniboxLearnMoreURL);
467   values->SetString(
468       "defaultSearchGroupLabel",
469       l10n_util::GetStringFUTF16(IDS_SEARCH_PREF_EXPLANATION, omnibox_url));
470   values->SetString("hotwordLearnMoreURL", chrome::kHotwordLearnMoreURL);
471   RegisterTitle(values, "hotwordConfirmOverlay",
472                 IDS_HOTWORD_SEARCH_PREF_CHKBOX);
473
474 #if defined(OS_CHROMEOS)
475   Profile* profile = Profile::FromWebUI(web_ui());
476   std::string username = profile->GetProfileName();
477   if (username.empty()) {
478     chromeos::User* user =
479         chromeos::UserManager::Get()->GetUserByProfile(profile);
480     if (user && (user->GetType() != chromeos::User::USER_TYPE_GUEST))
481       username = user->email();
482
483   }
484   if (!username.empty())
485     username = gaia::SanitizeEmail(gaia::CanonicalizeEmail(username));
486
487   values->SetString("username", username);
488 #endif
489
490   // Pass along sync status early so it will be available during page init.
491   values->Set("syncData", GetSyncStateDictionary().release());
492
493   // The Reset Profile Settings feature makes no sense for an off-the-record
494   // profile (e.g. in Guest mode on Chrome OS), so hide it.
495   values->SetBoolean("enableResetProfileSettings",
496                      !Profile::FromWebUI(web_ui())->IsOffTheRecord());
497
498   values->SetString("privacyLearnMoreURL", chrome::kPrivacyLearnMoreURL);
499   values->SetString("doNotTrackLearnMoreURL", chrome::kDoNotTrackLearnMoreURL);
500
501 #if defined(OS_CHROMEOS)
502   // TODO(pastarmovj): replace this with a call to the CrosSettings list
503   // handling functionality to come.
504   values->Set("timezoneList", chromeos::system::GetTimezoneList().release());
505
506   values->SetString("accessibilityLearnMoreURL",
507                     chrome::kChromeAccessibilityHelpURL);
508
509   std::string settings_url = std::string("chrome-extension://") +
510       extension_misc::kChromeVoxExtensionId +
511       chrome::kChromeAccessibilitySettingsURL;
512
513   values->SetString("accessibilitySettingsURL",
514                     settings_url);
515
516   values->SetString("contentProtectionAttestationLearnMoreURL",
517                     chrome::kAttestationForContentProtectionLearnMoreURL);
518
519   // Creates magnifierList.
520   scoped_ptr<base::ListValue> magnifier_list(new base::ListValue);
521
522   scoped_ptr<base::ListValue> option_full(new base::ListValue);
523   option_full->AppendInteger(ash::MAGNIFIER_FULL);
524   option_full->AppendString(l10n_util::GetStringUTF16(
525       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SCREEN_MAGNIFIER_FULL));
526   magnifier_list->Append(option_full.release());
527
528   scoped_ptr<base::ListValue> option_partial(new base::ListValue);
529   option_partial->AppendInteger(ash::MAGNIFIER_PARTIAL);
530   option_partial->Append(new base::StringValue(l10n_util::GetStringUTF16(
531       IDS_OPTIONS_SETTINGS_ACCESSIBILITY_SCREEN_MAGNIFIER_PARTIAL)));
532   magnifier_list->Append(option_partial.release());
533
534   values->Set("magnifierList", magnifier_list.release());
535 #endif
536
537 #if defined(OS_MACOSX)
538   values->SetString("macPasswordsWarning",
539       l10n_util::GetStringUTF16(IDS_OPTIONS_PASSWORDS_MAC_WARNING));
540   values->SetBoolean("multiple_profiles",
541       g_browser_process->profile_manager()->GetNumberOfProfiles() > 1);
542 #endif
543
544   if (ShouldShowMultiProfilesUserList())
545     values->Set("profilesInfo", GetProfilesInfoList().release());
546
547   values->SetBoolean("profileIsManaged",
548                      Profile::FromWebUI(web_ui())->IsManaged());
549
550 #if !defined(OS_CHROMEOS)
551   values->SetBoolean(
552       "gpuEnabledAtStart",
553       g_browser_process->gpu_mode_manager()->initial_gpu_mode_pref());
554 #endif
555
556 #if defined(ENABLE_MDNS)
557   values->SetBoolean("cloudPrintHideNotificationsCheckbox",
558                      !local_discovery::PrivetNotificationService::IsEnabled());
559 #endif
560
561   values->SetBoolean("cloudPrintShowMDnsOptions",
562                      cloud_print_mdns_ui_enabled_);
563
564   values->SetString("cloudPrintLearnMoreURL", chrome::kCloudPrintLearnMoreURL);
565
566   values->SetString("languagesLearnMoreURL",
567                     chrome::kLanguageSettingsLearnMoreUrl);
568 }
569
570 #if defined(ENABLE_FULL_PRINTING)
571 void BrowserOptionsHandler::RegisterCloudPrintValues(
572     base::DictionaryValue* values) {
573   values->SetString("cloudPrintOptionLabel",
574                     l10n_util::GetStringFUTF16(
575                         IDS_CLOUD_PRINT_CHROMEOS_OPTION_LABEL,
576                         l10n_util::GetStringUTF16(IDS_GOOGLE_CLOUD_PRINT)));
577
578 #if defined(OS_CHROMEOS)
579   values->SetString("cloudPrintManageButton",
580       l10n_util::GetStringFUTF16(
581       IDS_CLOUD_PRINT_CHROMEOS_OPTION_BUTTON,
582       l10n_util::GetStringUTF16(IDS_GOOGLE_CLOUD_PRINT)));
583 #else
584   // TODO(noamsml): Remove all cloud print connector related code from the
585   // settings page as soon as the devices page is supported on all platforms.
586   values->SetString("cloudPrintConnectorDisabledLabel",
587       l10n_util::GetStringFUTF16(
588       IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_DISABLED_LABEL,
589       l10n_util::GetStringUTF16(IDS_GOOGLE_CLOUD_PRINT)));
590   values->SetString("cloudPrintConnectorDisabledButton",
591       l10n_util::GetStringUTF16(
592       IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_DISABLED_BUTTON));
593   values->SetString("cloudPrintConnectorEnabledButton",
594       l10n_util::GetStringUTF16(
595       IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_ENABLED_BUTTON));
596 #endif
597
598   values->SetBoolean("showSetDefault", ShouldShowSetDefaultBrowser());
599 }
600 #endif  // defined(ENABLE_FULL_PRINTING)
601
602 void BrowserOptionsHandler::RegisterMessages() {
603   web_ui()->RegisterMessageCallback(
604       "becomeDefaultBrowser",
605       base::Bind(&BrowserOptionsHandler::BecomeDefaultBrowser,
606                  base::Unretained(this)));
607   web_ui()->RegisterMessageCallback(
608       "setDefaultSearchEngine",
609       base::Bind(&BrowserOptionsHandler::SetDefaultSearchEngine,
610                  base::Unretained(this)));
611   web_ui()->RegisterMessageCallback(
612       "deleteProfile",
613       base::Bind(&BrowserOptionsHandler::DeleteProfile,
614                  base::Unretained(this)));
615   web_ui()->RegisterMessageCallback(
616       "themesReset",
617       base::Bind(&BrowserOptionsHandler::ThemesReset,
618                  base::Unretained(this)));
619   web_ui()->RegisterMessageCallback(
620       "requestProfilesInfo",
621       base::Bind(&BrowserOptionsHandler::HandleRequestProfilesInfo,
622                  base::Unretained(this)));
623 #if defined(OS_LINUX) && !defined(OS_CHROMEOS)
624   web_ui()->RegisterMessageCallback(
625       "themesSetNative",
626       base::Bind(&BrowserOptionsHandler::ThemesSetNative,
627                  base::Unretained(this)));
628 #endif
629   web_ui()->RegisterMessageCallback(
630       "selectDownloadLocation",
631       base::Bind(&BrowserOptionsHandler::HandleSelectDownloadLocation,
632                  base::Unretained(this)));
633   web_ui()->RegisterMessageCallback(
634       "autoOpenFileTypesAction",
635       base::Bind(&BrowserOptionsHandler::HandleAutoOpenButton,
636                  base::Unretained(this)));
637   web_ui()->RegisterMessageCallback(
638       "defaultFontSizeAction",
639       base::Bind(&BrowserOptionsHandler::HandleDefaultFontSize,
640                  base::Unretained(this)));
641   web_ui()->RegisterMessageCallback(
642       "defaultZoomFactorAction",
643       base::Bind(&BrowserOptionsHandler::HandleDefaultZoomFactor,
644                  base::Unretained(this)));
645 #if !defined(USE_NSS) && !defined(USE_OPENSSL)
646   web_ui()->RegisterMessageCallback(
647       "showManageSSLCertificates",
648       base::Bind(&BrowserOptionsHandler::ShowManageSSLCertificates,
649                  base::Unretained(this)));
650 #endif
651 #if defined(ENABLE_FULL_PRINTING)
652   web_ui()->RegisterMessageCallback(
653       "showCloudPrintManagePage",
654       base::Bind(&BrowserOptionsHandler::ShowCloudPrintManagePage,
655                  base::Unretained(this)));
656 #endif
657 #if defined(OS_CHROMEOS)
658   web_ui()->RegisterMessageCallback(
659       "openWallpaperManager",
660       base::Bind(&BrowserOptionsHandler::HandleOpenWallpaperManager,
661                  base::Unretained(this)));
662   web_ui()->RegisterMessageCallback(
663       "virtualKeyboardChange",
664       base::Bind(&BrowserOptionsHandler::VirtualKeyboardChangeCallback,
665                  base::Unretained(this)));
666   web_ui()->RegisterMessageCallback(
667       "performFactoryResetRestart",
668       base::Bind(&BrowserOptionsHandler::PerformFactoryResetRestart,
669                  base::Unretained(this)));
670 #else
671   web_ui()->RegisterMessageCallback(
672       "restartBrowser",
673       base::Bind(&BrowserOptionsHandler::HandleRestartBrowser,
674                  base::Unretained(this)));
675 #if defined(ENABLE_FULL_PRINTING)
676   if (cloud_print_connector_ui_enabled_) {
677     web_ui()->RegisterMessageCallback(
678         "showCloudPrintSetupDialog",
679         base::Bind(&BrowserOptionsHandler::ShowCloudPrintSetupDialog,
680                    base::Unretained(this)));
681     web_ui()->RegisterMessageCallback(
682         "disableCloudPrintConnector",
683         base::Bind(&BrowserOptionsHandler::HandleDisableCloudPrintConnector,
684                    base::Unretained(this)));
685   }
686 #endif  // defined(ENABLE_FULL_PRINTING)
687   web_ui()->RegisterMessageCallback(
688       "showNetworkProxySettings",
689       base::Bind(&BrowserOptionsHandler::ShowNetworkProxySettings,
690                  base::Unretained(this)));
691 #endif  // defined(OS_CHROMEOS)
692
693 #if defined(ENABLE_MDNS)
694   if (cloud_print_mdns_ui_enabled_) {
695     web_ui()->RegisterMessageCallback(
696         "showCloudPrintDevicesPage",
697         base::Bind(&BrowserOptionsHandler::ShowCloudPrintDevicesPage,
698                    base::Unretained(this)));
699   }
700 #endif
701   web_ui()->RegisterMessageCallback(
702       "requestHotwordAvailable",
703       base::Bind(&BrowserOptionsHandler::HandleRequestHotwordAvailable,
704                  base::Unretained(this)));
705 }
706
707 void BrowserOptionsHandler::Uninitialize() {
708   registrar_.RemoveAll();
709 }
710
711 void BrowserOptionsHandler::OnStateChanged() {
712   UpdateSyncState();
713 }
714
715 void BrowserOptionsHandler::PageLoadStarted() {
716   page_initialized_ = false;
717 }
718
719 void BrowserOptionsHandler::InitializeHandler() {
720   Profile* profile = Profile::FromWebUI(web_ui());
721   PrefService* prefs = profile->GetPrefs();
722
723   ProfileSyncService* sync_service(
724       ProfileSyncServiceFactory::GetInstance()->GetForProfile(profile));
725   if (sync_service)
726     sync_service->AddObserver(this);
727
728   // Create our favicon data source.
729   content::URLDataSource::Add(
730       profile, new FaviconSource(profile, FaviconSource::FAVICON));
731
732   default_browser_policy_.Init(
733       prefs::kDefaultBrowserSettingEnabled,
734       g_browser_process->local_state(),
735       base::Bind(&BrowserOptionsHandler::UpdateDefaultBrowserState,
736                  base::Unretained(this)));
737
738   registrar_.Add(this, chrome::NOTIFICATION_PROFILE_CACHED_INFO_CHANGED,
739                  content::NotificationService::AllSources());
740 #if defined(OS_CHROMEOS)
741   registrar_.Add(this, chrome::NOTIFICATION_LOGIN_USER_IMAGE_CHANGED,
742                  content::NotificationService::AllSources());
743 #endif
744   registrar_.Add(this, chrome::NOTIFICATION_BROWSER_THEME_CHANGED,
745                  content::Source<ThemeService>(
746                      ThemeServiceFactory::GetForProfile(profile)));
747   registrar_.Add(this, chrome::NOTIFICATION_GLOBAL_ERRORS_CHANGED,
748                  content::Source<Profile>(profile));
749   registrar_.Add(this, chrome::NOTIFICATION_GOOGLE_SIGNIN_SUCCESSFUL,
750                  content::Source<Profile>(profile));
751   registrar_.Add(this, chrome::NOTIFICATION_GOOGLE_SIGNED_OUT,
752                  content::Source<Profile>(profile));
753   AddTemplateUrlServiceObserver();
754
755 #if defined(OS_WIN)
756   const CommandLine& command_line = *CommandLine::ForCurrentProcess();
757   if (!command_line.HasSwitch(switches::kUserDataDir)) {
758     BrowserThread::PostTask(BrowserThread::FILE, FROM_HERE,
759         base::Bind(&BrowserOptionsHandler::CheckAutoLaunch,
760                    weak_ptr_factory_.GetWeakPtr(),
761                    profile->GetPath()));
762   }
763 #endif
764
765 #if defined(ENABLE_FULL_PRINTING) && !defined(OS_CHROMEOS)
766   base::Closure cloud_print_callback = base::Bind(
767       &BrowserOptionsHandler::OnCloudPrintPrefsChanged, base::Unretained(this));
768   cloud_print_connector_email_.Init(
769       prefs::kCloudPrintEmail, prefs, cloud_print_callback);
770   cloud_print_connector_enabled_.Init(
771       prefs::kCloudPrintProxyEnabled, prefs, cloud_print_callback);
772 #endif
773
774   auto_open_files_.Init(
775       prefs::kDownloadExtensionsToOpen, prefs,
776       base::Bind(&BrowserOptionsHandler::SetupAutoOpenFileTypes,
777                  base::Unretained(this)));
778   default_zoom_level_.Init(
779       prefs::kDefaultZoomLevel, prefs,
780       base::Bind(&BrowserOptionsHandler::SetupPageZoomSelector,
781                  base::Unretained(this)));
782   profile_pref_registrar_.Init(prefs);
783   profile_pref_registrar_.Add(
784       prefs::kWebKitDefaultFontSize,
785       base::Bind(&BrowserOptionsHandler::SetupFontSizeSelector,
786                  base::Unretained(this)));
787   profile_pref_registrar_.Add(
788       prefs::kWebKitDefaultFixedFontSize,
789       base::Bind(&BrowserOptionsHandler::SetupFontSizeSelector,
790                  base::Unretained(this)));
791   profile_pref_registrar_.Add(
792       prefs::kManagedUsers,
793       base::Bind(&BrowserOptionsHandler::SetupManagingSupervisedUsers,
794                  base::Unretained(this)));
795   profile_pref_registrar_.Add(
796       prefs::kSigninAllowed,
797       base::Bind(&BrowserOptionsHandler::OnSigninAllowedPrefChange,
798                  base::Unretained(this)));
799
800 #if defined(OS_CHROMEOS)
801   if (!policy_registrar_) {
802     policy_registrar_.reset(new policy::PolicyChangeRegistrar(
803         policy::ProfilePolicyConnectorFactory::GetForProfile(profile)->
804             policy_service(),
805         policy::PolicyNamespace(policy::POLICY_DOMAIN_CHROME, std::string())));
806     policy_registrar_->Observe(
807         policy::key::kUserAvatarImage,
808         base::Bind(&BrowserOptionsHandler::OnUserImagePolicyChanged,
809                    base::Unretained(this)));
810   }
811 #else  // !defined(OS_CHROMEOS)
812   profile_pref_registrar_.Add(
813       prefs::kProxy,
814       base::Bind(&BrowserOptionsHandler::SetupProxySettingsSection,
815                  base::Unretained(this)));
816 #endif  // !defined(OS_CHROMEOS)
817 }
818
819 void BrowserOptionsHandler::InitializePage() {
820   page_initialized_ = true;
821
822   OnTemplateURLServiceChanged();
823
824   ObserveThemeChanged();
825   OnStateChanged();
826   UpdateDefaultBrowserState();
827
828   SetupMetricsReportingSettingVisibility();
829   SetupFontSizeSelector();
830   SetupPageZoomSelector();
831   SetupAutoOpenFileTypes();
832   SetupProxySettingsSection();
833   SetupManageCertificatesSection();
834   SetupManagingSupervisedUsers();
835
836 #if defined(ENABLE_FULL_PRINTING) && !defined(OS_CHROMEOS)
837   if (!cloud_print_mdns_ui_enabled_) {
838     if (cloud_print_connector_ui_enabled_) {
839       SetupCloudPrintConnectorSection();
840       RefreshCloudPrintStatusFromService();
841     } else {
842       RemoveCloudPrintConnectorSection();
843     }
844   }
845 #endif
846
847 #if defined(OS_CHROMEOS)
848   SetupAccessibilityFeatures();
849   policy::BrowserPolicyConnectorChromeOS* connector =
850       g_browser_process->platform_part()->browser_policy_connector_chromeos();
851   if (!connector->IsEnterpriseManaged() &&
852       !chromeos::UserManager::Get()->IsLoggedInAsGuest() &&
853       !chromeos::UserManager::Get()->IsLoggedInAsLocallyManagedUser()) {
854     web_ui()->CallJavascriptFunction(
855         "BrowserOptions.enableFactoryResetSection");
856   }
857
858   Profile* profile = Profile::FromWebUI(web_ui());
859   OnAccountPictureManagedChanged(
860       policy::ProfilePolicyConnectorFactory::GetForProfile(profile)->
861           policy_service()->GetPolicies(
862               policy::PolicyNamespace(policy::POLICY_DOMAIN_CHROME,
863                                       std::string()))
864              .Get(policy::key::kUserAvatarImage));
865 #endif
866 }
867
868 // static
869 void BrowserOptionsHandler::CheckAutoLaunch(
870     base::WeakPtr<BrowserOptionsHandler> weak_this,
871     const base::FilePath& profile_path) {
872 #if defined(OS_WIN)
873   DCHECK(BrowserThread::CurrentlyOn(BrowserThread::FILE));
874
875   // Auto-launch is not supported for secondary profiles yet.
876   if (profile_path.BaseName().value() !=
877           base::ASCIIToUTF16(chrome::kInitialProfile)) {
878     return;
879   }
880
881   // Pass in weak pointer to this to avoid race if BrowserOptionsHandler is
882   // deleted.
883   BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
884       base::Bind(&BrowserOptionsHandler::CheckAutoLaunchCallback,
885                  weak_this,
886                  auto_launch_trial::IsInAutoLaunchGroup(),
887                  auto_launch_util::AutoStartRequested(
888                      profile_path.BaseName().value(),
889                      true,  // Window requested.
890                      base::FilePath())));
891 #endif
892 }
893
894 void BrowserOptionsHandler::CheckAutoLaunchCallback(
895     bool is_in_auto_launch_group,
896     bool will_launch_at_login) {
897 #if defined(OS_WIN)
898   DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
899
900   if (is_in_auto_launch_group) {
901     web_ui()->RegisterMessageCallback("toggleAutoLaunch",
902         base::Bind(&BrowserOptionsHandler::ToggleAutoLaunch,
903         base::Unretained(this)));
904
905     base::FundamentalValue enabled(will_launch_at_login);
906     web_ui()->CallJavascriptFunction("BrowserOptions.updateAutoLaunchState",
907                                      enabled);
908   }
909 #endif
910 }
911
912 bool BrowserOptionsHandler::ShouldShowSetDefaultBrowser() {
913 #if defined(OS_CHROMEOS)
914   // We're always the default browser on ChromeOS.
915   return false;
916 #else
917   Profile* profile = Profile::FromWebUI(web_ui());
918   return !profile->IsGuestSession();
919 #endif
920 }
921
922 bool BrowserOptionsHandler::ShouldShowMultiProfilesUserList() {
923 #if defined(OS_CHROMEOS)
924   // On Chrome OS we use different UI for multi-profiles.
925   return false;
926 #else
927   if (helper::GetDesktopType(web_ui()) != chrome::HOST_DESKTOP_TYPE_NATIVE)
928     return false;
929   Profile* profile = Profile::FromWebUI(web_ui());
930   if (profile->IsGuestSession())
931     return false;
932   return profiles::IsMultipleProfilesEnabled();
933 #endif
934 }
935
936 void BrowserOptionsHandler::UpdateDefaultBrowserState() {
937 #if defined(OS_MACOSX)
938   ShellIntegration::DefaultWebClientState state =
939       ShellIntegration::GetDefaultBrowser();
940   int status_string_id;
941   if (state == ShellIntegration::IS_DEFAULT)
942     status_string_id = IDS_OPTIONS_DEFAULTBROWSER_DEFAULT;
943   else if (state == ShellIntegration::NOT_DEFAULT)
944     status_string_id = IDS_OPTIONS_DEFAULTBROWSER_NOTDEFAULT;
945   else
946     status_string_id = IDS_OPTIONS_DEFAULTBROWSER_UNKNOWN;
947
948   SetDefaultBrowserUIString(status_string_id);
949 #else
950   default_browser_worker_->StartCheckIsDefault();
951 #endif
952 }
953
954 void BrowserOptionsHandler::BecomeDefaultBrowser(const base::ListValue* args) {
955   // If the default browser setting is managed then we should not be able to
956   // call this function.
957   if (default_browser_policy_.IsManaged())
958     return;
959
960   content::RecordAction(UserMetricsAction("Options_SetAsDefaultBrowser"));
961 #if defined(OS_MACOSX)
962   if (ShellIntegration::SetAsDefaultBrowser())
963     UpdateDefaultBrowserState();
964 #else
965   default_browser_worker_->StartSetAsDefault();
966   // Callback takes care of updating UI.
967 #endif
968
969   // If the user attempted to make Chrome the default browser, then he/she
970   // arguably wants to be notified when that changes.
971   PrefService* prefs = Profile::FromWebUI(web_ui())->GetPrefs();
972   prefs->SetBoolean(prefs::kCheckDefaultBrowser, true);
973 }
974
975 int BrowserOptionsHandler::StatusStringIdForState(
976     ShellIntegration::DefaultWebClientState state) {
977   if (state == ShellIntegration::IS_DEFAULT)
978     return IDS_OPTIONS_DEFAULTBROWSER_DEFAULT;
979   if (state == ShellIntegration::NOT_DEFAULT)
980     return IDS_OPTIONS_DEFAULTBROWSER_NOTDEFAULT;
981   return IDS_OPTIONS_DEFAULTBROWSER_UNKNOWN;
982 }
983
984 void BrowserOptionsHandler::SetDefaultWebClientUIState(
985     ShellIntegration::DefaultWebClientUIState state) {
986   int status_string_id;
987
988   if (state == ShellIntegration::STATE_IS_DEFAULT) {
989     status_string_id = IDS_OPTIONS_DEFAULTBROWSER_DEFAULT;
990   } else if (state == ShellIntegration::STATE_NOT_DEFAULT) {
991     if (ShellIntegration::CanSetAsDefaultBrowser() ==
992             ShellIntegration::SET_DEFAULT_NOT_ALLOWED) {
993       status_string_id = IDS_OPTIONS_DEFAULTBROWSER_SXS;
994     } else {
995       status_string_id = IDS_OPTIONS_DEFAULTBROWSER_NOTDEFAULT;
996     }
997   } else if (state == ShellIntegration::STATE_UNKNOWN) {
998     status_string_id = IDS_OPTIONS_DEFAULTBROWSER_UNKNOWN;
999   } else {
1000     return;  // Still processing.
1001   }
1002
1003   SetDefaultBrowserUIString(status_string_id);
1004 }
1005
1006 bool BrowserOptionsHandler::IsInteractiveSetDefaultPermitted() {
1007   return true;  // This is UI so we can allow it.
1008 }
1009
1010 void BrowserOptionsHandler::SetDefaultBrowserUIString(int status_string_id) {
1011   base::StringValue status_string(
1012       l10n_util::GetStringFUTF16(status_string_id,
1013                                  l10n_util::GetStringUTF16(IDS_PRODUCT_NAME)));
1014
1015   base::FundamentalValue is_default(
1016       status_string_id == IDS_OPTIONS_DEFAULTBROWSER_DEFAULT);
1017
1018   base::FundamentalValue can_be_default(
1019       !default_browser_policy_.IsManaged() &&
1020       (status_string_id == IDS_OPTIONS_DEFAULTBROWSER_DEFAULT ||
1021        status_string_id == IDS_OPTIONS_DEFAULTBROWSER_NOTDEFAULT));
1022
1023   web_ui()->CallJavascriptFunction(
1024       "BrowserOptions.updateDefaultBrowserState",
1025       status_string, is_default, can_be_default);
1026 }
1027
1028 void BrowserOptionsHandler::OnTemplateURLServiceChanged() {
1029   if (!template_url_service_ || !template_url_service_->loaded())
1030     return;
1031
1032   const TemplateURL* default_url =
1033       template_url_service_->GetDefaultSearchProvider();
1034
1035   int default_index = -1;
1036   base::ListValue search_engines;
1037   TemplateURLService::TemplateURLVector model_urls(
1038       template_url_service_->GetTemplateURLs());
1039   for (size_t i = 0; i < model_urls.size(); ++i) {
1040     if (!model_urls[i]->ShowInDefaultList())
1041       continue;
1042
1043     base::DictionaryValue* entry = new base::DictionaryValue();
1044     entry->SetString("name", model_urls[i]->short_name());
1045     entry->SetInteger("index", i);
1046     search_engines.Append(entry);
1047     if (model_urls[i] == default_url)
1048       default_index = i;
1049   }
1050
1051   web_ui()->CallJavascriptFunction(
1052       "BrowserOptions.updateSearchEngines",
1053       search_engines,
1054       base::FundamentalValue(default_index),
1055       base::FundamentalValue(
1056           template_url_service_->is_default_search_managed() ||
1057           template_url_service_->IsExtensionControlledDefaultSearch()));
1058 }
1059
1060 void BrowserOptionsHandler::SetDefaultSearchEngine(
1061     const base::ListValue* args) {
1062   int selected_index = -1;
1063   if (!ExtractIntegerValue(args, &selected_index)) {
1064     NOTREACHED();
1065     return;
1066   }
1067
1068   TemplateURLService::TemplateURLVector model_urls(
1069       template_url_service_->GetTemplateURLs());
1070   if (selected_index >= 0 &&
1071       selected_index < static_cast<int>(model_urls.size()))
1072     template_url_service_->SetDefaultSearchProvider(model_urls[selected_index]);
1073
1074   content::RecordAction(UserMetricsAction("Options_SearchEngineChanged"));
1075 }
1076
1077 void BrowserOptionsHandler::AddTemplateUrlServiceObserver() {
1078   template_url_service_ =
1079       TemplateURLServiceFactory::GetForProfile(Profile::FromWebUI(web_ui()));
1080   if (template_url_service_) {
1081     template_url_service_->Load();
1082     template_url_service_->AddObserver(this);
1083   }
1084 }
1085
1086 void BrowserOptionsHandler::Observe(
1087     int type,
1088     const content::NotificationSource& source,
1089     const content::NotificationDetails& details) {
1090   // Notifications are used to update the UI dynamically when settings change in
1091   // the background. If the UI is currently being loaded, no dynamic updates are
1092   // possible (as the DOM and JS are not fully loaded) or necessary (as
1093   // InitializePage() will update the UI at the end of the load).
1094   if (!page_initialized_)
1095     return;
1096
1097   switch (type) {
1098     case chrome::NOTIFICATION_BROWSER_THEME_CHANGED:
1099       ObserveThemeChanged();
1100       break;
1101 #if defined(OS_CHROMEOS)
1102     case chrome::NOTIFICATION_LOGIN_USER_IMAGE_CHANGED:
1103       UpdateAccountPicture();
1104       break;
1105 #endif
1106     case chrome::NOTIFICATION_PROFILE_CACHED_INFO_CHANGED:
1107     SendProfilesInfo();
1108       break;
1109     case chrome::NOTIFICATION_GLOBAL_ERRORS_CHANGED:
1110     case chrome::NOTIFICATION_GOOGLE_SIGNIN_SUCCESSFUL:
1111     case chrome::NOTIFICATION_GOOGLE_SIGNED_OUT:
1112       // Update our sync/signin status display.
1113       OnStateChanged();
1114       break;
1115     default:
1116       NOTREACHED();
1117   }
1118 }
1119
1120 #if defined(ENABLE_FULL_PRINTING) && !defined(OS_CHROMEOS)
1121 void BrowserOptionsHandler::OnCloudPrintPrefsChanged() {
1122   if (cloud_print_connector_ui_enabled_)
1123     SetupCloudPrintConnectorSection();
1124 }
1125 #endif
1126
1127 void BrowserOptionsHandler::ToggleAutoLaunch(const base::ListValue* args) {
1128 #if defined(OS_WIN)
1129   if (!auto_launch_trial::IsInAutoLaunchGroup())
1130     return;
1131
1132   bool enable;
1133   CHECK_EQ(args->GetSize(), 1U);
1134   CHECK(args->GetBoolean(0, &enable));
1135
1136   Profile* profile = Profile::FromWebUI(web_ui());
1137   content::BrowserThread::PostTask(
1138       content::BrowserThread::FILE, FROM_HERE,
1139       enable ?
1140           base::Bind(&auto_launch_util::EnableForegroundStartAtLogin,
1141                      profile->GetPath().BaseName().value(), base::FilePath()) :
1142           base::Bind(&auto_launch_util::DisableForegroundStartAtLogin,
1143                       profile->GetPath().BaseName().value()));
1144 #endif  // OS_WIN
1145 }
1146
1147 scoped_ptr<base::ListValue> BrowserOptionsHandler::GetProfilesInfoList() {
1148   ProfileInfoCache& cache =
1149       g_browser_process->profile_manager()->GetProfileInfoCache();
1150   scoped_ptr<base::ListValue> profile_info_list(new base::ListValue);
1151   base::FilePath current_profile_path =
1152       web_ui()->GetWebContents()->GetBrowserContext()->GetPath();
1153
1154   for (size_t i = 0, e = cache.GetNumberOfProfiles(); i < e; ++i) {
1155     base::DictionaryValue* profile_value = new base::DictionaryValue();
1156     profile_value->SetString("name", cache.GetNameOfProfileAtIndex(i));
1157     base::FilePath profile_path = cache.GetPathOfProfileAtIndex(i);
1158     profile_value->Set("filePath", base::CreateFilePathValue(profile_path));
1159     profile_value->SetBoolean("isCurrentProfile",
1160                               profile_path == current_profile_path);
1161     profile_value->SetBoolean("isManaged", cache.ProfileIsManagedAtIndex(i));
1162
1163     bool is_gaia_picture =
1164         cache.IsUsingGAIAPictureOfProfileAtIndex(i) &&
1165         cache.GetGAIAPictureOfProfileAtIndex(i);
1166     if (is_gaia_picture) {
1167       gfx::Image icon = profiles::GetAvatarIconForWebUI(
1168           cache.GetAvatarIconOfProfileAtIndex(i), true);
1169       profile_value->SetString("iconURL",
1170           webui::GetBitmapDataUrl(icon.AsBitmap()));
1171     } else {
1172       size_t icon_index = cache.GetAvatarIconIndexOfProfileAtIndex(i);
1173       profile_value->SetString("iconURL",
1174                                cache.GetDefaultAvatarIconUrl(icon_index));
1175     }
1176
1177     profile_info_list->Append(profile_value);
1178   }
1179
1180   return profile_info_list.Pass();
1181 }
1182
1183 void BrowserOptionsHandler::SendProfilesInfo() {
1184   if (!ShouldShowMultiProfilesUserList())
1185     return;
1186   web_ui()->CallJavascriptFunction("BrowserOptions.setProfilesInfo",
1187                                    *GetProfilesInfoList());
1188 }
1189
1190 void BrowserOptionsHandler::DeleteProfile(const base::ListValue* args) {
1191   DCHECK(args);
1192   const base::Value* file_path_value;
1193   if (!args->Get(0, &file_path_value))
1194     return;
1195
1196   base::FilePath file_path;
1197   if (!base::GetValueAsFilePath(*file_path_value, &file_path))
1198     return;
1199   helper::DeleteProfileAtPath(file_path, web_ui());
1200 }
1201
1202 void BrowserOptionsHandler::ObserveThemeChanged() {
1203   Profile* profile = Profile::FromWebUI(web_ui());
1204   ThemeService* theme_service = ThemeServiceFactory::GetForProfile(profile);
1205   bool is_native_theme = false;
1206
1207 #if defined(OS_LINUX) && !defined(OS_CHROMEOS)
1208   bool profile_is_managed = profile->IsManaged();
1209   is_native_theme = theme_service->UsingNativeTheme();
1210   base::FundamentalValue native_theme_enabled(!is_native_theme &&
1211                                               !profile_is_managed);
1212   web_ui()->CallJavascriptFunction("BrowserOptions.setNativeThemeButtonEnabled",
1213                                    native_theme_enabled);
1214 #endif
1215
1216   bool is_classic_theme = !is_native_theme &&
1217                           theme_service->UsingDefaultTheme();
1218   base::FundamentalValue enabled(!is_classic_theme);
1219   web_ui()->CallJavascriptFunction("BrowserOptions.setThemesResetButtonEnabled",
1220                                    enabled);
1221 }
1222
1223 void BrowserOptionsHandler::ThemesReset(const base::ListValue* args) {
1224   Profile* profile = Profile::FromWebUI(web_ui());
1225   content::RecordAction(UserMetricsAction("Options_ThemesReset"));
1226   ThemeServiceFactory::GetForProfile(profile)->UseDefaultTheme();
1227 }
1228
1229 #if defined(OS_LINUX) && !defined(OS_CHROMEOS)
1230 void BrowserOptionsHandler::ThemesSetNative(const base::ListValue* args) {
1231   content::RecordAction(UserMetricsAction("Options_GtkThemeSet"));
1232   Profile* profile = Profile::FromWebUI(web_ui());
1233   ThemeServiceFactory::GetForProfile(profile)->SetNativeTheme();
1234 }
1235 #endif
1236
1237 #if defined(OS_CHROMEOS)
1238 void BrowserOptionsHandler::UpdateAccountPicture() {
1239   std::string email = chromeos::UserManager::Get()->GetLoggedInUser()->email();
1240   if (!email.empty()) {
1241     web_ui()->CallJavascriptFunction("BrowserOptions.updateAccountPicture");
1242     base::StringValue email_value(email);
1243     web_ui()->CallJavascriptFunction("BrowserOptions.updateAccountPicture",
1244                                      email_value);
1245   }
1246 }
1247
1248 void BrowserOptionsHandler::OnAccountPictureManagedChanged(bool managed) {
1249   web_ui()->CallJavascriptFunction("BrowserOptions.setAccountPictureManaged",
1250                                    base::FundamentalValue(managed));
1251 }
1252 #endif
1253
1254 scoped_ptr<base::DictionaryValue>
1255 BrowserOptionsHandler::GetSyncStateDictionary() {
1256   scoped_ptr<base::DictionaryValue> sync_status(new base::DictionaryValue);
1257   Profile* profile = Profile::FromWebUI(web_ui());
1258   if (profile->IsManaged()) {
1259     sync_status->SetBoolean("supervisedUser", true);
1260     sync_status->SetBoolean("signinAllowed", false);
1261     return sync_status.Pass();
1262   }
1263   if (profile->IsGuestSession()) {
1264     // Cannot display signin status when running in guest mode on chromeos
1265     // because there is no SigninManager.
1266     sync_status->SetBoolean("signinAllowed", false);
1267     return sync_status.Pass();
1268   }
1269   sync_status->SetBoolean("supervisedUser", false);
1270
1271   bool signout_prohibited = false;
1272 #if !defined(OS_CHROMEOS)
1273   // Signout is not allowed if the user has policy (crbug.com/172204).
1274   signout_prohibited =
1275       SigninManagerFactory::GetForProfile(profile)->IsSignoutProhibited();
1276 #endif
1277
1278   ProfileSyncService* service =
1279       ProfileSyncServiceFactory::GetInstance()->GetForProfile(profile);
1280   SigninManagerBase* signin = SigninManagerFactory::GetForProfile(profile);
1281   DCHECK(signin);
1282   sync_status->SetBoolean("signoutAllowed", !signout_prohibited);
1283   sync_status->SetBoolean("signinAllowed", signin->IsSigninAllowed());
1284   sync_status->SetBoolean("syncSystemEnabled", !!service);
1285   sync_status->SetBoolean("setupCompleted",
1286                           service && service->HasSyncSetupCompleted());
1287   sync_status->SetBoolean("setupInProgress",
1288       service && !service->IsManaged() && service->FirstSetupInProgress());
1289
1290   base::string16 status_label;
1291   base::string16 link_label;
1292   bool status_has_error = sync_ui_util::GetStatusLabels(
1293       service, *signin, sync_ui_util::WITH_HTML, &status_label, &link_label) ==
1294           sync_ui_util::SYNC_ERROR;
1295   sync_status->SetString("statusText", status_label);
1296   sync_status->SetString("actionLinkText", link_label);
1297   sync_status->SetBoolean("hasError", status_has_error);
1298
1299   sync_status->SetBoolean("managed", service && service->IsManaged());
1300   sync_status->SetBoolean("signedIn",
1301                           !signin->GetAuthenticatedUsername().empty());
1302   sync_status->SetBoolean("hasUnrecoverableError",
1303                           service && service->HasUnrecoverableError());
1304   sync_status->SetBoolean(
1305       "autoLoginVisible",
1306       CommandLine::ForCurrentProcess()->HasSwitch(switches::kEnableAutologin) &&
1307       service && service->IsSyncEnabledAndLoggedIn() &&
1308       service->IsOAuthRefreshTokenAvailable());
1309
1310   return sync_status.Pass();
1311 }
1312
1313 void BrowserOptionsHandler::HandleSelectDownloadLocation(
1314     const base::ListValue* args) {
1315   PrefService* pref_service = Profile::FromWebUI(web_ui())->GetPrefs();
1316   select_folder_dialog_ = ui::SelectFileDialog::Create(
1317       this, new ChromeSelectFilePolicy(web_ui()->GetWebContents()));
1318   ui::SelectFileDialog::FileTypeInfo info;
1319   info.support_drive = true;
1320   select_folder_dialog_->SelectFile(
1321       ui::SelectFileDialog::SELECT_FOLDER,
1322       l10n_util::GetStringUTF16(IDS_OPTIONS_DOWNLOADLOCATION_BROWSE_TITLE),
1323       pref_service->GetFilePath(prefs::kDownloadDefaultDirectory),
1324       &info,
1325       0,
1326       base::FilePath::StringType(),
1327       web_ui()->GetWebContents()->GetView()->GetTopLevelNativeWindow(),
1328       NULL);
1329 }
1330
1331 void BrowserOptionsHandler::FileSelected(const base::FilePath& path, int index,
1332                                          void* params) {
1333   content::RecordAction(UserMetricsAction("Options_SetDownloadDirectory"));
1334   PrefService* pref_service = Profile::FromWebUI(web_ui())->GetPrefs();
1335   pref_service->SetFilePath(prefs::kDownloadDefaultDirectory, path);
1336   pref_service->SetFilePath(prefs::kSaveFileDefaultDirectory, path);
1337 }
1338
1339 #if defined(OS_CHROMEOS)
1340 void BrowserOptionsHandler::TouchpadExists(bool exists) {
1341   base::FundamentalValue val(exists);
1342   web_ui()->CallJavascriptFunction("BrowserOptions.showTouchpadControls", val);
1343 }
1344
1345 void BrowserOptionsHandler::MouseExists(bool exists) {
1346   base::FundamentalValue val(exists);
1347   web_ui()->CallJavascriptFunction("BrowserOptions.showMouseControls", val);
1348 }
1349
1350 void BrowserOptionsHandler::OnUserImagePolicyChanged(
1351     const base::Value* previous_policy,
1352     const base::Value* current_policy) {
1353   const bool had_policy = !!previous_policy;
1354   const bool has_policy = !!current_policy;
1355   if (had_policy != has_policy)
1356     OnAccountPictureManagedChanged(has_policy);
1357 }
1358
1359 #endif  // defined(OS_CHROMEOS)
1360
1361 void BrowserOptionsHandler::UpdateSyncState() {
1362   web_ui()->CallJavascriptFunction("BrowserOptions.updateSyncState",
1363                                    *GetSyncStateDictionary());
1364 }
1365
1366 void BrowserOptionsHandler::OnSigninAllowedPrefChange() {
1367   UpdateSyncState();
1368 }
1369
1370 void BrowserOptionsHandler::HandleAutoOpenButton(const base::ListValue* args) {
1371   content::RecordAction(UserMetricsAction("Options_ResetAutoOpenFiles"));
1372   DownloadManager* manager = BrowserContext::GetDownloadManager(
1373       web_ui()->GetWebContents()->GetBrowserContext());
1374   if (manager)
1375     DownloadPrefs::FromDownloadManager(manager)->ResetAutoOpen();
1376 }
1377
1378 void BrowserOptionsHandler::HandleDefaultFontSize(const base::ListValue* args) {
1379   int font_size;
1380   if (ExtractIntegerValue(args, &font_size)) {
1381     if (font_size > 0) {
1382       PrefService* pref_service = Profile::FromWebUI(web_ui())->GetPrefs();
1383       pref_service->SetInteger(prefs::kWebKitDefaultFontSize, font_size);
1384       SetupFontSizeSelector();
1385     }
1386   }
1387 }
1388
1389 void BrowserOptionsHandler::HandleDefaultZoomFactor(
1390     const base::ListValue* args) {
1391   double zoom_factor;
1392   if (ExtractDoubleValue(args, &zoom_factor)) {
1393     default_zoom_level_.SetValue(content::ZoomFactorToZoomLevel(zoom_factor));
1394   }
1395 }
1396
1397 void BrowserOptionsHandler::HandleRestartBrowser(const base::ListValue* args) {
1398 #if defined(OS_WIN) && defined(USE_ASH)
1399   // If hardware acceleration is disabled then we need to force restart
1400   // browser in desktop mode.
1401   // TODO(shrikant): Remove this once we fix start mode logic for browser.
1402   // Currently there are issues with determining correct browser mode
1403   // at startup.
1404   if (chrome::GetActiveDesktop() == chrome::HOST_DESKTOP_TYPE_ASH) {
1405     PrefService* pref_service = g_browser_process->local_state();
1406     if (!pref_service->GetBoolean(prefs::kHardwareAccelerationModeEnabled)) {
1407       chrome::AttemptRestartToDesktopMode();
1408       return;
1409     }
1410   }
1411 #endif
1412
1413   chrome::AttemptRestart();
1414 }
1415
1416 void BrowserOptionsHandler::HandleRequestProfilesInfo(
1417     const base::ListValue* args) {
1418   SendProfilesInfo();
1419 }
1420
1421 #if !defined(OS_CHROMEOS)
1422 void BrowserOptionsHandler::ShowNetworkProxySettings(
1423     const base::ListValue* args) {
1424   content::RecordAction(UserMetricsAction("Options_ShowProxySettings"));
1425   AdvancedOptionsUtilities::ShowNetworkProxySettings(
1426       web_ui()->GetWebContents());
1427 }
1428 #endif
1429
1430 #if !defined(USE_NSS) && !defined(USE_OPENSSL)
1431 void BrowserOptionsHandler::ShowManageSSLCertificates(
1432     const base::ListValue* args) {
1433   content::RecordAction(UserMetricsAction("Options_ManageSSLCertificates"));
1434   AdvancedOptionsUtilities::ShowManageSSLCertificates(
1435       web_ui()->GetWebContents());
1436 }
1437 #endif
1438
1439 #if defined(ENABLE_MDNS)
1440
1441 void BrowserOptionsHandler::ShowCloudPrintDevicesPage(
1442     const base::ListValue* args) {
1443   content::RecordAction(UserMetricsAction("Options_CloudPrintDevicesPage"));
1444   // Navigate in current tab to devices page.
1445   OpenURLParams params(
1446       GURL(chrome::kChromeUIDevicesURL), Referrer(),
1447       CURRENT_TAB, content::PAGE_TRANSITION_LINK, false);
1448   web_ui()->GetWebContents()->OpenURL(params);
1449 }
1450
1451 #endif
1452
1453 #if defined(ENABLE_FULL_PRINTING)
1454 void BrowserOptionsHandler::ShowCloudPrintManagePage(
1455     const base::ListValue* args) {
1456   content::RecordAction(UserMetricsAction("Options_ManageCloudPrinters"));
1457   // Open a new tab in the current window for the management page.
1458   Profile* profile = Profile::FromWebUI(web_ui());
1459   OpenURLParams params(
1460       CloudPrintURL(profile).GetCloudPrintServiceManageURL(), Referrer(),
1461       NEW_FOREGROUND_TAB, content::PAGE_TRANSITION_LINK, false);
1462   web_ui()->GetWebContents()->OpenURL(params);
1463 }
1464
1465 #if !defined(OS_CHROMEOS)
1466 void BrowserOptionsHandler::ShowCloudPrintSetupDialog(
1467     const base::ListValue* args) {
1468   content::RecordAction(UserMetricsAction("Options_EnableCloudPrintProxy"));
1469   // Open the connector enable page in the current tab.
1470   Profile* profile = Profile::FromWebUI(web_ui());
1471   OpenURLParams params(
1472       CloudPrintURL(profile).GetCloudPrintServiceEnableURL(
1473           CloudPrintProxyServiceFactory::GetForProfile(profile)->proxy_id()),
1474       Referrer(), CURRENT_TAB, content::PAGE_TRANSITION_LINK, false);
1475   web_ui()->GetWebContents()->OpenURL(params);
1476 }
1477
1478 void BrowserOptionsHandler::HandleDisableCloudPrintConnector(
1479     const base::ListValue* args) {
1480   content::RecordAction(
1481       UserMetricsAction("Options_DisableCloudPrintProxy"));
1482   CloudPrintProxyServiceFactory::GetForProfile(Profile::FromWebUI(web_ui()))->
1483       DisableForUser();
1484 }
1485
1486 void BrowserOptionsHandler::RefreshCloudPrintStatusFromService() {
1487   if (cloud_print_connector_ui_enabled_)
1488     CloudPrintProxyServiceFactory::GetForProfile(Profile::FromWebUI(web_ui()))->
1489         RefreshStatusFromService();
1490 }
1491
1492 void BrowserOptionsHandler::SetupCloudPrintConnectorSection() {
1493   Profile* profile = Profile::FromWebUI(web_ui());
1494   if (!CloudPrintProxyServiceFactory::GetForProfile(profile)) {
1495     cloud_print_connector_ui_enabled_ = false;
1496     RemoveCloudPrintConnectorSection();
1497     return;
1498   }
1499
1500   bool cloud_print_connector_allowed =
1501       !cloud_print_connector_enabled_.IsManaged() ||
1502       cloud_print_connector_enabled_.GetValue();
1503   base::FundamentalValue allowed(cloud_print_connector_allowed);
1504
1505   std::string email;
1506   if (profile->GetPrefs()->HasPrefPath(prefs::kCloudPrintEmail) &&
1507       cloud_print_connector_allowed) {
1508     email = profile->GetPrefs()->GetString(prefs::kCloudPrintEmail);
1509   }
1510   base::FundamentalValue disabled(email.empty());
1511
1512   base::string16 label_str;
1513   if (email.empty()) {
1514     label_str = l10n_util::GetStringFUTF16(
1515         IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_DISABLED_LABEL,
1516         l10n_util::GetStringUTF16(IDS_GOOGLE_CLOUD_PRINT));
1517   } else {
1518     label_str = l10n_util::GetStringFUTF16(
1519         IDS_OPTIONS_CLOUD_PRINT_CONNECTOR_ENABLED_LABEL,
1520         l10n_util::GetStringUTF16(IDS_GOOGLE_CLOUD_PRINT),
1521         base::UTF8ToUTF16(email));
1522   }
1523   base::StringValue label(label_str);
1524
1525   web_ui()->CallJavascriptFunction(
1526       "BrowserOptions.setupCloudPrintConnectorSection", disabled, label,
1527       allowed);
1528 }
1529
1530 void BrowserOptionsHandler::RemoveCloudPrintConnectorSection() {
1531   web_ui()->CallJavascriptFunction(
1532       "BrowserOptions.removeCloudPrintConnectorSection");
1533 }
1534 #endif  // defined(OS_CHROMEOS)
1535 #endif  // defined(ENABLE_FULL_PRINTING)
1536
1537 void BrowserOptionsHandler::HandleRequestHotwordAvailable(
1538     const base::ListValue* args) {
1539   Profile* profile = Profile::FromWebUI(web_ui());
1540   std::string group = base::FieldTrialList::FindFullName("VoiceTrigger");
1541   if (group != "" && group != "Disabled" &&
1542       HotwordServiceFactory::IsServiceAvailable(profile)) {
1543     web_ui()->CallJavascriptFunction("BrowserOptions.showHotwordSection");
1544   }
1545 }
1546
1547 #if defined(OS_CHROMEOS)
1548 void BrowserOptionsHandler::HandleOpenWallpaperManager(
1549     const base::ListValue* args) {
1550   wallpaper_manager_util::OpenWallpaperManager();
1551 }
1552
1553 void BrowserOptionsHandler::VirtualKeyboardChangeCallback(
1554     const base::ListValue* args) {
1555   bool enabled = false;
1556   args->GetBoolean(0, &enabled);
1557
1558   chromeos::accessibility::EnableVirtualKeyboard(enabled);
1559 }
1560
1561 void BrowserOptionsHandler::PerformFactoryResetRestart(
1562     const base::ListValue* args) {
1563   policy::BrowserPolicyConnectorChromeOS* connector =
1564       g_browser_process->platform_part()->browser_policy_connector_chromeos();
1565   if (connector->IsEnterpriseManaged())
1566     return;
1567
1568   PrefService* prefs = g_browser_process->local_state();
1569   prefs->SetBoolean(prefs::kFactoryResetRequested, true);
1570   prefs->CommitPendingWrite();
1571
1572   // Perform sign out. Current chrome process will then terminate, new one will
1573   // be launched (as if it was a restart).
1574   chromeos::DBusThreadManager::Get()->GetPowerManagerClient()->RequestRestart();
1575 }
1576
1577 void BrowserOptionsHandler::SetupAccessibilityFeatures() {
1578   PrefService* pref_service = g_browser_process->local_state();
1579   base::FundamentalValue virtual_keyboard_enabled(
1580       pref_service->GetBoolean(prefs::kVirtualKeyboardEnabled));
1581   web_ui()->CallJavascriptFunction(
1582       "BrowserOptions.setVirtualKeyboardCheckboxState",
1583       virtual_keyboard_enabled);
1584 }
1585 #endif
1586
1587 void BrowserOptionsHandler::SetupMetricsReportingSettingVisibility() {
1588 #if defined(GOOGLE_CHROME_BUILD)
1589   // Don't show the reporting setting if we are in the guest mode.
1590   if (Profile::FromWebUI(web_ui())->IsGuestSession()) {
1591     base::FundamentalValue visible(false);
1592     web_ui()->CallJavascriptFunction(
1593         "BrowserOptions.setMetricsReportingSettingVisibility", visible);
1594   }
1595 #endif
1596 }
1597
1598 void BrowserOptionsHandler::SetupFontSizeSelector() {
1599   PrefService* pref_service = Profile::FromWebUI(web_ui())->GetPrefs();
1600   const PrefService::Preference* default_font_size =
1601       pref_service->FindPreference(prefs::kWebKitDefaultFontSize);
1602   const PrefService::Preference* default_fixed_font_size =
1603       pref_service->FindPreference(prefs::kWebKitDefaultFixedFontSize);
1604
1605   base::DictionaryValue dict;
1606   dict.SetInteger("value",
1607                   pref_service->GetInteger(prefs::kWebKitDefaultFontSize));
1608
1609   // The font size control displays the value of the default font size, but
1610   // setting it alters both the default font size and the default fixed font
1611   // size. So it must be disabled when either of those prefs is not user
1612   // modifiable.
1613   dict.SetBoolean("disabled",
1614       !default_font_size->IsUserModifiable() ||
1615       !default_fixed_font_size->IsUserModifiable());
1616
1617   // This is a poor man's version of CoreOptionsHandler::CreateValueForPref,
1618   // adapted to consider two prefs. It may be better to refactor
1619   // CreateValueForPref so it can be called from here.
1620   if (default_font_size->IsManaged() || default_fixed_font_size->IsManaged()) {
1621       dict.SetString("controlledBy", "policy");
1622   } else if (default_font_size->IsExtensionControlled() ||
1623              default_fixed_font_size->IsExtensionControlled()) {
1624       dict.SetString("controlledBy", "extension");
1625   }
1626
1627   web_ui()->CallJavascriptFunction("BrowserOptions.setFontSize", dict);
1628 }
1629
1630 void BrowserOptionsHandler::SetupPageZoomSelector() {
1631   PrefService* pref_service = Profile::FromWebUI(web_ui())->GetPrefs();
1632   double default_zoom_level = pref_service->GetDouble(prefs::kDefaultZoomLevel);
1633   double default_zoom_factor =
1634       content::ZoomLevelToZoomFactor(default_zoom_level);
1635
1636   // Generate a vector of zoom factors from an array of known presets along with
1637   // the default factor added if necessary.
1638   std::vector<double> zoom_factors =
1639       chrome_page_zoom::PresetZoomFactors(default_zoom_factor);
1640
1641   // Iterate through the zoom factors and and build the contents of the
1642   // selector that will be sent to the javascript handler.
1643   // Each item in the list has the following parameters:
1644   // 1. Title (string).
1645   // 2. Value (double).
1646   // 3. Is selected? (bool).
1647   base::ListValue zoom_factors_value;
1648   for (std::vector<double>::const_iterator i = zoom_factors.begin();
1649        i != zoom_factors.end(); ++i) {
1650     base::ListValue* option = new base::ListValue();
1651     double factor = *i;
1652     int percent = static_cast<int>(factor * 100 + 0.5);
1653     option->Append(new base::StringValue(
1654         l10n_util::GetStringFUTF16Int(IDS_ZOOM_PERCENT, percent)));
1655     option->Append(new base::FundamentalValue(factor));
1656     bool selected = content::ZoomValuesEqual(factor, default_zoom_factor);
1657     option->Append(new base::FundamentalValue(selected));
1658     zoom_factors_value.Append(option);
1659   }
1660
1661   web_ui()->CallJavascriptFunction(
1662       "BrowserOptions.setupPageZoomSelector", zoom_factors_value);
1663 }
1664
1665 void BrowserOptionsHandler::SetupAutoOpenFileTypes() {
1666   // Set the hidden state for the AutoOpenFileTypesResetToDefault button.
1667   // We show the button if the user has any auto-open file types registered.
1668   DownloadManager* manager = BrowserContext::GetDownloadManager(
1669       web_ui()->GetWebContents()->GetBrowserContext());
1670   bool display = manager &&
1671       DownloadPrefs::FromDownloadManager(manager)->IsAutoOpenUsed();
1672   base::FundamentalValue value(display);
1673   web_ui()->CallJavascriptFunction(
1674       "BrowserOptions.setAutoOpenFileTypesDisplayed", value);
1675 }
1676
1677 void BrowserOptionsHandler::SetupProxySettingsSection() {
1678 #if !defined(OS_CHROMEOS)
1679   // Disable the button if proxy settings are managed by a sysadmin, overridden
1680   // by an extension, or the browser is running in Windows Ash (on Windows the
1681   // proxy settings dialog will open on the Windows desktop and be invisible
1682   // to a user in Ash).
1683   bool is_win_ash = false;
1684 #if defined(OS_WIN)
1685   chrome::HostDesktopType desktop_type = helper::GetDesktopType(web_ui());
1686   is_win_ash = (desktop_type == chrome::HOST_DESKTOP_TYPE_ASH);
1687 #endif
1688   PrefService* pref_service = Profile::FromWebUI(web_ui())->GetPrefs();
1689   const PrefService::Preference* proxy_config =
1690       pref_service->FindPreference(prefs::kProxy);
1691   bool is_extension_controlled = (proxy_config &&
1692                                   proxy_config->IsExtensionControlled());
1693
1694   base::FundamentalValue disabled(is_win_ash || (proxy_config &&
1695                                   !proxy_config->IsUserModifiable()));
1696   base::FundamentalValue extension_controlled(is_extension_controlled);
1697   web_ui()->CallJavascriptFunction("BrowserOptions.setupProxySettingsSection",
1698                                    disabled, extension_controlled);
1699
1700 #endif  // !defined(OS_CHROMEOS)
1701 }
1702
1703 void BrowserOptionsHandler::SetupManageCertificatesSection() {
1704 #if defined(OS_WIN)
1705   // Disable the button if the settings page is displayed in Windows Ash,
1706   // otherwise the proxy settings dialog will open on the Windows desktop and
1707   // be invisible to a user in Ash.
1708   if (helper::GetDesktopType(web_ui()) == chrome::HOST_DESKTOP_TYPE_ASH) {
1709     base::FundamentalValue enabled(false);
1710     web_ui()->CallJavascriptFunction("BrowserOptions.enableCertificateButton",
1711                                      enabled);
1712   }
1713 #endif  // defined(OS_WIN)
1714 }
1715
1716 void BrowserOptionsHandler::SetupManagingSupervisedUsers() {
1717   bool has_users = !Profile::FromWebUI(web_ui())->
1718       GetPrefs()->GetDictionary(prefs::kManagedUsers)->empty();
1719   base::FundamentalValue has_users_value(has_users);
1720   web_ui()->CallJavascriptFunction(
1721       "BrowserOptions.updateManagesSupervisedUsers",
1722       has_users_value);
1723 }
1724
1725 }  // namespace options