1// Copyright (c) 2013 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/extensions/extension_commands_global_registry.h" 6 7#include "base/lazy_instance.h" 8#include "chrome/browser/extensions/api/commands/command_service.h" 9#include "chrome/browser/extensions/global_shortcut_listener.h" 10#include "extensions/common/extension.h" 11 12namespace extensions { 13 14ExtensionCommandsGlobalRegistry::ExtensionCommandsGlobalRegistry( 15 content::BrowserContext* context) 16 : ExtensionKeybindingRegistry(context, 17 ExtensionKeybindingRegistry::ALL_EXTENSIONS, 18 NULL), 19 browser_context_(context), 20 registry_for_active_window_(NULL) { 21 Init(); 22} 23 24ExtensionCommandsGlobalRegistry::~ExtensionCommandsGlobalRegistry() { 25 if (!IsEventTargetsEmpty()) { 26 GlobalShortcutListener* global_shortcut_listener = 27 GlobalShortcutListener::GetInstance(); 28 29 // Resume GlobalShortcutListener before we clean up if the shortcut handling 30 // is currently suspended. 31 if (global_shortcut_listener->IsShortcutHandlingSuspended()) 32 global_shortcut_listener->SetShortcutHandlingSuspended(false); 33 34 global_shortcut_listener->UnregisterAccelerators(this); 35 } 36} 37 38static base::LazyInstance< 39 BrowserContextKeyedAPIFactory<ExtensionCommandsGlobalRegistry> > g_factory = 40 LAZY_INSTANCE_INITIALIZER; 41 42// static 43BrowserContextKeyedAPIFactory<ExtensionCommandsGlobalRegistry>* 44ExtensionCommandsGlobalRegistry::GetFactoryInstance() { 45 return g_factory.Pointer(); 46} 47 48// static 49ExtensionCommandsGlobalRegistry* ExtensionCommandsGlobalRegistry::Get( 50 content::BrowserContext* context) { 51 return BrowserContextKeyedAPIFactory<ExtensionCommandsGlobalRegistry>::Get( 52 context); 53} 54 55// static 56void ExtensionCommandsGlobalRegistry::SetShortcutHandlingSuspended( 57 bool suspended) { 58 GlobalShortcutListener::GetInstance()->SetShortcutHandlingSuspended( 59 suspended); 60} 61 62bool ExtensionCommandsGlobalRegistry::IsRegistered( 63 const ui::Accelerator& accelerator) { 64 return (registry_for_active_window() && 65 registry_for_active_window()->IsAcceleratorRegistered(accelerator)) || 66 IsAcceleratorRegistered(accelerator); 67} 68 69void ExtensionCommandsGlobalRegistry::AddExtensionKeybinding( 70 const extensions::Extension* extension, 71 const std::string& command_name) { 72 // This object only handles named commands, not browser/page actions. 73 if (ShouldIgnoreCommand(command_name)) 74 return; 75 76 extensions::CommandService* command_service = 77 extensions::CommandService::Get(browser_context_); 78 // Add all the active global keybindings, if any. 79 extensions::CommandMap commands; 80 if (!command_service->GetNamedCommands( 81 extension->id(), 82 extensions::CommandService::ACTIVE_ONLY, 83 extensions::CommandService::GLOBAL, 84 &commands)) 85 return; 86 87 extensions::CommandMap::const_iterator iter = commands.begin(); 88 for (; iter != commands.end(); ++iter) { 89 if (!command_name.empty() && (iter->second.command_name() != command_name)) 90 continue; 91 const ui::Accelerator& accelerator = iter->second.accelerator(); 92 93 VLOG(0) << "Adding global keybinding for " << extension->name().c_str() 94 << " " << command_name.c_str() 95 << " key: " << accelerator.GetShortcutText(); 96 97 if (!IsAcceleratorRegistered(accelerator)) { 98 if (!GlobalShortcutListener::GetInstance()->RegisterAccelerator( 99 accelerator, this)) 100 continue; 101 } 102 103 AddEventTarget(accelerator, extension->id(), iter->second.command_name()); 104 } 105} 106 107void ExtensionCommandsGlobalRegistry::RemoveExtensionKeybindingImpl( 108 const ui::Accelerator& accelerator, 109 const std::string& command_name) { 110 VLOG(0) << "Removing keybinding for " << command_name.c_str(); 111 112 GlobalShortcutListener::GetInstance()->UnregisterAccelerator( 113 accelerator, this); 114} 115 116void ExtensionCommandsGlobalRegistry::OnKeyPressed( 117 const ui::Accelerator& accelerator) { 118 ExtensionKeybindingRegistry::NotifyEventTargets(accelerator); 119} 120 121} // namespace extensions 122