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

Side by Side Diff: webrtc/sdk/android/src/jni/native_handle_impl.cc

Issue 3009613002: Android: Replace webrtc_jni namespace with nested jni namespace (Closed)
Patch Set: Rebase Created 3 years, 3 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
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 "webrtc/sdk/android/src/jni/native_handle_impl.h" 11 #include "webrtc/sdk/android/src/jni/native_handle_impl.h"
12 12
13 #include <memory> 13 #include <memory>
14 14
15 #include "webrtc/common_video/include/video_frame_buffer.h" 15 #include "webrtc/common_video/include/video_frame_buffer.h"
16 #include "webrtc/rtc_base/bind.h" 16 #include "webrtc/rtc_base/bind.h"
17 #include "webrtc/rtc_base/checks.h" 17 #include "webrtc/rtc_base/checks.h"
18 #include "webrtc/rtc_base/keep_ref_until_done.h" 18 #include "webrtc/rtc_base/keep_ref_until_done.h"
19 #include "webrtc/rtc_base/logging.h" 19 #include "webrtc/rtc_base/logging.h"
20 #include "webrtc/rtc_base/scoped_ref_ptr.h" 20 #include "webrtc/rtc_base/scoped_ref_ptr.h"
21 #include "webrtc/rtc_base/timeutils.h" 21 #include "webrtc/rtc_base/timeutils.h"
22 #include "webrtc/sdk/android/src/jni/classreferenceholder.h" 22 #include "webrtc/sdk/android/src/jni/classreferenceholder.h"
23 #include "webrtc/sdk/android/src/jni/jni_helpers.h" 23 #include "webrtc/sdk/android/src/jni/jni_helpers.h"
24 #include "webrtc/sdk/android/src/jni/wrapped_native_i420_buffer.h" 24 #include "webrtc/sdk/android/src/jni/wrapped_native_i420_buffer.h"
25 #include "webrtc/system_wrappers/include/aligned_malloc.h" 25 #include "webrtc/system_wrappers/include/aligned_malloc.h"
26 26
27 namespace webrtc_jni { 27 namespace webrtc {
28 namespace jni {
28 29
29 namespace { 30 namespace {
30 31
31 class AndroidVideoI420Buffer : public webrtc::I420BufferInterface { 32 class AndroidVideoI420Buffer : public I420BufferInterface {
32 public: 33 public:
33 // Wraps an existing reference to a Java VideoBuffer. Retain will not be 34 // Wraps an existing reference to a Java VideoBuffer. Retain will not be
34 // called but release will be called when the C++ object is destroyed. 35 // called but release will be called when the C++ object is destroyed.
35 static rtc::scoped_refptr<AndroidVideoI420Buffer> WrapReference( 36 static rtc::scoped_refptr<AndroidVideoI420Buffer> WrapReference(
36 JNIEnv* jni, 37 JNIEnv* jni,
37 jmethodID j_release_id, 38 jmethodID j_release_id,
38 int width, 39 int width,
39 int height, 40 int height,
40 jobject j_video_frame_buffer); 41 jobject j_video_frame_buffer);
41 42
(...skipping 118 matching lines...) Expand 10 before | Expand all | Expand 10 after
160 } 161 }
161 jni->ReleaseFloatArrayElements(a, ptr, 0); 162 jni->ReleaseFloatArrayElements(a, ptr, 0);
162 } 163 }
163 164
164 jfloatArray Matrix::ToJava(JNIEnv* jni) const { 165 jfloatArray Matrix::ToJava(JNIEnv* jni) const {
165 jfloatArray matrix = jni->NewFloatArray(16); 166 jfloatArray matrix = jni->NewFloatArray(16);
166 jni->SetFloatArrayRegion(matrix, 0, 16, elem_); 167 jni->SetFloatArrayRegion(matrix, 0, 16, elem_);
167 return matrix; 168 return matrix;
168 } 169 }
169 170
170 void Matrix::Rotate(webrtc::VideoRotation rotation) { 171 void Matrix::Rotate(VideoRotation rotation) {
171 // Texture coordinates are in the range 0 to 1. The transformation of the last 172 // Texture coordinates are in the range 0 to 1. The transformation of the last
172 // row in each rotation matrix is needed for proper translation, e.g, to 173 // row in each rotation matrix is needed for proper translation, e.g, to
173 // mirror x, we don't replace x by -x, but by 1-x. 174 // mirror x, we don't replace x by -x, but by 1-x.
174 switch (rotation) { 175 switch (rotation) {
175 case webrtc::kVideoRotation_0: 176 case kVideoRotation_0:
176 break; 177 break;
177 case webrtc::kVideoRotation_90: { 178 case kVideoRotation_90: {
178 const float ROTATE_90[16] = 179 const float ROTATE_90[16] =
179 { elem_[4], elem_[5], elem_[6], elem_[7], 180 { elem_[4], elem_[5], elem_[6], elem_[7],
180 -elem_[0], -elem_[1], -elem_[2], -elem_[3], 181 -elem_[0], -elem_[1], -elem_[2], -elem_[3],
181 elem_[8], elem_[9], elem_[10], elem_[11], 182 elem_[8], elem_[9], elem_[10], elem_[11],
182 elem_[0] + elem_[12], elem_[1] + elem_[13], 183 elem_[0] + elem_[12], elem_[1] + elem_[13],
183 elem_[2] + elem_[14], elem_[3] + elem_[15]}; 184 elem_[2] + elem_[14], elem_[3] + elem_[15]};
184 memcpy(elem_, ROTATE_90, sizeof(elem_)); 185 memcpy(elem_, ROTATE_90, sizeof(elem_));
185 } break; 186 } break;
186 case webrtc::kVideoRotation_180: { 187 case kVideoRotation_180: {
187 const float ROTATE_180[16] = 188 const float ROTATE_180[16] =
188 { -elem_[0], -elem_[1], -elem_[2], -elem_[3], 189 { -elem_[0], -elem_[1], -elem_[2], -elem_[3],
189 -elem_[4], -elem_[5], -elem_[6], -elem_[7], 190 -elem_[4], -elem_[5], -elem_[6], -elem_[7],
190 elem_[8], elem_[9], elem_[10], elem_[11], 191 elem_[8], elem_[9], elem_[10], elem_[11],
191 elem_[0] + elem_[4] + elem_[12], elem_[1] + elem_[5] + elem_[13], 192 elem_[0] + elem_[4] + elem_[12], elem_[1] + elem_[5] + elem_[13],
192 elem_[2] + elem_[6] + elem_[14], elem_[3] + elem_[11]+ elem_[15]}; 193 elem_[2] + elem_[6] + elem_[14], elem_[3] + elem_[11]+ elem_[15]};
193 memcpy(elem_, ROTATE_180, sizeof(elem_)); 194 memcpy(elem_, ROTATE_180, sizeof(elem_));
194 } break; 195 } break;
195 case webrtc::kVideoRotation_270: { 196 case kVideoRotation_270: {
196 const float ROTATE_270[16] = 197 const float ROTATE_270[16] =
197 { -elem_[4], -elem_[5], -elem_[6], -elem_[7], 198 { -elem_[4], -elem_[5], -elem_[6], -elem_[7],
198 elem_[0], elem_[1], elem_[2], elem_[3], 199 elem_[0], elem_[1], elem_[2], elem_[3],
199 elem_[8], elem_[9], elem_[10], elem_[11], 200 elem_[8], elem_[9], elem_[10], elem_[11],
200 elem_[4] + elem_[12], elem_[5] + elem_[13], 201 elem_[4] + elem_[12], elem_[5] + elem_[13],
201 elem_[6] + elem_[14], elem_[7] + elem_[15]}; 202 elem_[6] + elem_[14], elem_[7] + elem_[15]};
202 memcpy(elem_, ROTATE_270, sizeof(elem_)); 203 memcpy(elem_, ROTATE_270, sizeof(elem_));
203 } break; 204 } break;
204 } 205 }
205 } 206 }
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
254 : width_(width), 255 : width_(width),
255 height_(height), 256 height_(height),
256 native_handle_(native_handle), 257 native_handle_(native_handle),
257 surface_texture_helper_(surface_texture_helper), 258 surface_texture_helper_(surface_texture_helper),
258 no_longer_used_cb_(no_longer_used) {} 259 no_longer_used_cb_(no_longer_used) {}
259 260
260 AndroidTextureBuffer::~AndroidTextureBuffer() { 261 AndroidTextureBuffer::~AndroidTextureBuffer() {
261 no_longer_used_cb_(); 262 no_longer_used_cb_();
262 } 263 }
263 264
264 webrtc::VideoFrameBuffer::Type AndroidTextureBuffer::type() const { 265 VideoFrameBuffer::Type AndroidTextureBuffer::type() const {
265 return Type::kNative; 266 return Type::kNative;
266 } 267 }
267 268
268 NativeHandleImpl AndroidTextureBuffer::native_handle_impl() const { 269 NativeHandleImpl AndroidTextureBuffer::native_handle_impl() const {
269 return native_handle_; 270 return native_handle_;
270 } 271 }
271 272
272 int AndroidTextureBuffer::width() const { 273 int AndroidTextureBuffer::width() const {
273 return width_; 274 return width_;
274 } 275 }
275 276
276 int AndroidTextureBuffer::height() const { 277 int AndroidTextureBuffer::height() const {
277 return height_; 278 return height_;
278 } 279 }
279 280
280 rtc::scoped_refptr<webrtc::I420BufferInterface> AndroidTextureBuffer::ToI420() { 281 rtc::scoped_refptr<I420BufferInterface> AndroidTextureBuffer::ToI420() {
281 int uv_width = (width() + 7) / 8; 282 int uv_width = (width() + 7) / 8;
282 int stride = 8 * uv_width; 283 int stride = 8 * uv_width;
283 int uv_height = (height() + 1) / 2; 284 int uv_height = (height() + 1) / 2;
284 size_t size = stride * (height() + uv_height); 285 size_t size = stride * (height() + uv_height);
285 // The data is owned by the frame, and the normal case is that the 286 // The data is owned by the frame, and the normal case is that the
286 // data is deleted by the frame's destructor callback. 287 // data is deleted by the frame's destructor callback.
287 // 288 //
288 // TODO(nisse): Use an I420BufferPool. We then need to extend that 289 // TODO(nisse): Use an I420BufferPool. We then need to extend that
289 // class, and I420Buffer, to support our memory layout. 290 // class, and I420Buffer, to support our memory layout.
290 // TODO(nisse): Depending on 291 // TODO(nisse): Depending on
291 // system_wrappers/include/aligned_malloc.h violate current DEPS 292 // system_wrappers/include/aligned_malloc.h violate current DEPS
292 // rules. We get away for now only because it is indirectly included 293 // rules. We get away for now only because it is indirectly included
293 // by i420_buffer.h 294 // by i420_buffer.h
294 std::unique_ptr<uint8_t, webrtc::AlignedFreeDeleter> yuv_data( 295 std::unique_ptr<uint8_t, AlignedFreeDeleter> yuv_data(
295 static_cast<uint8_t*>(webrtc::AlignedMalloc(size, kBufferAlignment))); 296 static_cast<uint8_t*>(AlignedMalloc(size, kBufferAlignment)));
296 // See YuvConverter.java for the required layout. 297 // See YuvConverter.java for the required layout.
297 uint8_t* y_data = yuv_data.get(); 298 uint8_t* y_data = yuv_data.get();
298 uint8_t* u_data = y_data + height() * stride; 299 uint8_t* u_data = y_data + height() * stride;
299 uint8_t* v_data = u_data + stride/2; 300 uint8_t* v_data = u_data + stride/2;
300 301
301 rtc::scoped_refptr<webrtc::I420BufferInterface> copy = webrtc::WrapI420Buffer( 302 rtc::scoped_refptr<I420BufferInterface> copy = webrtc::WrapI420Buffer(
302 width(), height(), y_data, stride, u_data, stride, v_data, stride, 303 width(), height(), y_data, stride, u_data, stride, v_data, stride,
303 rtc::Bind(&webrtc::AlignedFree, yuv_data.release())); 304 rtc::Bind(&AlignedFree, yuv_data.release()));
304 305
305 JNIEnv* jni = AttachCurrentThreadIfNeeded(); 306 JNIEnv* jni = AttachCurrentThreadIfNeeded();
306 ScopedLocalRefFrame local_ref_frame(jni); 307 ScopedLocalRefFrame local_ref_frame(jni);
307 308
308 jmethodID transform_mid = GetMethodID( 309 jmethodID transform_mid = GetMethodID(
309 jni, 310 jni,
310 GetObjectClass(jni, surface_texture_helper_), 311 GetObjectClass(jni, surface_texture_helper_),
311 "textureToYUV", 312 "textureToYUV",
312 "(Ljava/nio/ByteBuffer;IIII[F)V"); 313 "(Ljava/nio/ByteBuffer;IIII[F)V");
313 314
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
359 360
360 AndroidVideoBuffer::~AndroidVideoBuffer() { 361 AndroidVideoBuffer::~AndroidVideoBuffer() {
361 JNIEnv* jni = AttachCurrentThreadIfNeeded(); 362 JNIEnv* jni = AttachCurrentThreadIfNeeded();
362 jni->CallVoidMethod(*j_video_frame_buffer_, j_release_id_); 363 jni->CallVoidMethod(*j_video_frame_buffer_, j_release_id_);
363 } 364 }
364 365
365 jobject AndroidVideoBuffer::video_frame_buffer() const { 366 jobject AndroidVideoBuffer::video_frame_buffer() const {
366 return *j_video_frame_buffer_; 367 return *j_video_frame_buffer_;
367 } 368 }
368 369
369 webrtc::VideoFrameBuffer::Type AndroidVideoBuffer::type() const { 370 VideoFrameBuffer::Type AndroidVideoBuffer::type() const {
370 return Type::kNative; 371 return Type::kNative;
371 } 372 }
372 373
373 int AndroidVideoBuffer::width() const { 374 int AndroidVideoBuffer::width() const {
374 return width_; 375 return width_;
375 } 376 }
376 377
377 int AndroidVideoBuffer::height() const { 378 int AndroidVideoBuffer::height() const {
378 return height_; 379 return height_;
379 } 380 }
380 381
381 rtc::scoped_refptr<webrtc::I420BufferInterface> AndroidVideoBuffer::ToI420() { 382 rtc::scoped_refptr<I420BufferInterface> AndroidVideoBuffer::ToI420() {
382 JNIEnv* jni = AttachCurrentThreadIfNeeded(); 383 JNIEnv* jni = AttachCurrentThreadIfNeeded();
383 ScopedLocalRefFrame local_ref_frame(jni); 384 ScopedLocalRefFrame local_ref_frame(jni);
384 385
385 jclass j_video_frame_buffer_class = 386 jclass j_video_frame_buffer_class =
386 FindClass(jni, "org/webrtc/VideoFrame$Buffer"); 387 FindClass(jni, "org/webrtc/VideoFrame$Buffer");
387 jmethodID j_to_i420_id = 388 jmethodID j_to_i420_id =
388 jni->GetMethodID(j_video_frame_buffer_class, "toI420", 389 jni->GetMethodID(j_video_frame_buffer_class, "toI420",
389 "()Lorg/webrtc/VideoFrame$I420Buffer;"); 390 "()Lorg/webrtc/VideoFrame$I420Buffer;");
390 391
391 jobject j_i420_buffer = 392 jobject j_i420_buffer =
392 jni->CallObjectMethod(*j_video_frame_buffer_, j_to_i420_id); 393 jni->CallObjectMethod(*j_video_frame_buffer_, j_to_i420_id);
393 394
394 // We don't need to retain the buffer because toI420 returns a new object that 395 // We don't need to retain the buffer because toI420 returns a new object that
395 // we are assumed to take the ownership of. 396 // we are assumed to take the ownership of.
396 return AndroidVideoI420Buffer::WrapReference(jni, j_release_id_, width_, 397 return AndroidVideoI420Buffer::WrapReference(jni, j_release_id_, width_,
397 height_, j_i420_buffer); 398 height_, j_i420_buffer);
398 } 399 }
399 400
400 jobject AndroidVideoBuffer::ToJavaI420Frame(JNIEnv* jni, int rotation) { 401 jobject AndroidVideoBuffer::ToJavaI420Frame(JNIEnv* jni, int rotation) {
401 jclass j_byte_buffer_class = jni->FindClass("java/nio/ByteBuffer"); 402 jclass j_byte_buffer_class = jni->FindClass("java/nio/ByteBuffer");
402 jclass j_i420_frame_class = 403 jclass j_i420_frame_class =
403 FindClass(jni, "org/webrtc/VideoRenderer$I420Frame"); 404 FindClass(jni, "org/webrtc/VideoRenderer$I420Frame");
404 jmethodID j_i420_frame_ctor_id = GetMethodID( 405 jmethodID j_i420_frame_ctor_id = GetMethodID(
405 jni, j_i420_frame_class, "<init>", "(ILorg/webrtc/VideoFrame$Buffer;J)V"); 406 jni, j_i420_frame_class, "<init>", "(ILorg/webrtc/VideoFrame$Buffer;J)V");
406 // Java code just uses the native frame to hold a reference to the buffer so 407 // Java code just uses the native frame to hold a reference to the buffer so
407 // this is okay. 408 // this is okay.
408 webrtc::VideoFrame* native_frame = new webrtc::VideoFrame( 409 VideoFrame* native_frame =
409 this, 0 /* timestamp */, 0 /* render_time_ms */, 410 new VideoFrame(this, 0 /* timestamp */, 0 /* render_time_ms */,
410 webrtc::VideoRotation::kVideoRotation_0 /* rotation */); 411 VideoRotation::kVideoRotation_0 /* rotation */);
411 return jni->NewObject(j_i420_frame_class, j_i420_frame_ctor_id, rotation, 412 return jni->NewObject(j_i420_frame_class, j_i420_frame_ctor_id, rotation,
412 *j_video_frame_buffer_, jlongFromPointer(native_frame)); 413 *j_video_frame_buffer_, jlongFromPointer(native_frame));
413 } 414 }
414 415
415 AndroidVideoBufferFactory::AndroidVideoBufferFactory(JNIEnv* jni) 416 AndroidVideoBufferFactory::AndroidVideoBufferFactory(JNIEnv* jni)
416 : j_video_frame_class_(jni, FindClass(jni, "org/webrtc/VideoFrame")), 417 : j_video_frame_class_(jni, FindClass(jni, "org/webrtc/VideoFrame")),
417 j_get_buffer_id_(GetMethodID(jni, 418 j_get_buffer_id_(GetMethodID(jni,
418 *j_video_frame_class_, 419 *j_video_frame_class_,
419 "getBuffer", 420 "getBuffer",
420 "()Lorg/webrtc/VideoFrame$Buffer;")), 421 "()Lorg/webrtc/VideoFrame$Buffer;")),
421 j_get_rotation_id_( 422 j_get_rotation_id_(
422 GetMethodID(jni, *j_video_frame_class_, "getRotation", "()I")), 423 GetMethodID(jni, *j_video_frame_class_, "getRotation", "()I")),
423 j_get_timestamp_ns_id_( 424 j_get_timestamp_ns_id_(
424 GetMethodID(jni, *j_video_frame_class_, "getTimestampNs", "()J")), 425 GetMethodID(jni, *j_video_frame_class_, "getTimestampNs", "()J")),
425 j_video_frame_buffer_class_( 426 j_video_frame_buffer_class_(
426 jni, 427 jni,
427 FindClass(jni, "org/webrtc/VideoFrame$Buffer")), 428 FindClass(jni, "org/webrtc/VideoFrame$Buffer")),
428 j_retain_id_( 429 j_retain_id_(
429 GetMethodID(jni, *j_video_frame_buffer_class_, "retain", "()V")), 430 GetMethodID(jni, *j_video_frame_buffer_class_, "retain", "()V")),
430 j_release_id_( 431 j_release_id_(
431 GetMethodID(jni, *j_video_frame_buffer_class_, "release", "()V")), 432 GetMethodID(jni, *j_video_frame_buffer_class_, "release", "()V")),
432 j_get_width_id_( 433 j_get_width_id_(
433 GetMethodID(jni, *j_video_frame_buffer_class_, "getWidth", "()I")), 434 GetMethodID(jni, *j_video_frame_buffer_class_, "getWidth", "()I")),
434 j_get_height_id_( 435 j_get_height_id_(
435 GetMethodID(jni, *j_video_frame_buffer_class_, "getHeight", "()I")) {} 436 GetMethodID(jni, *j_video_frame_buffer_class_, "getHeight", "()I")) {}
436 437
437 webrtc::VideoFrame AndroidVideoBufferFactory::CreateFrame( 438 VideoFrame AndroidVideoBufferFactory::CreateFrame(
438 JNIEnv* jni, 439 JNIEnv* jni,
439 jobject j_video_frame, 440 jobject j_video_frame,
440 uint32_t timestamp_rtp) const { 441 uint32_t timestamp_rtp) const {
441 jobject j_video_frame_buffer = 442 jobject j_video_frame_buffer =
442 jni->CallObjectMethod(j_video_frame, j_get_buffer_id_); 443 jni->CallObjectMethod(j_video_frame, j_get_buffer_id_);
443 int rotation = jni->CallIntMethod(j_video_frame, j_get_rotation_id_); 444 int rotation = jni->CallIntMethod(j_video_frame, j_get_rotation_id_);
444 uint32_t timestamp_ns = 445 uint32_t timestamp_ns =
445 jni->CallLongMethod(j_video_frame, j_get_timestamp_ns_id_); 446 jni->CallLongMethod(j_video_frame, j_get_timestamp_ns_id_);
446 rtc::scoped_refptr<AndroidVideoBuffer> buffer = 447 rtc::scoped_refptr<AndroidVideoBuffer> buffer =
447 CreateBuffer(jni, j_video_frame_buffer); 448 CreateBuffer(jni, j_video_frame_buffer);
448 return webrtc::VideoFrame(buffer, timestamp_rtp, 449 return VideoFrame(buffer, timestamp_rtp,
449 timestamp_ns / rtc::kNumNanosecsPerMillisec, 450 timestamp_ns / rtc::kNumNanosecsPerMillisec,
450 static_cast<webrtc::VideoRotation>(rotation)); 451 static_cast<VideoRotation>(rotation));
451 } 452 }
452 453
453 rtc::scoped_refptr<AndroidVideoBuffer> AndroidVideoBufferFactory::WrapBuffer( 454 rtc::scoped_refptr<AndroidVideoBuffer> AndroidVideoBufferFactory::WrapBuffer(
454 JNIEnv* jni, 455 JNIEnv* jni,
455 jobject j_video_frame_buffer) const { 456 jobject j_video_frame_buffer) const {
456 int width = jni->CallIntMethod(j_video_frame_buffer, j_get_width_id_); 457 int width = jni->CallIntMethod(j_video_frame_buffer, j_get_width_id_);
457 int height = jni->CallIntMethod(j_video_frame_buffer, j_get_height_id_); 458 int height = jni->CallIntMethod(j_video_frame_buffer, j_get_height_id_);
458 return AndroidVideoBuffer::WrapReference(jni, j_release_id_, width, height, 459 return AndroidVideoBuffer::WrapReference(jni, j_release_id_, width, height,
459 j_video_frame_buffer); 460 j_video_frame_buffer);
460 } 461 }
461 462
462 rtc::scoped_refptr<AndroidVideoBuffer> AndroidVideoBufferFactory::CreateBuffer( 463 rtc::scoped_refptr<AndroidVideoBuffer> AndroidVideoBufferFactory::CreateBuffer(
463 JNIEnv* jni, 464 JNIEnv* jni,
464 jobject j_video_frame_buffer) const { 465 jobject j_video_frame_buffer) const {
465 int width = jni->CallIntMethod(j_video_frame_buffer, j_get_width_id_); 466 int width = jni->CallIntMethod(j_video_frame_buffer, j_get_width_id_);
466 int height = jni->CallIntMethod(j_video_frame_buffer, j_get_height_id_); 467 int height = jni->CallIntMethod(j_video_frame_buffer, j_get_height_id_);
467 return new rtc::RefCountedObject<AndroidVideoBuffer>( 468 return new rtc::RefCountedObject<AndroidVideoBuffer>(
468 jni, j_retain_id_, j_release_id_, width, height, j_video_frame_buffer); 469 jni, j_retain_id_, j_release_id_, width, height, j_video_frame_buffer);
469 } 470 }
470 471
471 JavaVideoFrameFactory::JavaVideoFrameFactory(JNIEnv* jni) 472 JavaVideoFrameFactory::JavaVideoFrameFactory(JNIEnv* jni)
472 : j_video_frame_class_(jni, FindClass(jni, "org/webrtc/VideoFrame")) { 473 : j_video_frame_class_(jni, FindClass(jni, "org/webrtc/VideoFrame")) {
473 j_video_frame_constructor_id_ = 474 j_video_frame_constructor_id_ =
474 GetMethodID(jni, *j_video_frame_class_, "<init>", 475 GetMethodID(jni, *j_video_frame_class_, "<init>",
475 "(Lorg/webrtc/VideoFrame$Buffer;IJ)V"); 476 "(Lorg/webrtc/VideoFrame$Buffer;IJ)V");
476 } 477 }
477 478
478 static bool IsJavaVideoBuffer( 479 static bool IsJavaVideoBuffer(rtc::scoped_refptr<VideoFrameBuffer> buffer) {
479 rtc::scoped_refptr<webrtc::VideoFrameBuffer> buffer) { 480 if (buffer->type() != VideoFrameBuffer::Type::kNative) {
480 if (buffer->type() != webrtc::VideoFrameBuffer::Type::kNative) {
481 return false; 481 return false;
482 } 482 }
483 AndroidVideoFrameBuffer* android_buffer = 483 AndroidVideoFrameBuffer* android_buffer =
484 static_cast<AndroidVideoFrameBuffer*>(buffer.get()); 484 static_cast<AndroidVideoFrameBuffer*>(buffer.get());
485 return android_buffer->android_type() == 485 return android_buffer->android_type() ==
486 AndroidVideoFrameBuffer::AndroidType::kJavaBuffer; 486 AndroidVideoFrameBuffer::AndroidType::kJavaBuffer;
487 } 487 }
488 488
489 jobject JavaVideoFrameFactory::ToJavaFrame( 489 jobject JavaVideoFrameFactory::ToJavaFrame(JNIEnv* jni,
490 JNIEnv* jni, 490 const VideoFrame& frame) const {
491 const webrtc::VideoFrame& frame) const { 491 rtc::scoped_refptr<VideoFrameBuffer> buffer = frame.video_frame_buffer();
492 rtc::scoped_refptr<webrtc::VideoFrameBuffer> buffer =
493 frame.video_frame_buffer();
494 jobject j_buffer; 492 jobject j_buffer;
495 if (IsJavaVideoBuffer(buffer)) { 493 if (IsJavaVideoBuffer(buffer)) {
496 RTC_DCHECK(buffer->type() == webrtc::VideoFrameBuffer::Type::kNative); 494 RTC_DCHECK(buffer->type() == VideoFrameBuffer::Type::kNative);
497 AndroidVideoFrameBuffer* android_buffer = 495 AndroidVideoFrameBuffer* android_buffer =
498 static_cast<AndroidVideoFrameBuffer*>(buffer.get()); 496 static_cast<AndroidVideoFrameBuffer*>(buffer.get());
499 RTC_DCHECK(android_buffer->android_type() == 497 RTC_DCHECK(android_buffer->android_type() ==
500 AndroidVideoFrameBuffer::AndroidType::kJavaBuffer); 498 AndroidVideoFrameBuffer::AndroidType::kJavaBuffer);
501 AndroidVideoBuffer* android_video_buffer = 499 AndroidVideoBuffer* android_video_buffer =
502 static_cast<AndroidVideoBuffer*>(android_buffer); 500 static_cast<AndroidVideoBuffer*>(android_buffer);
503 j_buffer = android_video_buffer->video_frame_buffer(); 501 j_buffer = android_video_buffer->video_frame_buffer();
504 } else { 502 } else {
505 j_buffer = WrapI420Buffer(jni, buffer->ToI420()); 503 j_buffer = WrapI420Buffer(jni, buffer->ToI420());
506 } 504 }
507 return jni->NewObject( 505 return jni->NewObject(
508 *j_video_frame_class_, j_video_frame_constructor_id_, j_buffer, 506 *j_video_frame_class_, j_video_frame_constructor_id_, j_buffer,
509 static_cast<jint>(frame.rotation()), 507 static_cast<jint>(frame.rotation()),
510 static_cast<jlong>(frame.timestamp_us() * rtc::kNumNanosecsPerMicrosec)); 508 static_cast<jlong>(frame.timestamp_us() * rtc::kNumNanosecsPerMicrosec));
511 } 509 }
512 510
513 } // namespace webrtc_jni 511 } // namespace jni
512 } // namespace webrtc
OLDNEW
« no previous file with comments | « webrtc/sdk/android/src/jni/native_handle_impl.h ('k') | webrtc/sdk/android/src/jni/nv12buffer_jni.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698