summaryrefslogtreecommitdiffstats
path: root/media/video
diff options
context:
space:
mode:
authormcasas@chromium.org <mcasas@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-04-01 08:48:00 +0000
committermcasas@chromium.org <mcasas@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2014-04-01 08:48:00 +0000
commitb1d26db2602f3b7ba8824995771da53e9af367f3 (patch)
tree89aec58efdfe019b9e8c2263178b522a58fce221 /media/video
parent5c963e67502659d49c28c81bbdd151ccbecce903 (diff)
downloadchromium_src-b1d26db2602f3b7ba8824995771da53e9af367f3.zip
chromium_src-b1d26db2602f3b7ba8824995771da53e9af367f3.tar.gz
chromium_src-b1d26db2602f3b7ba8824995771da53e9af367f3.tar.bz2
Add Project Tango video capture for Android
Project Tango is a special Android device [1]. It supports a number of special cameras, see bug. VideoCapture.java is divided into a base class and a VideoCaptureFactory. The base class VideoCapture.java abstracts most of the code commong to VideoCaptureAndroid and VideoCaptureTango, the two extensions. VideoCaptureFactory creates either a VideoCaptureAndroid (normal devices and Tango front facing camera), or a VideoCaptureTango if the device is identified as a Tango. This division clarifies the already large VideoCapture.java and is expected to be used further down the line in migrating VideoCaptureAndroid to using VideoFrames, hence reducing copies. The identification of the Tango comes from checking the android.os.Build.{MODEL,DEVICE} in the static class VideoCapture.ChromiumCameraInfo. The extra cameras are then added after the "normal" ones in the mId-indexed. list. Tested via [2], click on GetDevices, then open any of the listed cameras, "depth", "fisheye", "4MP". [1] http://www.google.com/atap/projecttango/ [1] https://src.chromium.org/svn/trunk/src/chrome/test/data/webrtc/manual/peerconnection.html BUG=352542 Review URL: https://codereview.chromium.org/151513006 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@260798 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'media/video')
-rw-r--r--media/video/capture/android/video_capture_device_android.cc108
-rw-r--r--media/video/capture/android/video_capture_device_android.h2
-rw-r--r--media/video/capture/android/video_capture_device_factory_android.cc111
-rw-r--r--media/video/capture/android/video_capture_device_factory_android.h40
4 files changed, 174 insertions, 87 deletions
diff --git a/media/video/capture/android/video_capture_device_android.cc b/media/video/capture/android/video_capture_device_android.cc
index dff396f..426be13 100644
--- a/media/video/capture/android/video_capture_device_android.cc
+++ b/media/video/capture/android/video_capture_device_android.cc
@@ -7,12 +7,10 @@
#include <string>
#include "base/android/jni_android.h"
-#include "base/android/jni_string.h"
#include "base/android/scoped_java_ref.h"
#include "base/strings/string_number_conversions.h"
-#include "base/strings/stringprintf.h"
#include "jni/VideoCapture_jni.h"
-#include "media/base/video_util.h"
+#include "media/video/capture/android/video_capture_device_factory_android.h"
using base::android::AttachCurrentThread;
using base::android::CheckException;
@@ -23,82 +21,17 @@ using base::android::ScopedJavaLocalRef;
namespace media {
-// static
+//static
void VideoCaptureDevice::GetDeviceNames(Names* device_names) {
- device_names->clear();
-
- JNIEnv* env = AttachCurrentThread();
-
- int num_cameras = Java_ChromiumCameraInfo_getNumberOfCameras(env);
- DVLOG(1) << "VideoCaptureDevice::GetDeviceNames: num_cameras=" << num_cameras;
- if (num_cameras <= 0)
- return;
-
- for (int camera_id = num_cameras - 1; camera_id >= 0; --camera_id) {
- ScopedJavaLocalRef<jobject> ci =
- Java_ChromiumCameraInfo_getAt(env, camera_id);
-
- Name name(
- base::android::ConvertJavaStringToUTF8(
- Java_ChromiumCameraInfo_getDeviceName(env, ci.obj())),
- base::StringPrintf("%d", Java_ChromiumCameraInfo_getId(env, ci.obj())));
- device_names->push_back(name);
-
- DVLOG(1) << "VideoCaptureDevice::GetDeviceNames: camera device_name="
- << name.name()
- << ", unique_id="
- << name.id()
- << ", orientation "
- << Java_ChromiumCameraInfo_getOrientation(env, ci.obj());
- }
+ VideoCaptureDeviceFactoryAndroid::GetDeviceNames(device_names);
}
// static
-void VideoCaptureDevice::GetDeviceSupportedFormats(const Name& device,
+void VideoCaptureDevice::GetDeviceSupportedFormats(
+ const Name& device,
VideoCaptureFormats* capture_formats) {
- int id;
- if (!base::StringToInt(device.id(), &id))
- return;
- JNIEnv* env = AttachCurrentThread();
- base::android::ScopedJavaLocalRef<jobjectArray> collected_formats =
- Java_VideoCapture_getDeviceSupportedFormats(env, id);
- if (collected_formats.is_null())
- return;
-
- jsize num_formats = env->GetArrayLength(collected_formats.obj());
- for (int i = 0; i < num_formats; ++i) {
- base::android::ScopedJavaLocalRef<jobject> format(
- env, env->GetObjectArrayElement(collected_formats.obj(), i));
-
- VideoPixelFormat pixel_format = media::PIXEL_FORMAT_UNKNOWN;
- switch (media::Java_CaptureFormat_getPixelFormat(env, format.obj())) {
- case VideoCaptureDeviceAndroid::ANDROID_IMAGEFORMAT_YV12:
- pixel_format = media::PIXEL_FORMAT_YV12;
- break;
- case VideoCaptureDeviceAndroid::ANDROID_IMAGEFORMAT_NV21:
- pixel_format = media::PIXEL_FORMAT_NV21;
- break;
- default:
- break;
- }
- VideoCaptureFormat capture_format(
- gfx::Size(media::Java_CaptureFormat_getWidth(env, format.obj()),
- media::Java_CaptureFormat_getHeight(env, format.obj())),
- media::Java_CaptureFormat_getFramerate(env, format.obj()),
- pixel_format);
- capture_formats->push_back(capture_format);
- DVLOG(1) << device.name() << " resolution: "
- << capture_format.frame_size.ToString() << ", fps: "
- << capture_format.frame_rate << ", pixel format: "
- << capture_format.pixel_format;
- }
-}
-
-const std::string VideoCaptureDevice::Name::GetModel() const {
- // Android cameras are not typically USB devices, and this method is currently
- // only used for USB model identifiers, so this implementation just indicates
- // an unknown device model.
- return "";
+ VideoCaptureDeviceFactoryAndroid::GetDeviceSupportedFormats(device,
+ capture_formats);
}
// static
@@ -120,6 +53,13 @@ bool VideoCaptureDeviceAndroid::RegisterVideoCaptureDevice(JNIEnv* env) {
return RegisterNativesImpl(env);
}
+const std::string VideoCaptureDevice::Name::GetModel() const {
+ // Android cameras are not typically USB devices, and this method is currently
+ // only used for USB model identifiers, so this implementation just indicates
+ // an unknown device model.
+ return "";
+}
+
VideoCaptureDeviceAndroid::VideoCaptureDeviceAndroid(const Name& device_name)
: state_(kIdle), got_first_frame_(false), device_name_(device_name) {}
@@ -132,12 +72,8 @@ bool VideoCaptureDeviceAndroid::Init() {
if (!base::StringToInt(device_name_.id(), &id))
return false;
- JNIEnv* env = AttachCurrentThread();
-
- j_capture_.Reset(Java_VideoCapture_createVideoCapture(
- env, base::android::GetApplicationContext(), id,
- reinterpret_cast<intptr_t>(this)));
-
+ j_capture_.Reset(VideoCaptureDeviceFactoryAndroid::createVideoCaptureAndroid(
+ id, reinterpret_cast<intptr_t>(this)));
return true;
}
@@ -155,12 +91,12 @@ void VideoCaptureDeviceAndroid::AllocateAndStart(
JNIEnv* env = AttachCurrentThread();
- jboolean ret =
- Java_VideoCapture_allocate(env,
- j_capture_.obj(),
- params.requested_format.frame_size.width(),
- params.requested_format.frame_size.height(),
- params.requested_format.frame_rate);
+ jboolean ret = Java_VideoCapture_allocate(
+ env,
+ j_capture_.obj(),
+ params.requested_format.frame_size.width(),
+ params.requested_format.frame_size.height(),
+ params.requested_format.frame_rate);
if (!ret) {
SetErrorState("failed to allocate");
return;
diff --git a/media/video/capture/android/video_capture_device_android.h b/media/video/capture/android/video_capture_device_android.h
index 4a59b8b..958036f 100644
--- a/media/video/capture/android/video_capture_device_android.h
+++ b/media/video/capture/android/video_capture_device_android.h
@@ -73,7 +73,7 @@ class MEDIA_EXPORT VideoCaptureDeviceAndroid : public VideoCaptureDevice {
VideoCaptureFormat capture_format_;
// Java VideoCaptureAndroid instance.
- base::android::ScopedJavaGlobalRef<jobject> j_capture_;
+ base::android::ScopedJavaLocalRef<jobject> j_capture_;
DISALLOW_IMPLICIT_CONSTRUCTORS(VideoCaptureDeviceAndroid);
};
diff --git a/media/video/capture/android/video_capture_device_factory_android.cc b/media/video/capture/android/video_capture_device_factory_android.cc
new file mode 100644
index 0000000..a473cb9
--- /dev/null
+++ b/media/video/capture/android/video_capture_device_factory_android.cc
@@ -0,0 +1,111 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "media/video/capture/android/video_capture_device_factory_android.h"
+
+#include "base/android/jni_string.h"
+#include "base/android/scoped_java_ref.h"
+#include "base/strings/string_number_conversions.h"
+#include "base/strings/stringprintf.h"
+#include "jni/VideoCaptureFactory_jni.h"
+
+using base::android::AttachCurrentThread;
+using base::android::ScopedJavaLocalRef;
+
+namespace media {
+
+// static
+void VideoCaptureDeviceFactoryAndroid::GetDeviceNames(
+ VideoCaptureDevice::Names* device_names) {
+ device_names->clear();
+
+ JNIEnv* env = AttachCurrentThread();
+
+ int num_cameras = Java_ChromiumCameraInfo_getNumberOfCameras(env);
+ DVLOG(1) << "VideoCaptureDevice::GetDeviceNames: num_cameras=" << num_cameras;
+ if (num_cameras <= 0)
+ return;
+
+ for (int camera_id = num_cameras - 1; camera_id >= 0; --camera_id) {
+ ScopedJavaLocalRef<jobject> ci =
+ Java_ChromiumCameraInfo_getAt(env, camera_id);
+
+ VideoCaptureDevice::Name name(
+ base::android::ConvertJavaStringToUTF8(
+ Java_ChromiumCameraInfo_getDeviceName(env, ci.obj())),
+ base::StringPrintf("%d", Java_ChromiumCameraInfo_getId(env, ci.obj())));
+ device_names->push_back(name);
+
+ DVLOG(1) << "VideoCaptureDeviceFactoryAndroid::GetDeviceNames: camera"
+ << "device_name=" << name.name() << ", unique_id=" << name.id()
+ << ", orientation "
+ << Java_ChromiumCameraInfo_getOrientation(env, ci.obj());
+ }
+}
+
+// static
+void VideoCaptureDeviceFactoryAndroid::GetDeviceSupportedFormats(
+ const VideoCaptureDevice::Name& device,
+ VideoCaptureFormats* capture_formats) {
+ int id;
+ if (!base::StringToInt(device.id(), &id))
+ return;
+ JNIEnv* env = AttachCurrentThread();
+ base::android::ScopedJavaLocalRef<jobjectArray> collected_formats =
+ Java_VideoCaptureFactory_getDeviceSupportedFormats(env, id);
+ if (collected_formats.is_null())
+ return;
+
+ jsize num_formats = env->GetArrayLength(collected_formats.obj());
+ for (int i = 0; i < num_formats; ++i) {
+ base::android::ScopedJavaLocalRef<jobject> format(
+ env, env->GetObjectArrayElement(collected_formats.obj(), i));
+
+ VideoPixelFormat pixel_format = media::PIXEL_FORMAT_UNKNOWN;
+ switch (media::Java_VideoCaptureFactory_getCaptureFormatPixelFormat(
+ env, format.obj())) {
+ case ANDROID_IMAGEFORMAT_YV12:
+ pixel_format = media::PIXEL_FORMAT_YV12;
+ break;
+ case ANDROID_IMAGEFORMAT_NV21:
+ pixel_format = media::PIXEL_FORMAT_NV21;
+ break;
+ default:
+ break;
+ }
+ VideoCaptureFormat capture_format(
+ gfx::Size(media::Java_VideoCaptureFactory_getCaptureFormatWidth(env,
+ format.obj()),
+ media::Java_VideoCaptureFactory_getCaptureFormatHeight(env,
+ format.obj())),
+ media::Java_VideoCaptureFactory_getCaptureFormatFramerate(env,
+ format.obj()),
+ pixel_format);
+ capture_formats->push_back(capture_format);
+ DVLOG(1) << device.name() << " resolution: "
+ << capture_format.frame_size.ToString() << ", fps: "
+ << capture_format.frame_rate << ", pixel format: "
+ << capture_format.pixel_format;
+ }
+}
+
+//static
+ScopedJavaLocalRef<jobject>
+VideoCaptureDeviceFactoryAndroid::createVideoCaptureAndroid(
+ int id,
+ jlong nativeVideoCaptureDeviceAndroid) {
+ return (Java_VideoCaptureFactory_createVideoCapture(
+ AttachCurrentThread(),
+ base::android::GetApplicationContext(),
+ id,
+ nativeVideoCaptureDeviceAndroid));
+}
+
+// static
+bool VideoCaptureDeviceFactoryAndroid::RegisterVideoCaptureDeviceFactory(
+ JNIEnv* env) {
+ return RegisterNativesImpl(env);
+}
+
+} // namespace media
diff --git a/media/video/capture/android/video_capture_device_factory_android.h b/media/video/capture/android/video_capture_device_factory_android.h
new file mode 100644
index 0000000..b52d4f0
--- /dev/null
+++ b/media/video/capture/android/video_capture_device_factory_android.h
@@ -0,0 +1,40 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef MEDIA_VIDEO_CAPTURE_ANDROID_VIDEO_CAPTURE_DEVICE_FACTORY_ANDROID_H_
+#define MEDIA_VIDEO_CAPTURE_ANDROID_VIDEO_CAPTURE_DEVICE_FACTORY_ANDROID_H_
+
+#include <jni.h>
+
+#include "base/android/scoped_java_ref.h"
+#include "media/video/capture/video_capture_device.h"
+
+namespace media {
+
+// VideoCaptureDeviceFactory on Android. This class implements the static
+// VideoCapture methods and the factory of VideoCaptureAndroid.
+class MEDIA_EXPORT VideoCaptureDeviceFactoryAndroid {
+ public:
+ // Automatically generated enum to interface with Java world.
+ enum AndroidImageFormat {
+#define DEFINE_ANDROID_IMAGEFORMAT(name, value) name = value,
+#include "media/video/capture/android/imageformat_list.h"
+#undef DEFINE_ANDROID_IMAGEFORMAT
+ };
+
+ virtual ~VideoCaptureDeviceFactoryAndroid();
+
+ static void GetDeviceNames(VideoCaptureDevice::Names* device_names);
+ static void GetDeviceSupportedFormats(
+ const VideoCaptureDevice::Name& device,
+ VideoCaptureFormats* capture_formats);
+ static bool RegisterVideoCaptureDeviceFactory(JNIEnv* env);
+ static base::android::ScopedJavaLocalRef<jobject> createVideoCaptureAndroid(
+ int id,
+ jlong nativeVideoCaptureDeviceAndroid);
+};
+
+} // namespace media
+
+#endif // MEDIA_VIDEO_CAPTURE_ANDROID_VIDEO_CAPTURE_DEVICE_FACTORY_ANDROID_H_