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/ui/prefs/prefs_tab_helper.h"
9 #include "base/prefs/overlay_user_pref_store.h"
10 #include "base/prefs/pref_service.h"
11 #include "base/strings/string_util.h"
12 #include "base/strings/stringprintf.h"
13 #include "base/strings/utf_string_conversions.h"
14 #include "chrome/browser/browser_process.h"
15 #include "chrome/browser/chrome_notification_types.h"
16 #include "chrome/browser/profiles/profile.h"
17 #include "chrome/browser/renderer_preferences_util.h"
18 #include "chrome/common/pref_font_webkit_names.h"
19 #include "chrome/common/pref_names.h"
20 #include "chrome/common/pref_names_util.h"
21 #include "components/user_prefs/pref_registry_syncable.h"
22 #include "content/public/browser/notification_details.h"
23 #include "content/public/browser/notification_service.h"
24 #include "content/public/browser/render_view_host.h"
25 #include "content/public/browser/web_contents.h"
26 #include "grit/locale_settings.h"
27 #include "grit/platform_locale_settings.h"
28 #include "third_party/icu/source/common/unicode/uchar.h"
29 #include "third_party/icu/source/common/unicode/uscript.h"
30 #include "webkit/common/webpreferences.h"
32 #if defined(OS_POSIX) && !defined(OS_MACOSX) && defined(ENABLE_THEMES)
33 #include "chrome/browser/themes/theme_service.h"
34 #include "chrome/browser/themes/theme_service_factory.h"
37 using content::WebContents
;
39 DEFINE_WEB_CONTENTS_USER_DATA_KEY(PrefsTabHelper
);
43 // The list of prefs we want to observe.
44 const char* kPrefsToObserve
[] = {
45 prefs::kDefaultCharset
,
46 prefs::kWebKitAllowDisplayingInsecureContent
,
47 prefs::kWebKitAllowRunningInsecureContent
,
48 prefs::kWebKitDefaultFixedFontSize
,
49 prefs::kWebKitDefaultFontSize
,
50 #if defined(OS_ANDROID)
51 prefs::kWebKitFontScaleFactor
,
52 prefs::kWebKitForceEnableZoom
,
53 prefs::kWebKitPasswordEchoEnabled
,
55 prefs::kWebKitJavascriptEnabled
,
56 prefs::kWebKitJavaEnabled
,
57 prefs::kWebKitLoadsImagesAutomatically
,
58 prefs::kWebKitMinimumFontSize
,
59 prefs::kWebKitMinimumLogicalFontSize
,
60 prefs::kWebKitPluginsEnabled
,
61 prefs::kWebkitTabsToLinks
,
62 prefs::kWebKitUsesUniversalDetector
65 const int kPrefsToObserveLength
= arraysize(kPrefsToObserve
);
67 #if !defined(OS_ANDROID)
68 // Registers a preference under the path |pref_name| for each script used for
69 // per-script font prefs.
70 // For example, for WEBKIT_WEBPREFS_FONTS_SERIF ("fonts.serif"):
71 // "fonts.serif.Arab", "fonts.serif.Hang", etc. are registered.
72 // |fonts_with_defaults| contains all |pref_names| already registered since they
73 // have a specified default value.
74 // On Android there are no default values for these properties and there is no
75 // way to set them (because extensions are not supported so the Font Settings
76 // API cannot be used), so we can avoid registering them altogether.
77 void RegisterFontFamilyPrefs(user_prefs::PrefRegistrySyncable
* registry
,
78 const std::set
<std::string
>& fonts_with_defaults
) {
80 // Expand the font concatenated with script name so this stays at RO memory
81 // rather than allocated in heap.
82 static const char* const kFontFamilyMap
[] = {
83 #define EXPAND_SCRIPT_FONT(map_name, script_name) map_name "." script_name,
85 #include "chrome/common/pref_font_script_names-inl.h"
86 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_CURSIVE
)
87 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_FANTASY
)
88 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_FIXED
)
89 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_PICTOGRAPH
)
90 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_SANSERIF
)
91 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_SERIF
)
92 ALL_FONT_SCRIPTS(WEBKIT_WEBPREFS_FONTS_STANDARD
)
94 #undef EXPAND_SCRIPT_FONT
97 for (size_t i
= 0; i
< arraysize(kFontFamilyMap
); ++i
) {
98 const char* pref_name
= kFontFamilyMap
[i
];
99 if (fonts_with_defaults
.find(pref_name
) == fonts_with_defaults
.end()) {
100 // We haven't already set a default value for this font preference, so set
101 // an empty string as the default.
102 registry
->RegisterStringPref(
105 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
110 // Registers |obs| to observe per-script font prefs under the path |map_name|.
111 // On android, there's no exposed way to change these prefs, so we can save
112 // ~715KB of heap and some startup cycles by avoiding observing these prefs
113 // since they will never change.
114 void RegisterFontFamilyMapObserver(
115 PrefChangeRegistrar
* registrar
,
116 const char* map_name
,
117 const PrefChangeRegistrar::NamedChangeCallback
& obs
) {
118 DCHECK(StartsWithASCII(map_name
, "webkit.webprefs.", true));
119 for (size_t i
= 0; i
< prefs::kWebKitScriptsForFontFamilyMapsLength
; ++i
) {
120 const char* script
= prefs::kWebKitScriptsForFontFamilyMaps
[i
];
121 std::string pref_name
= base::StringPrintf("%s.%s", map_name
, script
);
122 registrar
->Add(pref_name
.c_str(), obs
);
125 #endif // !defined(OS_ANDROID)
128 const char* pref_name
;
132 // Font pref defaults. The prefs that have defaults vary by platform, since not
133 // all platforms have fonts for all scripts for all generic families.
134 // TODO(falken): add proper defaults when possible for all
135 // platforms/scripts/generic families.
136 const FontDefault kFontDefaults
[] = {
137 { prefs::kWebKitStandardFontFamily
, IDS_STANDARD_FONT_FAMILY
},
138 { prefs::kWebKitFixedFontFamily
, IDS_FIXED_FONT_FAMILY
},
139 { prefs::kWebKitSerifFontFamily
, IDS_SERIF_FONT_FAMILY
},
140 { prefs::kWebKitSansSerifFontFamily
, IDS_SANS_SERIF_FONT_FAMILY
},
141 { prefs::kWebKitCursiveFontFamily
, IDS_CURSIVE_FONT_FAMILY
},
142 { prefs::kWebKitFantasyFontFamily
, IDS_FANTASY_FONT_FAMILY
},
143 { prefs::kWebKitPictographFontFamily
, IDS_PICTOGRAPH_FONT_FAMILY
},
144 #if defined(OS_CHROMEOS) || defined(OS_MACOSX) || defined(OS_WIN)
145 { prefs::kWebKitStandardFontFamilyJapanese
,
146 IDS_STANDARD_FONT_FAMILY_JAPANESE
},
147 { prefs::kWebKitFixedFontFamilyJapanese
, IDS_FIXED_FONT_FAMILY_JAPANESE
},
148 { prefs::kWebKitSerifFontFamilyJapanese
, IDS_SERIF_FONT_FAMILY_JAPANESE
},
149 { prefs::kWebKitSansSerifFontFamilyJapanese
,
150 IDS_SANS_SERIF_FONT_FAMILY_JAPANESE
},
151 { prefs::kWebKitStandardFontFamilyKorean
, IDS_STANDARD_FONT_FAMILY_KOREAN
},
152 { prefs::kWebKitSerifFontFamilyKorean
, IDS_SERIF_FONT_FAMILY_KOREAN
},
153 { prefs::kWebKitSansSerifFontFamilyKorean
,
154 IDS_SANS_SERIF_FONT_FAMILY_KOREAN
},
155 { prefs::kWebKitStandardFontFamilySimplifiedHan
,
156 IDS_STANDARD_FONT_FAMILY_SIMPLIFIED_HAN
},
157 { prefs::kWebKitSerifFontFamilySimplifiedHan
,
158 IDS_SERIF_FONT_FAMILY_SIMPLIFIED_HAN
},
159 { prefs::kWebKitSansSerifFontFamilySimplifiedHan
,
160 IDS_SANS_SERIF_FONT_FAMILY_SIMPLIFIED_HAN
},
161 { prefs::kWebKitStandardFontFamilyTraditionalHan
,
162 IDS_STANDARD_FONT_FAMILY_TRADITIONAL_HAN
},
163 { prefs::kWebKitSerifFontFamilyTraditionalHan
,
164 IDS_SERIF_FONT_FAMILY_TRADITIONAL_HAN
},
165 { prefs::kWebKitSansSerifFontFamilyTraditionalHan
,
166 IDS_SANS_SERIF_FONT_FAMILY_TRADITIONAL_HAN
},
168 #if defined(OS_CHROMEOS)
169 { prefs::kWebKitStandardFontFamilyArabic
, IDS_STANDARD_FONT_FAMILY_ARABIC
},
170 { prefs::kWebKitSerifFontFamilyArabic
, IDS_SERIF_FONT_FAMILY_ARABIC
},
171 { prefs::kWebKitSansSerifFontFamilyArabic
,
172 IDS_SANS_SERIF_FONT_FAMILY_ARABIC
},
173 { prefs::kWebKitFixedFontFamilyKorean
, IDS_FIXED_FONT_FAMILY_KOREAN
},
174 { prefs::kWebKitFixedFontFamilySimplifiedHan
,
175 IDS_FIXED_FONT_FAMILY_SIMPLIFIED_HAN
},
176 { prefs::kWebKitFixedFontFamilyTraditionalHan
,
177 IDS_FIXED_FONT_FAMILY_TRADITIONAL_HAN
},
178 #elif defined(OS_WIN)
179 { prefs::kWebKitStandardFontFamilyCyrillic
,
180 IDS_STANDARD_FONT_FAMILY_CYRILLIC
},
181 { prefs::kWebKitFixedFontFamilyCyrillic
, IDS_FIXED_FONT_FAMILY_CYRILLIC
},
182 { prefs::kWebKitSerifFontFamilyCyrillic
, IDS_SERIF_FONT_FAMILY_CYRILLIC
},
183 { prefs::kWebKitSansSerifFontFamilyCyrillic
,
184 IDS_SANS_SERIF_FONT_FAMILY_CYRILLIC
},
185 { prefs::kWebKitStandardFontFamilyGreek
, IDS_STANDARD_FONT_FAMILY_GREEK
},
186 { prefs::kWebKitFixedFontFamilyGreek
, IDS_FIXED_FONT_FAMILY_GREEK
},
187 { prefs::kWebKitSerifFontFamilyGreek
, IDS_SERIF_FONT_FAMILY_GREEK
},
188 { prefs::kWebKitSansSerifFontFamilyGreek
, IDS_SANS_SERIF_FONT_FAMILY_GREEK
},
189 { prefs::kWebKitFixedFontFamilyKorean
, IDS_FIXED_FONT_FAMILY_KOREAN
},
190 { prefs::kWebKitCursiveFontFamilyKorean
, IDS_CURSIVE_FONT_FAMILY_KOREAN
},
191 { prefs::kWebKitFixedFontFamilySimplifiedHan
,
192 IDS_FIXED_FONT_FAMILY_SIMPLIFIED_HAN
},
193 { prefs::kWebKitFixedFontFamilyTraditionalHan
,
194 IDS_FIXED_FONT_FAMILY_TRADITIONAL_HAN
},
198 const size_t kFontDefaultsLength
= arraysize(kFontDefaults
);
200 // Returns the script of the font pref |pref_name|. For example, suppose
201 // |pref_name| is "webkit.webprefs.fonts.serif.Hant". Since the script code for
202 // the script name "Hant" is USCRIPT_TRADITIONAL_HAN, the function returns
203 // USCRIPT_TRADITIONAL_HAN. |pref_name| must be a valid font pref name.
204 UScriptCode
GetScriptOfFontPref(const char* pref_name
) {
205 // ICU script names are four letters.
206 static const size_t kScriptNameLength
= 4;
208 size_t len
= strlen(pref_name
);
209 DCHECK_GT(len
, kScriptNameLength
);
210 const char* scriptName
= &pref_name
[len
- kScriptNameLength
];
211 int32 code
= u_getPropertyValueEnum(UCHAR_SCRIPT
, scriptName
);
212 DCHECK(code
>= 0 && code
< USCRIPT_CODE_LIMIT
);
213 return static_cast<UScriptCode
>(code
);
216 // If |scriptCode| is a member of a family of "similar" script codes, returns
217 // the script code in that family that is used in font pref names. For example,
218 // USCRIPT_HANGUL and USCRIPT_KOREAN are considered equivalent for the purposes
219 // of font selection. Chrome uses the script code USCRIPT_HANGUL (script name
220 // "Hang") in Korean font pref names (for example,
221 // "webkit.webprefs.fonts.serif.Hang"). So, if |scriptCode| is USCRIPT_KOREAN,
222 // the function returns USCRIPT_HANGUL. If |scriptCode| is not a member of such
223 // a family, returns |scriptCode|.
224 UScriptCode
GetScriptForFontPrefMatching(UScriptCode scriptCode
) {
225 switch (scriptCode
) {
226 case USCRIPT_HIRAGANA
:
227 case USCRIPT_KATAKANA
:
228 case USCRIPT_KATAKANA_OR_HIRAGANA
:
229 return USCRIPT_JAPANESE
;
231 return USCRIPT_HANGUL
;
237 // Returns the primary script used by the browser's UI locale. For example, if
238 // the locale is "ru", the function returns USCRIPT_CYRILLIC, and if the locale
239 // is "en", the function returns USCRIPT_LATIN.
240 UScriptCode
GetScriptOfBrowserLocale() {
241 std::string locale
= g_browser_process
->GetApplicationLocale();
243 // For Chinese locales, uscript_getCode() just returns USCRIPT_HAN but our
244 // per-script fonts are for USCRIPT_SIMPLIFIED_HAN and
245 // USCRIPT_TRADITIONAL_HAN.
246 if (locale
== "zh-CN")
247 return USCRIPT_SIMPLIFIED_HAN
;
248 if (locale
== "zh-TW")
249 return USCRIPT_TRADITIONAL_HAN
;
251 UScriptCode code
= USCRIPT_INVALID_CODE
;
252 UErrorCode err
= U_ZERO_ERROR
;
253 uscript_getCode(locale
.c_str(), &code
, 1, &err
);
255 // Ignore the error that multiple scripts could be returned, since we only
257 if (U_FAILURE(err
) && err
!= U_BUFFER_OVERFLOW_ERROR
)
258 code
= USCRIPT_INVALID_CODE
;
259 return GetScriptForFontPrefMatching(code
);
262 // Sets a font family pref in |prefs| to |pref_value|.
263 void OverrideFontFamily(WebPreferences
* prefs
,
264 const std::string
& generic_family
,
265 const std::string
& script
,
266 const std::string
& pref_value
) {
267 webkit_glue::ScriptFontFamilyMap
* map
= NULL
;
268 if (generic_family
== "standard")
269 map
= &prefs
->standard_font_family_map
;
270 else if (generic_family
== "fixed")
271 map
= &prefs
->fixed_font_family_map
;
272 else if (generic_family
== "serif")
273 map
= &prefs
->serif_font_family_map
;
274 else if (generic_family
== "sansserif")
275 map
= &prefs
->sans_serif_font_family_map
;
276 else if (generic_family
== "cursive")
277 map
= &prefs
->cursive_font_family_map
;
278 else if (generic_family
== "fantasy")
279 map
= &prefs
->fantasy_font_family_map
;
280 else if (generic_family
== "pictograph")
281 map
= &prefs
->pictograph_font_family_map
;
283 NOTREACHED() << "Unknown generic font family: " << generic_family
;
284 (*map
)[script
] = base::UTF8ToUTF16(pref_value
);
289 PrefsTabHelper::PrefsTabHelper(WebContents
* contents
)
290 : web_contents_(contents
),
291 weak_ptr_factory_(this) {
292 PrefService
* prefs
= GetProfile()->GetPrefs();
293 pref_change_registrar_
.Init(prefs
);
295 base::Closure renderer_callback
= base::Bind(
296 &PrefsTabHelper::UpdateRendererPreferences
, base::Unretained(this));
297 pref_change_registrar_
.Add(prefs::kAcceptLanguages
, renderer_callback
);
298 pref_change_registrar_
.Add(prefs::kDefaultZoomLevel
, renderer_callback
);
299 pref_change_registrar_
.Add(prefs::kEnableDoNotTrack
, renderer_callback
);
300 pref_change_registrar_
.Add(prefs::kEnableReferrers
, renderer_callback
);
302 #if !defined(OS_MACOSX)
303 pref_change_registrar_
.Add(prefs::kFullscreenAllowed
, renderer_callback
);
306 PrefChangeRegistrar::NamedChangeCallback webkit_callback
= base::Bind(
307 &PrefsTabHelper::OnWebPrefChanged
, base::Unretained(this));
308 for (int i
= 0; i
< kPrefsToObserveLength
; ++i
) {
309 const char* pref_name
= kPrefsToObserve
[i
];
310 DCHECK(std::string(pref_name
) == prefs::kDefaultCharset
||
311 StartsWithASCII(pref_name
, "webkit.webprefs.", true));
312 pref_change_registrar_
.Add(pref_name
, webkit_callback
);
315 #if !defined(OS_ANDROID)
316 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
317 prefs::kWebKitStandardFontFamilyMap
,
319 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
320 prefs::kWebKitFixedFontFamilyMap
,
322 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
323 prefs::kWebKitSerifFontFamilyMap
,
325 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
326 prefs::kWebKitSansSerifFontFamilyMap
,
328 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
329 prefs::kWebKitCursiveFontFamilyMap
,
331 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
332 prefs::kWebKitFantasyFontFamilyMap
,
334 RegisterFontFamilyMapObserver(&pref_change_registrar_
,
335 prefs::kWebKitPictographFontFamilyMap
,
337 #endif // !defined(OS_ANDROID)
340 renderer_preferences_util::UpdateFromSystemSettings(
341 web_contents_
->GetMutableRendererPrefs(), GetProfile());
343 #if defined(OS_POSIX) && !defined(OS_MACOSX) && defined(ENABLE_THEMES)
344 registrar_
.Add(this, chrome::NOTIFICATION_BROWSER_THEME_CHANGED
,
345 content::Source
<ThemeService
>(
346 ThemeServiceFactory::GetForProfile(GetProfile())));
348 #if defined(USE_AURA)
350 chrome::NOTIFICATION_BROWSER_FLING_CURVE_PARAMETERS_CHANGED
,
351 content::NotificationService::AllSources());
355 PrefsTabHelper::~PrefsTabHelper() {
359 void PrefsTabHelper::InitIncognitoUserPrefStore(
360 OverlayUserPrefStore
* pref_store
) {
361 // List of keys that cannot be changed in the user prefs file by the incognito
362 // profile. All preferences that store information about the browsing history
363 // or behavior of the user should have this property.
364 pref_store
->RegisterOverlayPref(prefs::kBrowserWindowPlacement
);
365 pref_store
->RegisterOverlayPref(prefs::kSaveFileDefaultDirectory
);
366 #if defined(OS_ANDROID) || defined(OS_IOS)
367 pref_store
->RegisterOverlayPref(prefs::kProxy
);
368 #endif // defined(OS_ANDROID) || defined(OS_IOS)
372 void PrefsTabHelper::RegisterProfilePrefs(
373 user_prefs::PrefRegistrySyncable
* registry
) {
374 WebPreferences pref_defaults
;
375 registry
->RegisterBooleanPref(
376 prefs::kWebKitJavascriptEnabled
,
377 pref_defaults
.javascript_enabled
,
378 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
379 registry
->RegisterBooleanPref(
380 prefs::kWebKitWebSecurityEnabled
,
381 pref_defaults
.web_security_enabled
,
382 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
383 registry
->RegisterBooleanPref(
384 prefs::kWebKitJavascriptCanOpenWindowsAutomatically
,
386 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
387 registry
->RegisterBooleanPref(
388 prefs::kWebKitLoadsImagesAutomatically
,
389 pref_defaults
.loads_images_automatically
,
390 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
391 registry
->RegisterBooleanPref(
392 prefs::kWebKitPluginsEnabled
,
393 pref_defaults
.plugins_enabled
,
394 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
395 registry
->RegisterBooleanPref(
396 prefs::kWebKitDomPasteEnabled
,
397 pref_defaults
.dom_paste_enabled
,
398 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
399 registry
->RegisterBooleanPref(
400 prefs::kWebKitShrinksStandaloneImagesToFit
,
401 pref_defaults
.shrinks_standalone_images_to_fit
,
402 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
403 registry
->RegisterDictionaryPref(
404 prefs::kWebKitInspectorSettings
,
405 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
406 registry
->RegisterBooleanPref(
407 prefs::kWebKitTextAreasAreResizable
,
408 pref_defaults
.text_areas_are_resizable
,
409 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
410 registry
->RegisterBooleanPref(
411 prefs::kWebKitJavaEnabled
,
412 pref_defaults
.java_enabled
,
413 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
414 registry
->RegisterBooleanPref(
415 prefs::kWebkitTabsToLinks
,
416 pref_defaults
.tabs_to_links
,
417 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
418 registry
->RegisterBooleanPref(
419 prefs::kWebKitAllowRunningInsecureContent
,
421 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
422 registry
->RegisterBooleanPref(
423 prefs::kWebKitAllowDisplayingInsecureContent
,
425 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
426 registry
->RegisterBooleanPref(
427 prefs::kEnableReferrers
,
429 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
430 #if defined(OS_ANDROID)
431 registry
->RegisterDoublePref(
432 prefs::kWebKitFontScaleFactor
,
434 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
435 registry
->RegisterBooleanPref(
436 prefs::kWebKitForceEnableZoom
,
437 pref_defaults
.force_enable_zoom
,
438 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
439 registry
->RegisterBooleanPref(
440 prefs::kWebKitPasswordEchoEnabled
,
441 pref_defaults
.password_echo_enabled
,
442 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
444 registry
->RegisterLocalizedStringPref(
445 prefs::kAcceptLanguages
,
446 IDS_ACCEPT_LANGUAGES
,
447 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF
);
448 registry
->RegisterLocalizedStringPref(
449 prefs::kDefaultCharset
,
450 IDS_DEFAULT_ENCODING
,
451 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF
);
453 // Register font prefs that have defaults.
454 std::set
<std::string
> fonts_with_defaults
;
455 UScriptCode browser_script
= GetScriptOfBrowserLocale();
456 for (size_t i
= 0; i
< kFontDefaultsLength
; ++i
) {
457 const FontDefault
& pref
= kFontDefaults
[i
];
458 UScriptCode pref_script
= GetScriptOfFontPref(pref
.pref_name
);
460 // Suppress this default font pref value if it is for the primary script of
461 // the browser's UI locale. For example, if the pref is for the sans-serif
462 // font for the Cyrillic script, and the browser locale is "ru" (Russian),
463 // the default is suppressed. Otherwise, the default would override the
464 // user's font preferences when viewing pages in their native language.
465 // This is because users have no way yet of customizing their per-script
466 // font preferences. The font prefs accessible in the options UI are for
467 // the default, unknown script; these prefs have less priority than the
468 // per-script font prefs when the script of the content is known. This code
469 // can possibly be removed later if users can easily access per-script font
470 // prefs (e.g., via the extensions workflow), or the problem turns out to
471 // not be really critical after all.
472 if (browser_script
!= pref_script
) {
473 registry
->RegisterLocalizedStringPref(
476 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
477 fonts_with_defaults
.insert(pref
.pref_name
);
481 // Register per-script font prefs that don't have defaults.
482 #if !defined(OS_ANDROID)
483 RegisterFontFamilyPrefs(registry
, fonts_with_defaults
);
486 registry
->RegisterLocalizedIntegerPref(
487 prefs::kWebKitDefaultFontSize
,
488 IDS_DEFAULT_FONT_SIZE
,
489 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
490 registry
->RegisterLocalizedIntegerPref(
491 prefs::kWebKitDefaultFixedFontSize
,
492 IDS_DEFAULT_FIXED_FONT_SIZE
,
493 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
494 registry
->RegisterLocalizedIntegerPref(
495 prefs::kWebKitMinimumFontSize
,
496 IDS_MINIMUM_FONT_SIZE
,
497 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
498 registry
->RegisterLocalizedIntegerPref(
499 prefs::kWebKitMinimumLogicalFontSize
,
500 IDS_MINIMUM_LOGICAL_FONT_SIZE
,
501 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
502 registry
->RegisterLocalizedBooleanPref(
503 prefs::kWebKitUsesUniversalDetector
,
504 IDS_USES_UNIVERSAL_DETECTOR
,
505 user_prefs::PrefRegistrySyncable::SYNCABLE_PREF
);
506 registry
->RegisterLocalizedStringPref(
507 prefs::kStaticEncodings
,
508 IDS_STATIC_ENCODING_LIST
,
509 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
510 registry
->RegisterStringPref(
511 prefs::kRecentlySelectedEncoding
,
513 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
516 void PrefsTabHelper::Observe(int type
,
517 const content::NotificationSource
& source
,
518 const content::NotificationDetails
& details
) {
519 #if defined(OS_POSIX) && !defined(OS_MACOSX) && defined(ENABLE_THEMES)
520 if (type
== chrome::NOTIFICATION_BROWSER_THEME_CHANGED
) {
521 UpdateRendererPreferences();
526 #if defined(USE_AURA)
527 if (type
== chrome::NOTIFICATION_BROWSER_FLING_CURVE_PARAMETERS_CHANGED
) {
528 UpdateRendererPreferences();
531 #endif // defined(USE_AURA)
536 void PrefsTabHelper::UpdateWebPreferences() {
537 web_contents_
->GetRenderViewHost()->UpdateWebkitPreferences(
538 web_contents_
->GetRenderViewHost()->GetWebkitPreferences());
541 void PrefsTabHelper::UpdateRendererPreferences() {
542 renderer_preferences_util::UpdateFromSystemSettings(
543 web_contents_
->GetMutableRendererPrefs(), GetProfile());
544 web_contents_
->GetRenderViewHost()->SyncRendererPrefs();
547 Profile
* PrefsTabHelper::GetProfile() {
548 return Profile::FromBrowserContext(web_contents_
->GetBrowserContext());
551 void PrefsTabHelper::OnWebPrefChanged(const std::string
& pref_name
) {
552 // When a font family pref's value goes from non-empty to the empty string, we
553 // must add it to the usual WebPreferences struct passed to the renderer.
555 // The empty string means to fall back to the pref for the Common script
556 // ("Zyyy"). For example, if chrome.fonts.serif.Cyrl is the empty string, it
557 // means to use chrome.fonts.serif.Zyyy for Cyrillic script. Prefs that are
558 // the empty string are normally not passed to WebKit, since there are so many
559 // of them that it would cause a performance regression. Not passing the pref
560 // is normally okay since WebKit does the desired fallback behavior regardless
561 // of whether the empty string is passed or the pref is not passed at all. But
562 // if the pref has changed from non-empty to the empty string, we must let
564 std::string generic_family
;
566 if (pref_names_util::ParseFontNamePrefPath(pref_name
,
569 PrefService
* prefs
= GetProfile()->GetPrefs();
570 std::string pref_value
= prefs
->GetString(pref_name
.c_str());
571 if (pref_value
.empty()) {
572 WebPreferences web_prefs
=
573 web_contents_
->GetRenderViewHost()->GetWebkitPreferences();
574 OverrideFontFamily(&web_prefs
, generic_family
, script
, std::string());
575 web_contents_
->GetRenderViewHost()->UpdateWebkitPreferences(web_prefs
);
580 UpdateWebPreferences();