Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: respect system language preferences on Windows & macOS #23247

Merged
merged 1 commit into from May 4, 2020

Conversation

sorah
Copy link
Contributor

@sorah sorah commented Apr 23, 2020

Description of Change

This PR aims to fix #18829. Please refer to the issue for more details.

Add implementations to set user's OS language preferences to Accept-Language and navigator.languages, on Windows and macOS.

This also improves the CJK fallback font selection on Windows. Chromium uses Accept-Language to determine fallback fonts on Windows, especially kanji/han characters in CJK.

Previously the full preferences set to OS was not given to Chromium. For instance, when user sets en-US, ja-JP to Accept-Language, while Chromium chooses Japanese font for kanji text, but Electron chooses Chinese font. This is because only the first language is given to Accept-Language on Electron.

This patch is based on the idea given at #15532 /cc @nitsakh

image

Considerations

fix or feat?

❓ No sure this a feat or a fix. Might be a fix, and backports would be appreciated as I'm thinking this is a bug for CJK speakers.

WinRT API

In this implementation, GetThreadPreferedUILanguages API is used on Windows. But, I noticed this API doesn't provide the full list of user preferences.
Only the system locale (i.e. used for logon screen) and the user locale (i.e. UI used while logged in) are returned.

So, how do you think about adding ELECTRON_ACCEPT_LANGUAGE environment variable to give the preferences correctly, in addition to this change?

✅ Resolved using WinRT utility in Chromium #23247 (comment)

Checklist

Release Notes

notes: Fixed an issue with navigator.languages and Accept-Language did not fully respect users' language preferences on Windows and macOS. This also improved fallback font selection for CJK texts on Windows.

@welcome
Copy link

welcome bot commented Apr 23, 2020

💖 Thanks for opening this pull request! 💖

We use semantic commit messages to streamline the release process. Before your pull request can be merged, you should update your pull request title to start with a semantic prefix.

Examples of commit messages with semantic prefixes:

  • fix: don't overwrite prevent_default if default wasn't prevented
  • feat: add app.isPackaged() method
  • docs: app.isDefaultProtocolClient is now available on Linux

Things that will help get your PR across the finish line:

  • Follow the JavaScript, C++, and Python coding style.
  • Run npm run lint locally to catch formatting errors earlier.
  • Document any user-facing changes you've made following the documentation styleguide.
  • Include tests when adding/changing behavior.
  • Include screenshots and animated GIFs whenever possible.

We get a lot of pull requests on this repo, so please be patient and we will get back to you as soon as we can.

@electron-cation electron-cation bot added the new-pr 🌱 PR opened in the last 24 hours label Apr 23, 2020
@sorah sorah changed the title fix: set navigator.languages from OS preferences feat: respect language preferences on Windows & macOS Apr 23, 2020
@sorah sorah force-pushed the langs branch 3 times, most recently from 68ba39b to e5f23cb Compare April 23, 2020 04:20
@hanazuki
Copy link
Contributor

hanazuki commented Apr 23, 2020

I have a sample application to retrieve Windows 10's Preferred Language setting: https://github.com/hanazuki/win-accept-languages-sample

This program makes use of GlobalizationPreferences.Languages from WinRT library, which is available since Windows 10 as with the Preferred Languages setting itself.
We can try this method first, and if not supported by the running OS, fallback to GetThreadPreferedUILanguages.

Note on compatibility for old Windows:

  • Windows 7 and earlier does not support WinRT; we have to load RoInitialize and RoGetActivationFactory functions at runtime (i.e. using LoadLibrary&GetProcAddress) instead of linking runtimeobject.lib.
  • Windows 8 does not have GlobalizationPreferences; we can detect this case by checking the result of RoGetActivationFactory.

I hope this will help.

@sorah
Copy link
Contributor Author

sorah commented Apr 23, 2020

Nice. I regret that I did not imagine that Chrome should have such utility as Chrome is utilizing modern Windows APIs...

@sorah
Copy link
Contributor Author

sorah commented Apr 24, 2020

Changed to utilize Globalization API when available. Now trying to fix failing CIs.

@sorah
Copy link
Contributor Author

sorah commented Apr 24, 2020

CI Passed. Lint failure seems not relevant to my changes..

@sorah
Copy link
Contributor Author

sorah commented Apr 24, 2020

Opened #23266 for lint failure.

@electron-cation electron-cation bot removed the new-pr 🌱 PR opened in the last 24 hours label Apr 24, 2020
@sorah sorah force-pushed the langs branch 3 times, most recently from ebcc0e9 to 02de6fa Compare April 25, 2020 13:40
@sorah
Copy link
Contributor Author

sorah commented Apr 25, 2020

rebased and only linux-ia32 is failing with flaky timeout. my change is ready.

@@ -535,7 +535,7 @@ void WebContents::InitWithSessionAndOptions(
managed_web_contents()->GetView()->SetDelegate(this);

auto* prefs = web_contents()->GetMutableRendererPrefs();
prefs->accept_languages = g_browser_process->GetApplicationLocale();
SetAcceptLanguages(prefs);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can you move the language preferences code into separate files and then reference it here? Like this:

#include "shell/common/lang_util.h"

prefs->accept_languages = GetSystemLanguage();

It would make the code easier to maintain, and we might want to reuse the code in other places.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wasn't sure where to put this kind of code. Extracted: d947ed9

@zcbenz
Copy link
Member

zcbenz commented Apr 28, 2020

Can you fix the lint waring?

$ node ./script/lint.js
shell/common/language_util_mac.mm:14:  Add #include <string> for string  [build/include_what_you_use] [4]
shell/common/language_util_mac.mm:14:  Add #include <vector> for vector<>  [build/include_what_you_use] [4]
Total errors found: 2

@sorah
Copy link
Contributor Author

sorah commented Apr 28, 2020

Fixed, rebased & squashed.

@sorah
Copy link
Contributor Author

sorah commented Apr 28, 2020

nah, l10n_util::GetApplicationLocale() would block. changed to return empty vector (as getting one from a browser process can satisfy) at b8f4e09, but suggestions welcomed for possible Linux implementation.

https://app.circleci.com/pipelines/github/electron/electron/23740/workflows/27fc2fc4-3530-4576-979d-508f912d3172/jobs/533455/steps

[453:0428/013109.271509:FATAL:thread_restrictions.cc(78)] Check failed: !g_blocking_disallowed.Get().Get(). Function marked as blocking was called from a scope that disallows blocking! If this task is running inside the ThreadPool, it needs to have MayBlock() in its TaskTraits. Otherwise, consider making this blocking work asynchronous or, as a last resort, you may use ScopedAllowBlocking (see its documentation for best practices).

#0 0x55f86110bea9 base::debug::CollectStackTrace()
#1 0x55f861044643 base::debug::StackTrace::StackTrace()
#2 0x55f861058aaf logging::LogMessage::~LogMessage()
#3 0x55f86105932e logging::LogMessage::~LogMessage()
#4 0x55f8610dc235 base::internal::AssertBlockingAllowed()
#5 0x55f8610d65b9 base::ScopedBlockingCall::ScopedBlockingCall()
#6 0x55f861113658 base::CreateDirectoryAndGetError()
#7 0x55f862a00cf6 ui::PathProvider()
#8 0x55f861078c82 base::PathService::Get()
#9 0x55f861ed854e ui::ResourceBundle::GetLocaleFilePath()
#10 0x55f861ed84ca ui::ResourceBundle::LocaleDataPakExists()
#11 0x55f861eceadc l10n_util::CheckAndResolveLocale()
#12 0x55f861ecf58b l10n_util::GetApplicationLocaleInternalNonMac()
#13 0x55f861ecf706 l10n_util::GetApplicationLocale()
#14 0x55f85db4b1c4 electron::GetPreferredLanguages()
#15 0x55f85da6ad16 electron::api::WebContents::InitWithSessionAndOptions()

Copy link
Member

@deepak1556 deepak1556 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, nice change 👍

This commit fixes electron#18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on electron#15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
ckerr pushed a commit that referenced this pull request May 4, 2020
This commit fixes #18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on #15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
@trop
Copy link
Contributor

trop bot commented May 4, 2020

@ckerr has manually backported this PR to "9-x-y", please check out #23405

ckerr pushed a commit that referenced this pull request May 4, 2020
This commit fixes #18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on #15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
@trop
Copy link
Contributor

trop bot commented May 4, 2020

@ckerr has manually backported this PR to "8-x-y", please check out #23407

deepak1556 pushed a commit that referenced this pull request May 5, 2020
This commit fixes #18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on #15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Sorah Fukumori <her@sorah.jp>
Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
@sorah sorah deleted the langs branch May 5, 2020 03:17
@sorah
Copy link
Contributor Author

sorah commented May 5, 2020

thank you for treating this patch as a fix! 🤗

codebytere pushed a commit that referenced this pull request May 5, 2020
* fix: respect system language preferences on Win/macOS (#23247)

This commit fixes #18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on #15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

* fix: remove unintentionally-committed code

Some excess code was accidentally included in the last commit's cherry-pick.

* chore: fix extraneous #include found by lint

* fix: correct another manual backport error :P

Co-authored-by: Sorah Fukumori <her@sorah.jp>
Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
ckerr pushed a commit that referenced this pull request May 5, 2020
This commit fixes #18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on #15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
@trop trop bot added the in-flight/8-x-y label May 5, 2020
@trop
Copy link
Contributor

trop bot commented May 5, 2020

@ckerr has manually backported this PR to "7-2-x", please check out #23420

codebytere pushed a commit that referenced this pull request May 7, 2020
* fix: respect system language preferences on Win/macOS (#23247)

This commit fixes #18829

Previously the full preferences set to OS was not given to Chromium.

Also, this commit improves fallback font selection for CJK text.
Chromium uses browser languages to determine fallback fonts on Windows,
especially kanji/han characters in CJK.

For instance, when user sets 'en-US, ja-JP' to Accept-Language,
while Chromium chooses Japanese font for kanji text, but Electron
chooses Chinese font.  This is because only the first language was given
to Accept-Language on Electron.

This patch is based on #15532

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>

* fix: don't shadow the `w` local variable

* fixup! fix: respect system language preferences on Win/macOS (#23247)

Co-authored-by: Sorah Fukumori <her@sorah.jp>
Co-authored-by: Nitish Sakhawalkar <nitsakh@icloud.com>
Co-authored-by: Kasumi Hanazuki <kasumi@rollingapple.net>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Choosing appropriate fallback font list by system locale (especially on Windows)
5 participants