Skip to content

Commit

Permalink
fix: don't register some shortcuts without accessibility
Browse files Browse the repository at this point in the history
  • Loading branch information
codebytere committed Jan 11, 2019
1 parent aa57be7 commit aec1254
Show file tree
Hide file tree
Showing 6 changed files with 60 additions and 1 deletion.
37 changes: 36 additions & 1 deletion atom/browser/api/atom_api_global_shortcut.cc
Expand Up @@ -6,15 +6,45 @@

#include <string>

#include "atom/browser/api/atom_api_system_preferences.h"
#include "atom/common/native_mate_converters/accelerator_converter.h"
#include "atom/common/native_mate_converters/callback.h"
#include "base/stl_util.h"
#include "base/strings/utf_string_conversions.h"
#include "native_mate/dictionary.h"

#include "atom/common/node_includes.h"
#include "atom/common/platform_util.h"

#if defined(OS_MACOSX)
#include "base/mac/mac_util.h"
#endif

using extensions::GlobalShortcutListener;

namespace {

#if defined(OS_MACOSX)
bool RegisteringMediaKeyForUntrustedClient(const ui::Accelerator& accelerator) {
if (platform_util::IsAtLeastOS10_14()) {
constexpr ui::KeyboardCode mediaKeys[] = {
ui::VKEY_MEDIA_PLAY_PAUSE, ui::VKEY_MEDIA_NEXT_TRACK,
ui::VKEY_MEDIA_PREV_TRACK, ui::VKEY_MEDIA_STOP};

if (std::find(std::begin(mediaKeys), std::end(mediaKeys),
accelerator.key_code()) != std::end(mediaKeys)) {
bool trusted =
atom::api::SystemPreferences::IsTrustedAccessibilityClient(false);
if (!trusted)
return true;
}
}
return false;
}
#endif

} // namespace

namespace atom {

namespace api {
Expand All @@ -31,7 +61,7 @@ void GlobalShortcut::OnKeyPressed(const ui::Accelerator& accelerator) {
if (accelerator_callback_map_.find(accelerator) ==
accelerator_callback_map_.end()) {
// This should never occur, because if it does, GlobalGlobalShortcutListener
// notifes us with wrong accelerator.
// notifies us with wrong accelerator.
NOTREACHED();
return;
}
Expand All @@ -40,6 +70,11 @@ void GlobalShortcut::OnKeyPressed(const ui::Accelerator& accelerator) {

bool GlobalShortcut::Register(const ui::Accelerator& accelerator,
const base::Closure& callback) {
#if defined(OS_MACOSX)
if (RegisteringMediaKeyForUntrustedClient(accelerator))
return false;
#endif

if (!GlobalShortcutListener::GetInstance()->RegisterAccelerator(accelerator,
this)) {
return false;
Expand Down
2 changes: 2 additions & 0 deletions atom/browser/api/atom_api_system_preferences.h
Expand Up @@ -93,6 +93,8 @@ class SystemPreferences : public mate::EventEmitter<SystemPreferences>
mate::Arguments* args);
void RemoveUserDefault(const std::string& name);
bool IsSwipeTrackingFromScrollEventsEnabled();

static bool IsTrustedAccessibilityClient(bool prompt);
#endif
bool IsDarkMode();
bool IsInvertedColorScheme();
Expand Down
6 changes: 6 additions & 0 deletions atom/browser/api/atom_api_system_preferences_mac.mm
Expand Up @@ -308,6 +308,12 @@
}
}

// static
bool SystemPreferences::IsTrustedAccessibilityClient(bool prompt) {
NSDictionary* options = @{(id)kAXTrustedCheckOptionPrompt : @(prompt)};
return AXIsProcessTrustedWithOptions((CFDictionaryRef)options);
}

void SystemPreferences::RemoveUserDefault(const std::string& name) {
NSUserDefaults* defaults = [NSUserDefaults standardUserDefaults];
[defaults removeObjectForKey:base::SysUTF8ToNSString(name)];
Expand Down
1 change: 1 addition & 0 deletions atom/common/platform_util.h
Expand Up @@ -60,6 +60,7 @@ void Beep();
#if defined(OS_MACOSX)
bool GetLoginItemEnabled();
void SetLoginItemEnabled(bool enabled);
bool IsAtLeastOS10_14();
#endif

} // namespace platform_util
Expand Down
7 changes: 7 additions & 0 deletions atom/common/platform_util_mac.mm
Expand Up @@ -8,6 +8,8 @@
#import <Cocoa/Cocoa.h>
#import <ServiceManagement/ServiceManagement.h>

#include "atom/common/platform_util.h"

#include "base/callback.h"
#include "base/files/file_path.h"
#include "base/files/file_util.h"
Expand All @@ -18,6 +20,7 @@
#include "base/strings/stringprintf.h"
#include "base/strings/sys_string_conversions.h"
#include "net/base/mac/url_conversions.h"
#include "third_party/WebKit/Source/platform/mac/VersionUtilMac.h"
#include "url/gurl.h"

namespace {
Expand Down Expand Up @@ -166,6 +169,10 @@ void OpenExternal(const GURL& url,
});
}

bool IsAtLeastOS10_14() {
return blink::internal::MacOSXMinorVersion() >= 14;
}

bool MoveItemToTrash(const base::FilePath& full_path) {
NSString* path_string = base::SysUTF8ToNSString(full_path.value());
BOOL status = [[NSFileManager defaultManager]
Expand Down
8 changes: 8 additions & 0 deletions docs/api/global-shortcut.md
Expand Up @@ -54,6 +54,14 @@ When the accelerator is already taken by other applications, this call will
silently fail. This behavior is intended by operating systems, since they don't
want applications to fight for global shortcuts.

The following accelerators will not be registered successfully on macOS 10.14 Mojave unless
the app has been authorized as a [trusted accessibility client](https://developer.apple.com/library/archive/documentation/Accessibility/Conceptual/AccessibilityMacOSX/OSXAXTestingApps.html):

* "Media Play/Pause"
* "Media Next Track"
* "Media Previous Track"
* "Media Stop"

### `globalShortcut.isRegistered(accelerator)`

* `accelerator` [Accelerator](accelerator.md)
Expand Down

0 comments on commit aec1254

Please sign in to comment.