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

Side by Side Diff: webrtc/sdk/objc/Framework/Classes/avfoundationvideocapturer.mm

Issue 2135953002: AVFoundationVideoCapturer: Output native frames instead of I420 frames (Closed) Base URL: https://chromium.googlesource.com/external/webrtc.git@master
Patch Set: Created 4 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
« no previous file with comments | « webrtc/sdk/objc/Framework/Classes/avfoundationvideocapturer.h ('k') | 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 /* 1 /*
2 * Copyright 2015 The WebRTC project authors. All Rights Reserved. 2 * Copyright 2015 The WebRTC project authors. All Rights Reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source 5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
11 #include "avfoundationvideocapturer.h" 11 #include "avfoundationvideocapturer.h"
12 12
13 #import <AVFoundation/AVFoundation.h> 13 #import <AVFoundation/AVFoundation.h>
14 #import <Foundation/Foundation.h> 14 #import <Foundation/Foundation.h>
15 #if TARGET_OS_IPHONE 15 #if TARGET_OS_IPHONE
16 #import <UIKit/UIKit.h> 16 #import <UIKit/UIKit.h>
17 #endif 17 #endif
18 18
19 #import "RTCDispatcher+Private.h" 19 #import "RTCDispatcher+Private.h"
20 #import "WebRTC/RTCLogging.h" 20 #import "WebRTC/RTCLogging.h"
21 21
22 #include "webrtc/base/bind.h" 22 #include "webrtc/base/bind.h"
23 #include "webrtc/base/checks.h" 23 #include "webrtc/base/checks.h"
24 #include "webrtc/base/thread.h" 24 #include "webrtc/base/thread.h"
25 #include "webrtc/common_video/include/corevideo_frame_buffer.h"
25 26
26 // TODO(tkchin): support other formats. 27 // TODO(tkchin): support other formats.
27 static NSString *const kDefaultPreset = AVCaptureSessionPreset640x480; 28 static NSString *const kDefaultPreset = AVCaptureSessionPreset640x480;
28 static cricket::VideoFormat const kDefaultFormat = 29 static cricket::VideoFormat const kDefaultFormat =
29 cricket::VideoFormat(640, 30 cricket::VideoFormat(640,
30 480, 31 480,
31 cricket::VideoFormat::FpsToInterval(30), 32 cricket::VideoFormat::FpsToInterval(30),
32 cricket::FOURCC_NV12); 33 cricket::FOURCC_NV12);
33 34
34 // This class used to capture frames using AVFoundation APIs on iOS. It is meant 35 // This class used to capture frames using AVFoundation APIs on iOS. It is meant
(...skipping 600 matching lines...) Expand 10 before | Expand all | Expand 10 after
635 static_cast<rtc::TypedMessageData<AVFoundationFrame>*>(msg->pdata); 636 static_cast<rtc::TypedMessageData<AVFoundationFrame>*>(msg->pdata);
636 const AVFoundationFrame& frame = data->data(); 637 const AVFoundationFrame& frame = data->data();
637 OnFrameMessage(frame.image_buffer, frame.capture_time); 638 OnFrameMessage(frame.image_buffer, frame.capture_time);
638 delete data; 639 delete data;
639 break; 640 break;
640 } 641 }
641 } 642 }
642 } 643 }
643 644
644 void AVFoundationVideoCapturer::OnFrameMessage(CVImageBufferRef image_buffer, 645 void AVFoundationVideoCapturer::OnFrameMessage(CVImageBufferRef image_buffer,
645 int64_t capture_time) { 646 int64_t capture_time_ns) {
646 RTC_DCHECK(_startThread->IsCurrent()); 647 RTC_DCHECK(_startThread->IsCurrent());
647 648
648 // Base address must be unlocked to access frame data. 649 rtc::scoped_refptr<webrtc::VideoFrameBuffer> buffer =
649 CVOptionFlags lock_flags = kCVPixelBufferLock_ReadOnly; 650 new rtc::RefCountedObject<webrtc::CoreVideoFrameBuffer>(image_buffer);
650 CVReturn ret = CVPixelBufferLockBaseAddress(image_buffer, lock_flags); 651
651 if (ret != kCVReturnSuccess) { 652 const int captured_width = buffer->width();
653 const int captured_height = buffer->height();
654
655 int adapted_width;
656 int adapted_height;
657 int crop_width;
658 int crop_height;
659 int crop_x;
660 int crop_y;
661 int64_t translated_camera_time_us;
662
663 if (!AdaptFrame(captured_width, captured_height,
tkchin_webrtc 2016/07/11 18:49:01 superclass no longer does adaptation? Just curious
magjed_webrtc 2016/07/12 14:42:18 Right, this function now bypasses all adapation in
664 capture_time_ns / rtc::kNumNanosecsPerMicrosec,
665 rtc::TimeMicros(), &adapted_width, &adapted_height,
666 &crop_width, &crop_height, &crop_x, &crop_y,
667 &translated_camera_time_us)) {
652 return; 668 return;
653 } 669 }
654 670
655 static size_t const kYPlaneIndex = 0; 671 if (adapted_width != captured_width || crop_width != captured_width ||
656 static size_t const kUVPlaneIndex = 1; 672 adapted_height != captured_height || crop_height != captured_height) {
657 uint8_t* y_plane_address = 673 // TODO(magjed): Avoid converting to I420.
658 static_cast<uint8_t*>(CVPixelBufferGetBaseAddressOfPlane(image_buffer, 674 rtc::scoped_refptr<webrtc::I420Buffer> scaled_buffer(
659 kYPlaneIndex)); 675 _buffer_pool.CreateBuffer(adapted_width, adapted_height));
660 size_t y_plane_height = 676 scaled_buffer->CropAndScaleFrom(buffer->NativeToI420Buffer(), crop_x,
661 CVPixelBufferGetHeightOfPlane(image_buffer, kYPlaneIndex); 677 crop_y, crop_width, crop_height);
662 size_t y_plane_width = 678 buffer = scaled_buffer;
663 CVPixelBufferGetWidthOfPlane(image_buffer, kYPlaneIndex); 679 }
664 size_t y_plane_bytes_per_row =
665 CVPixelBufferGetBytesPerRowOfPlane(image_buffer, kYPlaneIndex);
666 size_t uv_plane_height =
667 CVPixelBufferGetHeightOfPlane(image_buffer, kUVPlaneIndex);
668 size_t uv_plane_bytes_per_row =
669 CVPixelBufferGetBytesPerRowOfPlane(image_buffer, kUVPlaneIndex);
670 size_t frame_size = y_plane_bytes_per_row * y_plane_height +
671 uv_plane_bytes_per_row * uv_plane_height;
672 680
673 // Sanity check assumption that planar bytes are contiguous. 681 OnFrame(cricket::WebRtcVideoFrame(buffer, webrtc::kVideoRotation_0,
tkchin_webrtc 2016/07/11 18:49:01 Is this the new way to do things? (As opposed to S
magjed_webrtc 2016/07/12 14:42:18 Yes, the new OnFrame() method was added by nisse@
674 uint8_t* uv_plane_address = 682 translated_camera_time_us),
675 static_cast<uint8_t*>(CVPixelBufferGetBaseAddressOfPlane(image_buffer, 683 captured_width, captured_height);
676 kUVPlaneIndex));
677 RTC_DCHECK(uv_plane_address ==
678 y_plane_address + y_plane_height * y_plane_bytes_per_row);
679 684
680 // Stuff data into a cricket::CapturedFrame.
681 cricket::CapturedFrame frame;
682 frame.width = y_plane_width;
683 frame.height = y_plane_height;
684 frame.pixel_width = 1;
685 frame.pixel_height = 1;
686 frame.fourcc = static_cast<uint32_t>(cricket::FOURCC_NV12);
687 frame.time_stamp = capture_time;
688 frame.data = y_plane_address;
689 frame.data_size = frame_size;
690
691 // This will call a superclass method that will perform the frame conversion
692 // to I420.
693 SignalFrameCaptured(this, &frame);
694
695 CVPixelBufferUnlockBaseAddress(image_buffer, lock_flags);
696 CVBufferRelease(image_buffer); 685 CVBufferRelease(image_buffer);
697 } 686 }
698 687
699 } // namespace webrtc 688 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/sdk/objc/Framework/Classes/avfoundationvideocapturer.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698