Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(78)

Side by Side Diff: chrome/browser/speech/tts_engine_extension_observer.cc

Issue 361363003: Support onvoiceschanged for extension-based tts engines. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright 2014 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/speech/tts_engine_extension_observer.h"
6
7 #include "base/logging.h"
8 #include "base/memory/singleton.h"
9 #include "chrome/browser/extensions/extension_service.h"
10 #include "chrome/browser/extensions/extension_system_factory.h"
11 #include "chrome/browser/profiles/incognito_helpers.h"
12 #include "chrome/browser/profiles/profile.h"
13 #include "chrome/browser/speech/extension_api/tts_engine_extension_api.h"
14 #include "chrome/browser/speech/tts_controller.h"
15 #include "components/keyed_service/content/browser_context_dependency_manager.h"
16 #include "components/keyed_service/content/browser_context_keyed_service_factory .h"
17 #include "components/keyed_service/core/keyed_service.h"
18 #include "extensions/browser/event_router.h"
19 #include "extensions/browser/extension_system.h"
20 #include "grit/browser_resources.h"
21
22 // Factory to load one instance of TtsExtensionLoaderChromeOs per profile.
23 class TtsEngineExtensionObserverFactory
24 : public BrowserContextKeyedServiceFactory {
25 public:
26 static TtsEngineExtensionObserver* GetForProfile(Profile* profile) {
27 return static_cast<TtsEngineExtensionObserver*>(
28 GetInstance()->GetServiceForBrowserContext(profile, true));
29 }
30
31 static TtsEngineExtensionObserverFactory* GetInstance() {
32 return Singleton<TtsEngineExtensionObserverFactory>::get();
33 }
34
35 private:
36 friend struct DefaultSingletonTraits<TtsEngineExtensionObserverFactory>;
37
38 TtsEngineExtensionObserverFactory()
39 : BrowserContextKeyedServiceFactory(
40 "TtsEngineExtensionObserver",
41 BrowserContextDependencyManager::GetInstance()) {
42 DependsOn(extensions::ExtensionSystemFactory::GetInstance());
43 }
44
45 virtual ~TtsEngineExtensionObserverFactory() {}
46
47 virtual content::BrowserContext* GetBrowserContextToUse(
48 content::BrowserContext* context) const OVERRIDE {
49 // If given an incognito profile (including the Chrome OS login
50 // profile), share the service with the original profile.
51 return chrome::GetBrowserContextRedirectedInIncognito(context);
52 }
53
54 virtual KeyedService* BuildServiceInstanceFor(
55 content::BrowserContext* profile) const OVERRIDE {
56 return new TtsEngineExtensionObserver(static_cast<Profile*>(profile));
57 }
58 };
59
60 TtsEngineExtensionObserver* TtsEngineExtensionObserver::GetInstance(
61 Profile* profile) {
62 return TtsEngineExtensionObserverFactory::GetInstance()->GetForProfile(
63 profile);
64 }
65
66 TtsEngineExtensionObserver::TtsEngineExtensionObserver(Profile* profile)
67 : extension_registry_observer_(this),
68 profile_(profile),
69 saw_tts_engine_added_(false) {
70 extension_registry_observer_.Add(
71 extensions::ExtensionRegistry::Get(profile_));
72
73 extensions::ExtensionSystem* system =
74 extensions::ExtensionSystem::Get(profile_);
75 DCHECK(system);
76 extensions::EventRouter* event_router = system->event_router();
77 DCHECK(event_router);
78 event_router->RegisterObserver(this, tts_engine_events::kOnSpeak);
79 event_router->RegisterObserver(this, tts_engine_events::kOnStop);
80 }
81
82 bool TtsEngineExtensionObserver::SawExtensionLoad(
83 const std::string& extension_id,
84 bool update) {
85 bool previously_loaded =
86 engine_extension_ids_.find(extension_id) != engine_extension_ids_.end();
87
88 if (update)
89 engine_extension_ids_.insert(extension_id);
90
91 return previously_loaded;
92 }
93
94 void TtsEngineExtensionObserver::Shutdown() {
95 extensions::EventRouter::Get(profile_)->UnregisterObserver(this);
96 }
97
98 bool TtsEngineExtensionObserver::IsLoadedTtsEngine(
99 const std::string& extension_id) {
100 extensions::ExtensionSystem* system =
101 extensions::ExtensionSystem::Get(profile_);
102 DCHECK(system);
103 extensions::EventRouter* event_router = system->event_router();
104 DCHECK(event_router);
105 if (event_router->ExtensionHasEventListener(extension_id,
106 tts_engine_events::kOnSpeak) &&
107 event_router->ExtensionHasEventListener(extension_id,
108 tts_engine_events::kOnStop)) {
109 return true;
110 }
111
112 return false;
113 }
114
115 void TtsEngineExtensionObserver::OnListenerAdded(
116 const extensions::EventListenerInfo& details) {
117 if (!IsLoadedTtsEngine(details.extension_id))
118 return;
119
120 if (!saw_tts_engine_added_) {
121 saw_tts_engine_added_ = true;
122 TtsController::GetInstance()->RetrySpeakingQueuedUtterances();
123 }
124
125 TtsController::GetInstance()->VoicesChanged();
dmazzoni 2014/07/07 15:37:26 Should this be before RetrySpeaking...?
David Tseng 2014/07/08 23:43:31 I didn't see a need since both calls are async. A
126 engine_extension_ids_.insert(details.extension_id);
127 }
128
129 void TtsEngineExtensionObserver::OnExtensionUnloaded(
130 content::BrowserContext* browser_context,
131 const extensions::Extension* extension,
132 extensions::UnloadedExtensionInfo::Reason reason) {
133 if (engine_extension_ids_.find(extension->id()) !=
134 engine_extension_ids_.end()) {
135 engine_extension_ids_.erase(extension->id());
136 TtsController::GetInstance()->VoicesChanged();
137 }
138 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698