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

Side by Side Diff: content/browser/device_monitor_mac.mm

Issue 188383004: Mac AVFoundation: clean removal of device observers (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 6 years, 9 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
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "content/browser/device_monitor_mac.h" 5 #include "content/browser/device_monitor_mac.h"
6 6
7 #import <QTKit/QTKit.h> 7 #import <QTKit/QTKit.h>
8 8
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/mac/scoped_nsobject.h" 10 #include "base/mac/scoped_nsobject.h"
(...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after
197 ![[device attributeForKey:QTCaptureDeviceSuspendedAttribute] 197 ![[device attributeForKey:QTCaptureDeviceSuspendedAttribute]
198 boolValue]) { 198 boolValue]) {
199 device_type = DeviceInfo::kAudio; 199 device_type = DeviceInfo::kAudio;
200 } 200 }
201 snapshot_devices.push_back( 201 snapshot_devices.push_back(
202 DeviceInfo([[device uniqueID] UTF8String], device_type)); 202 DeviceInfo([[device uniqueID] UTF8String], device_type));
203 } 203 }
204 ConsolidateDevicesListAndNotify(snapshot_devices); 204 ConsolidateDevicesListAndNotify(snapshot_devices);
205 } 205 }
206 206
207 // Forward declaration for use by CrAVFoundationSuspendObserver. 207 // Forward declaration for use by CrAVFoundationDeviceObserver.
208 class AVFoundationMonitorImpl; 208 class AVFoundationMonitorImpl;
209 209
210 } // namespace 210 } // namespace
211 211
212 // This class is a Key-Value Observer (KVO) shim. It is needed because C++ 212 // This class is a Key-Value Observer (KVO) shim. It is needed because C++
213 // classes cannot observe Key-Values directly. 213 // classes cannot observe Key-Values directly.
214 @interface CrAVFoundationSuspendObserver : NSObject { 214 @interface CrAVFoundationDeviceObserver : NSObject {
215 @private 215 @private
216 AVFoundationMonitorImpl* receiver_; 216 AVFoundationMonitorImpl* receiver_;
217 } 217 }
218 218
219 - (id)initWithChangeReceiver:(AVFoundationMonitorImpl*)receiver; 219 - (id)initWithChangeReceiver:(AVFoundationMonitorImpl*)receiver;
220 - (void)startObserving:(CrAVCaptureDevice*)device; 220 - (void)startObserving:(CrAVCaptureDevice*)device;
221 - (void)stopObserving:(CrAVCaptureDevice*)device; 221 - (void)stopObserving:(CrAVCaptureDevice*)device;
222 222
223 @end 223 @end
224 224
225 namespace { 225 namespace {
226 226
227 class AVFoundationMonitorImpl : public DeviceMonitorMacImpl { 227 class AVFoundationMonitorImpl : public DeviceMonitorMacImpl {
228 public: 228 public:
229 explicit AVFoundationMonitorImpl(content::DeviceMonitorMac* monitor); 229 explicit AVFoundationMonitorImpl(content::DeviceMonitorMac* monitor);
230 virtual ~AVFoundationMonitorImpl(); 230 virtual ~AVFoundationMonitorImpl();
231 231
232 virtual void OnDeviceChanged() OVERRIDE; 232 virtual void OnDeviceChanged() OVERRIDE;
233 233
234 private: 234 private:
235 base::scoped_nsobject<CrAVFoundationSuspendObserver> suspend_observer_; 235 base::scoped_nsobject<CrAVFoundationDeviceObserver> suspend_observer_;
236 DISALLOW_COPY_AND_ASSIGN(AVFoundationMonitorImpl); 236 DISALLOW_COPY_AND_ASSIGN(AVFoundationMonitorImpl);
237 }; 237 };
238 238
239 AVFoundationMonitorImpl::AVFoundationMonitorImpl( 239 AVFoundationMonitorImpl::AVFoundationMonitorImpl(
240 content::DeviceMonitorMac* monitor) 240 content::DeviceMonitorMac* monitor)
241 : DeviceMonitorMacImpl(monitor) { 241 : DeviceMonitorMacImpl(monitor) {
242 NSNotificationCenter* nc = [NSNotificationCenter defaultCenter]; 242 NSNotificationCenter* nc = [NSNotificationCenter defaultCenter];
243 device_arrival_ = 243 device_arrival_ =
244 [nc addObserverForName:AVFoundationGlue:: 244 [nc addObserverForName:AVFoundationGlue::
245 AVCaptureDeviceWasConnectedNotification() 245 AVCaptureDeviceWasConnectedNotification()
246 object:nil 246 object:nil
247 queue:nil 247 queue:nil
248 usingBlock:^(NSNotification* notification) { 248 usingBlock:^(NSNotification* notification) {
249 OnDeviceChanged();}]; 249 OnDeviceChanged();}];
250 device_removal_ = 250 device_removal_ =
251 [nc addObserverForName:AVFoundationGlue:: 251 [nc addObserverForName:AVFoundationGlue::
252 AVCaptureDeviceWasDisconnectedNotification() 252 AVCaptureDeviceWasDisconnectedNotification()
253 object:nil 253 object:nil
254 queue:nil 254 queue:nil
255 usingBlock:^(NSNotification* notification) { 255 usingBlock:^(NSNotification* notification) {
256 OnDeviceChanged();}]; 256 OnDeviceChanged();}];
257 suspend_observer_.reset( 257 suspend_observer_.reset(
258 [[CrAVFoundationSuspendObserver alloc] initWithChangeReceiver:this]); 258 [[CrAVFoundationDeviceObserver alloc] initWithChangeReceiver:this]);
259 for (CrAVCaptureDevice* device in [AVCaptureDeviceGlue devices]) 259 for (CrAVCaptureDevice* device in [AVCaptureDeviceGlue devices])
260 [suspend_observer_ startObserving:device]; 260 [suspend_observer_ startObserving:device];
261 } 261 }
262 262
263 AVFoundationMonitorImpl::~AVFoundationMonitorImpl() { 263 AVFoundationMonitorImpl::~AVFoundationMonitorImpl() {
264 NSNotificationCenter* nc = [NSNotificationCenter defaultCenter]; 264 NSNotificationCenter* nc = [NSNotificationCenter defaultCenter];
265 [nc removeObserver:device_arrival_]; 265 [nc removeObserver:device_arrival_];
266 [nc removeObserver:device_removal_]; 266 [nc removeObserver:device_removal_];
267 for (CrAVCaptureDevice* device in [AVCaptureDeviceGlue devices]) 267 for (CrAVCaptureDevice* device in [AVCaptureDeviceGlue devices])
268 [suspend_observer_ stopObserving:device]; 268 [suspend_observer_ stopObserving:device];
(...skipping 16 matching lines...) Expand all
285 device_type = DeviceInfo::kAudio; 285 device_type = DeviceInfo::kAudio;
286 } 286 }
287 snapshot_devices.push_back(DeviceInfo([[device uniqueID] UTF8String], 287 snapshot_devices.push_back(DeviceInfo([[device uniqueID] UTF8String],
288 device_type)); 288 device_type));
289 } 289 }
290 ConsolidateDevicesListAndNotify(snapshot_devices); 290 ConsolidateDevicesListAndNotify(snapshot_devices);
291 } 291 }
292 292
293 } // namespace 293 } // namespace
294 294
295 @implementation CrAVFoundationSuspendObserver 295 @implementation CrAVFoundationDeviceObserver
296 296
297 - (id)initWithChangeReceiver:(AVFoundationMonitorImpl*)receiver { 297 - (id)initWithChangeReceiver:(AVFoundationMonitorImpl*)receiver {
298 if ((self = [super init])) { 298 if ((self = [super init])) {
299 DCHECK(receiver != NULL); 299 DCHECK(receiver != NULL);
300 receiver_ = receiver; 300 receiver_ = receiver;
301 } 301 }
302 return self; 302 return self;
303 } 303 }
304 304
305 - (void)startObserving:(CrAVCaptureDevice*)device { 305 - (void)startObserving:(CrAVCaptureDevice*)device {
306 DCHECK(device != nil); 306 DCHECK(device != nil);
307 [device addObserver:self 307 [device addObserver:self
308 forKeyPath:@"suspended" 308 forKeyPath:@"suspended"
309 options:0 309 options:0
310 context:nil]; 310 context:device];
311 [device addObserver:self
312 forKeyPath:@"connected"
313 options:0
314 context:device];
311 } 315 }
312 316
313 - (void)stopObserving:(CrAVCaptureDevice*)device { 317 - (void)stopObserving:(CrAVCaptureDevice*)device {
314 DCHECK(device != nil); 318 DCHECK(device != nil);
315 [device removeObserver:self 319 [device removeObserver:self
316 forKeyPath:@"suspended"]; 320 forKeyPath:@"suspended"];
321 [device removeObserver:self
322 forKeyPath:@"connected"];
317 } 323 }
318 324
319 - (void)observeValueForKeyPath:(NSString*)keyPath 325 - (void)observeValueForKeyPath:(NSString*)keyPath
320 ofObject:(id)object 326 ofObject:(id)object
321 change:(NSDictionary*)change 327 change:(NSDictionary*)change
322 context:(void*)context { 328 context:(void*)context {
323 if ([keyPath isEqual:@"suspended"]) 329 if ([keyPath isEqual:@"suspended"])
324 receiver_->OnDeviceChanged(); 330 receiver_->OnDeviceChanged();
331 if ([keyPath isEqual:@"connected"]) {
Robert Sesek 2014/03/06 17:08:20 nit: you don't have braces around the other if, so
mcasas 2014/03/06 17:21:58 Done. Apologies, forgot them after removing debug
332 [self stopObserving:(CrAVCaptureDevice*)context];
Robert Sesek 2014/03/06 17:08:20 static_cast
mcasas 2014/03/06 17:21:58 Done.
333 }
325 } 334 }
326 335
327 @end // @implementation CrAVFoundationSuspendObserver 336 @end // @implementation CrAVFoundationDeviceObserver
328 337
329 namespace content { 338 namespace content {
330 339
331 DeviceMonitorMac::DeviceMonitorMac() { 340 DeviceMonitorMac::DeviceMonitorMac() {
332 if (AVFoundationGlue::IsAVFoundationSupported()) { 341 if (AVFoundationGlue::IsAVFoundationSupported()) {
333 DVLOG(1) << "Monitoring via AVFoundation"; 342 DVLOG(1) << "Monitoring via AVFoundation";
334 device_monitor_impl_.reset(new AVFoundationMonitorImpl(this)); 343 device_monitor_impl_.reset(new AVFoundationMonitorImpl(this));
335 // For the AVFoundation to start sending connect/disconnect notifications, 344 // For the AVFoundation to start sending connect/disconnect notifications,
336 // the AVFoundation NSBundle has to be loaded and the devices enumerated. 345 // the AVFoundation NSBundle has to be loaded and the devices enumerated.
337 // This operation seems to take in the range of hundred of ms. so should be 346 // This operation seems to take in the range of hundred of ms. so should be
338 // moved to the point when is needed, and that is during 347 // moved to the point when is needed, and that is during
339 // DeviceVideoCaptureMac +getDeviceNames. 348 // DeviceVideoCaptureMac +getDeviceNames.
340 } else { 349 } else {
341 DVLOG(1) << "Monitoring via QTKit"; 350 DVLOG(1) << "Monitoring via QTKit";
342 device_monitor_impl_.reset(new QTKitMonitorImpl(this)); 351 device_monitor_impl_.reset(new QTKitMonitorImpl(this));
343 } 352 }
344 } 353 }
345 354
346 DeviceMonitorMac::~DeviceMonitorMac() {} 355 DeviceMonitorMac::~DeviceMonitorMac() {}
347 356
348 void DeviceMonitorMac::NotifyDeviceChanged( 357 void DeviceMonitorMac::NotifyDeviceChanged(
349 base::SystemMonitor::DeviceType type) { 358 base::SystemMonitor::DeviceType type) {
350 // TODO(xians): Remove the global variable for SystemMonitor. 359 // TODO(xians): Remove the global variable for SystemMonitor.
351 base::SystemMonitor::Get()->ProcessDevicesChanged(type); 360 base::SystemMonitor::Get()->ProcessDevicesChanged(type);
352 } 361 }
353 362
354 } // namespace content 363 } // namespace content
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698