feat: detect high contrast color mode (#15493)

* feat: add event and method to detect high contrast color mode

* docs: add docs for isHighContrastColorScheme and high-contrast-color-scheme-changed

* refactor: correct type of contrast
This commit is contained in:
Heilig Benedek 2018-10-31 15:22:18 +01:00 committed by John Kleinschmidt
parent aa6f7a5d9f
commit 6d2a088be9
4 changed files with 54 additions and 5 deletions

View file

@ -37,6 +37,12 @@ bool SystemPreferences::IsInvertedColorScheme() {
return color_utils::IsInvertedColorScheme(); return color_utils::IsInvertedColorScheme();
} }
#if !defined(OS_WIN)
bool SystemPreferences::IsHighContrastColorScheme() {
return false;
}
#endif // !defined(OS_WIN)
// static // static
mate::Handle<SystemPreferences> SystemPreferences::Create( mate::Handle<SystemPreferences> SystemPreferences::Create(
v8::Isolate* isolate) { v8::Isolate* isolate) {
@ -86,6 +92,8 @@ void SystemPreferences::BuildPrototype(
#endif #endif
.SetMethod("isInvertedColorScheme", .SetMethod("isInvertedColorScheme",
&SystemPreferences::IsInvertedColorScheme) &SystemPreferences::IsInvertedColorScheme)
.SetMethod("isHighContrastColorScheme",
&SystemPreferences::IsHighContrastColorScheme)
.SetMethod("isDarkMode", &SystemPreferences::IsDarkMode); .SetMethod("isDarkMode", &SystemPreferences::IsDarkMode);
} }

View file

@ -98,6 +98,7 @@ class SystemPreferences : public mate::EventEmitter<SystemPreferences>
#endif #endif
bool IsDarkMode(); bool IsDarkMode();
bool IsInvertedColorScheme(); bool IsInvertedColorScheme();
bool IsHighContrastColorScheme();
protected: protected:
explicit SystemPreferences(v8::Isolate* isolate); explicit SystemPreferences(v8::Isolate* isolate);
@ -139,6 +140,8 @@ class SystemPreferences : public mate::EventEmitter<SystemPreferences>
bool invertered_color_scheme_; bool invertered_color_scheme_;
bool high_contrast_color_scheme_;
std::unique_ptr<gfx::ScopedSysColorChangeListener> color_change_listener_; std::unique_ptr<gfx::ScopedSysColorChangeListener> color_change_listener_;
#endif #endif
DISALLOW_COPY_AND_ASSIGN(SystemPreferences); DISALLOW_COPY_AND_ASSIGN(SystemPreferences);

View file

@ -20,6 +20,18 @@ namespace {
const wchar_t kSystemPreferencesWindowClass[] = const wchar_t kSystemPreferencesWindowClass[] =
L"Electron_SystemPreferencesHostWindow"; L"Electron_SystemPreferencesHostWindow";
bool g_is_high_contract_color_scheme = false;
bool g_is_high_contract_color_scheme_initialized = false;
void UpdateHighContrastColorScheme() {
HIGHCONTRAST high_contrast = {0};
high_contrast.cbSize = sizeof(HIGHCONTRAST);
g_is_high_contract_color_scheme =
SystemParametersInfo(SPI_GETHIGHCONTRAST, 0, &high_contrast, 0) &&
((high_contrast.dwFlags & HCF_HIGHCONTRASTON) != 0);
g_is_high_contract_color_scheme_initialized = true;
}
} // namespace } // namespace
namespace api { namespace api {
@ -28,6 +40,12 @@ bool SystemPreferences::IsAeroGlassEnabled() {
return ui::win::IsAeroGlassEnabled(); return ui::win::IsAeroGlassEnabled();
} }
bool SystemPreferences::IsHighContrastColorScheme() {
if (!g_is_high_contract_color_scheme_initialized)
UpdateHighContrastColorScheme();
return g_is_high_contract_color_scheme;
}
std::string hexColorDWORDToRGBA(DWORD color) { std::string hexColorDWORDToRGBA(DWORD color) {
DWORD rgba = color << 8 | color >> 24; DWORD rgba = color << 8 | color >> 24;
std::ostringstream stream; std::ostringstream stream;
@ -119,6 +137,7 @@ std::string SystemPreferences::GetColor(const std::string& color,
void SystemPreferences::InitializeWindow() { void SystemPreferences::InitializeWindow() {
invertered_color_scheme_ = IsInvertedColorScheme(); invertered_color_scheme_ = IsInvertedColorScheme();
high_contrast_color_scheme_ = IsHighContrastColorScheme();
// Wait until app is ready before creating sys color listener // Wait until app is ready before creating sys color listener
// Creating this listener before the app is ready causes global shortcuts // Creating this listener before the app is ready causes global shortcuts
@ -169,6 +188,9 @@ LRESULT CALLBACK SystemPreferences::WndProc(HWND hwnd,
Emit("accent-color-changed", hexColorDWORDToRGBA(new_color)); Emit("accent-color-changed", hexColorDWORDToRGBA(new_color));
current_color_ = new_color_string; current_color_ = new_color_string;
} }
} else if (message == WM_SYSCOLORCHANGE ||
(message == WM_SETTINGCHANGE && wparam == SPI_SETHIGHCONTRAST)) {
UpdateHighContrastColorScheme();
} }
return ::DefWindowProc(hwnd, message, wparam, lparam); return ::DefWindowProc(hwnd, message, wparam, lparam);
} }
@ -179,6 +201,13 @@ void SystemPreferences::OnSysColorChange() {
invertered_color_scheme_ = new_invertered_color_scheme; invertered_color_scheme_ = new_invertered_color_scheme;
Emit("inverted-color-scheme-changed", new_invertered_color_scheme); Emit("inverted-color-scheme-changed", new_invertered_color_scheme);
} }
bool new_high_contrast_color_scheme = IsHighContrastColorScheme();
if (new_high_contrast_color_scheme != high_contrast_color_scheme_) {
high_contrast_color_scheme_ = new_high_contrast_color_scheme;
Emit("high-contrast-color-scheme-changed", new_high_contrast_color_scheme);
}
Emit("color-changed"); Emit("color-changed");
} }

View file

@ -32,8 +32,14 @@ Returns:
Returns: Returns:
* `event` Event * `event` Event
* `invertedColorScheme` Boolean - `true` if an inverted color scheme, such as * `invertedColorScheme` Boolean - `true` if an inverted color scheme (a high contrast color scheme with light text and dark backgrounds) is being used, `false` otherwise.
a high contrast theme, is being used, `false` otherwise.
### Event: 'high-contrast-color-scheme-changed' _Windows_
Returns:
* `event` Event
* `highContrastColorScheme` Boolean - `true` if a high contrast theme is being used, `false` otherwise.
### Event: 'appearance-changed' _macOS_ ### Event: 'appearance-changed' _macOS_
@ -276,12 +282,15 @@ const alpha = color.substr(6, 2) // "dd"
Returns `String` - The system color setting in RGB hexadecimal form (`#ABCDEF`). Returns `String` - The system color setting in RGB hexadecimal form (`#ABCDEF`).
See the [Windows docs][windows-colors] for more details. See the [Windows docs][windows-colors] for more details.
[windows-colors]:https://msdn.microsoft.com/en-us/library/windows/desktop/ms724371(v=vs.85).aspx
### `systemPreferences.isInvertedColorScheme()` _Windows_ ### `systemPreferences.isInvertedColorScheme()` _Windows_
Returns `Boolean` - `true` if an inverted color scheme, such as a high contrast Returns `Boolean` - `true` if an inverted color scheme (a high contrast color scheme with light text and dark backgrounds) is active, `false` otherwise.
theme, is active, `false` otherwise.
[windows-colors]:https://msdn.microsoft.com/en-us/library/windows/desktop/ms724371(v=vs.85).aspx ### `systemPreferences.isHighContrastColorScheme()` _Windows_
Returns `Boolean` - `true` if a high contrast theme is active, `false` otherwise.
### `systemPreferences.getEffectiveAppearance()` _macOS_ ### `systemPreferences.getEffectiveAppearance()` _macOS_