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

Side by Side Diff: media/base/android/media_codec_bridge.cc

Issue 23517002: MediaSourcePlayer implements IsTypeSupported(). (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: rebase Created 7 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 | Annotate | Revision Log
« no previous file with comments | « media/base/android/media_codec_bridge.h ('k') | media/base/android/media_drm_bridge.h » ('j') | 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) 2013 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2013 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 "media/base/android/media_codec_bridge.h" 5 #include "media/base/android/media_codec_bridge.h"
6 6
7 #include <jni.h> 7 #include <jni.h>
8 #include <string>
8 9
9 #include "base/android/build_info.h" 10 #include "base/android/build_info.h"
10 #include "base/android/jni_android.h" 11 #include "base/android/jni_android.h"
11 #include "base/android/jni_array.h" 12 #include "base/android/jni_array.h"
12 #include "base/android/jni_string.h" 13 #include "base/android/jni_string.h"
13 #include "base/basictypes.h" 14 #include "base/basictypes.h"
14 #include "base/lazy_instance.h" 15 #include "base/lazy_instance.h"
15 #include "base/logging.h" 16 #include "base/logging.h"
16 #include "base/safe_numerics.h" 17 #include "base/safe_numerics.h"
17 #include "base/strings/stringprintf.h" 18 #include "base/strings/stringprintf.h"
18 #include "jni/MediaCodecBridge_jni.h" 19 #include "jni/MediaCodecBridge_jni.h"
19 #include "media/base/bit_reader.h" 20 #include "media/base/bit_reader.h"
20 #include "media/base/decrypt_config.h" 21 #include "media/base/decrypt_config.h"
21 22
22 using base::android::AttachCurrentThread; 23 using base::android::AttachCurrentThread;
23 using base::android::ConvertUTF8ToJavaString; 24 using base::android::ConvertUTF8ToJavaString;
24 using base::android::ScopedJavaLocalRef; 25 using base::android::ScopedJavaLocalRef;
25 26
26 namespace media { 27 namespace media {
27 28
28 enum { kBufferFlagEndOfStream = 4 }; 29 enum { kBufferFlagEndOfStream = 4 };
29 30
30 static const char* AudioCodecToMimeType(const AudioCodec codec) { 31 static const std::string AudioCodecToMimeType(const AudioCodec codec) {
31 switch (codec) { 32 switch (codec) {
32 case kCodecMP3: 33 case kCodecMP3:
33 return "audio/mpeg"; 34 return "audio/mpeg";
34 case kCodecVorbis: 35 case kCodecVorbis:
35 return "audio/vorbis"; 36 return "audio/vorbis";
36 case kCodecAAC: 37 case kCodecAAC:
37 return "audio/mp4a-latm"; 38 return "audio/mp4a-latm";
38 default: 39 default:
39 return NULL; 40 return std::string();
40 } 41 }
41 } 42 }
42 43
43 static const char* VideoCodecToMimeType(const VideoCodec codec) { 44 static const std::string VideoCodecToMimeType(const VideoCodec codec) {
44 switch (codec) { 45 switch (codec) {
45 case kCodecH264: 46 case kCodecH264:
46 return "video/avc"; 47 return "video/avc";
47 case kCodecVP8: 48 case kCodecVP8:
48 return "video/x-vnd.on2.vp8"; 49 return "video/x-vnd.on2.vp8";
49 default: 50 default:
50 return NULL; 51 return std::string();
51 } 52 }
52 } 53 }
53 54
55 static const std::string CodecTypeToMimeType(const std::string& codec) {
ddorwin 2013/08/30 16:59:15 What do you think of using the same type for this
56 // TODO(xhwang): Shall we handle more detailed strings like "mp4a.40.2"?
57 if (codec == "avc1")
58 return "video/avc";
59 if (codec == "mp4a")
60 return "audio/mp4a-latm";
61 if (codec == "vp8" || codec == "vp8.0")
62 return "video/x-vnd.on2.vp8";
63 if (codec == "vorbis")
64 return "audio/vorbis";
65 return std::string();
66 }
67
54 static ScopedJavaLocalRef<jintArray> ToJavaIntArray( 68 static ScopedJavaLocalRef<jintArray> ToJavaIntArray(
55 JNIEnv* env, scoped_ptr<jint[]> native_array, int size) { 69 JNIEnv* env, scoped_ptr<jint[]> native_array, int size) {
56 ScopedJavaLocalRef<jintArray> j_array(env, env->NewIntArray(size)); 70 ScopedJavaLocalRef<jintArray> j_array(env, env->NewIntArray(size));
57 env->SetIntArrayRegion(j_array.obj(), 0, size, native_array.get()); 71 env->SetIntArrayRegion(j_array.obj(), 0, size, native_array.get());
58 return j_array; 72 return j_array;
59 } 73 }
60 74
61 // static 75 // static
62 const base::TimeDelta MediaCodecBridge::kTimeOutInfinity = 76 const base::TimeDelta MediaCodecBridge::kTimeOutInfinity =
63 base::TimeDelta::FromMicroseconds(-1); 77 base::TimeDelta::FromMicroseconds(-1);
64 78
65 // static 79 // static
66 const base::TimeDelta MediaCodecBridge::kTimeOutNoWait = 80 const base::TimeDelta MediaCodecBridge::kTimeOutNoWait =
67 base::TimeDelta::FromMicroseconds(0); 81 base::TimeDelta::FromMicroseconds(0);
68 82
69 // static 83 // static
70 bool MediaCodecBridge::IsAvailable() { 84 bool MediaCodecBridge::IsAvailable() {
71 // MediaCodec is only available on JB and greater. 85 // MediaCodec is only available on JB and greater.
72 return base::android::BuildInfo::GetInstance()->sdk_int() >= 16; 86 return base::android::BuildInfo::GetInstance()->sdk_int() >= 16;
73 } 87 }
74 88
75 MediaCodecBridge::MediaCodecBridge(const char* mime) { 89 // static
90 bool MediaCodecBridge::CanDecode(const std::string& codec, bool is_secure) {
91 JNIEnv* env = AttachCurrentThread();
92 std::string mime = CodecTypeToMimeType(codec);
93 if (mime.empty())
94 return false;
95 ScopedJavaLocalRef<jstring> j_mime = ConvertUTF8ToJavaString(env, mime);
96 return !Java_MediaCodecBridge_create(env, j_mime.obj(), is_secure).is_null();
97 }
98
99 // TODO(xhwang): Support creating secure MediaCodecBridge.
100 MediaCodecBridge::MediaCodecBridge(const std::string& mime) {
76 JNIEnv* env = AttachCurrentThread(); 101 JNIEnv* env = AttachCurrentThread();
77 CHECK(env); 102 CHECK(env);
78 DCHECK(mime);
79 103
80 ScopedJavaLocalRef<jstring> j_type = ConvertUTF8ToJavaString(env, mime); 104 DCHECK(!mime.empty());
81 j_media_codec_.Reset(Java_MediaCodecBridge_create( 105 ScopedJavaLocalRef<jstring> j_mime = ConvertUTF8ToJavaString(env, mime);
82 env, j_type.obj())); 106 j_media_codec_.Reset(Java_MediaCodecBridge_create(env, j_mime.obj(), false));
83 } 107 }
84 108
85 MediaCodecBridge::~MediaCodecBridge() { 109 MediaCodecBridge::~MediaCodecBridge() {
86 JNIEnv* env = AttachCurrentThread(); 110 JNIEnv* env = AttachCurrentThread();
87 CHECK(env); 111 CHECK(env);
88 if (j_media_codec_.obj()) 112 if (j_media_codec_.obj())
89 Java_MediaCodecBridge_release(env, j_media_codec_.obj()); 113 Java_MediaCodecBridge_release(env, j_media_codec_.obj());
90 } 114 }
91 115
92 void MediaCodecBridge::StartInternal() { 116 void MediaCodecBridge::StartInternal() {
(...skipping 127 matching lines...) Expand 10 before | Expand all | Expand 10 after
220 int size_to_copy = (buffer_capacity < size) ? buffer_capacity : size; 244 int size_to_copy = (buffer_capacity < size) ? buffer_capacity : size;
221 // TODO(qinmin): Handling the case that not all the data can be copied. 245 // TODO(qinmin): Handling the case that not all the data can be copied.
222 DCHECK(size_to_copy == size) << 246 DCHECK(size_to_copy == size) <<
223 "Failed to fill all the data into the input buffer. Size to fill: " 247 "Failed to fill all the data into the input buffer. Size to fill: "
224 << size << ". Size filled: " << size_to_copy; 248 << size << ". Size filled: " << size_to_copy;
225 if (size_to_copy > 0) 249 if (size_to_copy > 0)
226 memcpy(direct_buffer, data, size_to_copy); 250 memcpy(direct_buffer, data, size_to_copy);
227 return size_to_copy; 251 return size_to_copy;
228 } 252 }
229 253
230 AudioCodecBridge::AudioCodecBridge(const char* mime) 254 AudioCodecBridge::AudioCodecBridge(const std::string& mime)
231 : MediaCodecBridge(mime) { 255 : MediaCodecBridge(mime) {
232 } 256 }
233 257
234 bool AudioCodecBridge::Start( 258 bool AudioCodecBridge::Start(
235 const AudioCodec codec, int sample_rate, int channel_count, 259 const AudioCodec codec, int sample_rate, int channel_count,
236 const uint8* extra_data, size_t extra_data_size, bool play_audio, 260 const uint8* extra_data, size_t extra_data_size, bool play_audio,
237 jobject media_crypto) { 261 jobject media_crypto) {
238 JNIEnv* env = AttachCurrentThread(); 262 JNIEnv* env = AttachCurrentThread();
239 DCHECK(AudioCodecToMimeType(codec));
240 263
241 if (!media_codec()) 264 if (!media_codec())
242 return false; 265 return false;
243 266
267 std::string codec_string = AudioCodecToMimeType(codec);
268 if (codec_string.empty())
269 return false;
270
244 ScopedJavaLocalRef<jstring> j_mime = 271 ScopedJavaLocalRef<jstring> j_mime =
245 ConvertUTF8ToJavaString(env, AudioCodecToMimeType(codec)); 272 ConvertUTF8ToJavaString(env, codec_string);
246 ScopedJavaLocalRef<jobject> j_format( 273 ScopedJavaLocalRef<jobject> j_format(
247 Java_MediaCodecBridge_createAudioFormat( 274 Java_MediaCodecBridge_createAudioFormat(
248 env, j_mime.obj(), sample_rate, channel_count)); 275 env, j_mime.obj(), sample_rate, channel_count));
249 DCHECK(!j_format.is_null()); 276 DCHECK(!j_format.is_null());
250 277
251 if (!ConfigureMediaFormat(j_format.obj(), codec, extra_data, extra_data_size)) 278 if (!ConfigureMediaFormat(j_format.obj(), codec, extra_data, extra_data_size))
252 return false; 279 return false;
253 280
254 if (!Java_MediaCodecBridge_configureAudio( 281 if (!Java_MediaCodecBridge_configureAudio(
255 env, media_codec(), j_format.obj(), media_crypto, 0, play_audio)) { 282 env, media_codec(), j_format.obj(), media_crypto, 0, play_audio)) {
256 return false; 283 return false;
257 } 284 }
285
258 StartInternal(); 286 StartInternal();
259 return true; 287 return true;
260 } 288 }
261 289
262 bool AudioCodecBridge::ConfigureMediaFormat( 290 bool AudioCodecBridge::ConfigureMediaFormat(
263 jobject j_format, const AudioCodec codec, const uint8* extra_data, 291 jobject j_format, const AudioCodec codec, const uint8* extra_data,
264 size_t extra_data_size) { 292 size_t extra_data_size) {
265 if (extra_data_size == 0) 293 if (extra_data_size == 0)
266 return true; 294 return true;
267 295
(...skipping 107 matching lines...) Expand 10 before | Expand all | Expand 10 after
375 base::android::ToJavaByteArray(env, buffer, numBytes); 403 base::android::ToJavaByteArray(env, buffer, numBytes);
376 Java_MediaCodecBridge_playOutputBuffer( 404 Java_MediaCodecBridge_playOutputBuffer(
377 env, media_codec(), byte_array.obj()); 405 env, media_codec(), byte_array.obj());
378 } 406 }
379 407
380 void AudioCodecBridge::SetVolume(double volume) { 408 void AudioCodecBridge::SetVolume(double volume) {
381 JNIEnv* env = AttachCurrentThread(); 409 JNIEnv* env = AttachCurrentThread();
382 Java_MediaCodecBridge_setVolume(env, media_codec(), volume); 410 Java_MediaCodecBridge_setVolume(env, media_codec(), volume);
383 } 411 }
384 412
385 VideoCodecBridge::VideoCodecBridge(const char* mime) 413 VideoCodecBridge::VideoCodecBridge(const std::string& mime)
386 : MediaCodecBridge(mime) { 414 : MediaCodecBridge(mime) {
387 } 415 }
388 416
389 bool VideoCodecBridge::Start( 417 bool VideoCodecBridge::Start(
390 const VideoCodec codec, const gfx::Size& size, jobject surface, 418 const VideoCodec codec, const gfx::Size& size, jobject surface,
391 jobject media_crypto) { 419 jobject media_crypto) {
392 JNIEnv* env = AttachCurrentThread(); 420 JNIEnv* env = AttachCurrentThread();
393 DCHECK(VideoCodecToMimeType(codec));
394 421
395 if (!media_codec()) 422 if (!media_codec())
396 return false; 423 return false;
397 424
425 std::string codec_string = VideoCodecToMimeType(codec);
426 if (codec_string.empty())
427 return false;
428
398 ScopedJavaLocalRef<jstring> j_mime = 429 ScopedJavaLocalRef<jstring> j_mime =
399 ConvertUTF8ToJavaString(env, VideoCodecToMimeType(codec)); 430 ConvertUTF8ToJavaString(env, codec_string);
400 ScopedJavaLocalRef<jobject> j_format( 431 ScopedJavaLocalRef<jobject> j_format(
401 Java_MediaCodecBridge_createVideoFormat( 432 Java_MediaCodecBridge_createVideoFormat(
402 env, j_mime.obj(), size.width(), size.height())); 433 env, j_mime.obj(), size.width(), size.height()));
403 DCHECK(!j_format.is_null()); 434 DCHECK(!j_format.is_null());
404 if (!Java_MediaCodecBridge_configureVideo( 435 if (!Java_MediaCodecBridge_configureVideo(
405 env, media_codec(), j_format.obj(), surface, media_crypto, 0)) { 436 env, media_codec(), j_format.obj(), surface, media_crypto, 0)) {
406 return false; 437 return false;
407 } 438 }
408 StartInternal(); 439 StartInternal();
409 return true; 440 return true;
410 } 441 }
411 442
412 AudioCodecBridge* AudioCodecBridge::Create(const AudioCodec codec) { 443 AudioCodecBridge* AudioCodecBridge::Create(const AudioCodec codec) {
413 const char* mime = AudioCodecToMimeType(codec); 444 const std::string mime = AudioCodecToMimeType(codec);
414 return mime ? new AudioCodecBridge(mime) : NULL; 445 return mime.empty() ? NULL : new AudioCodecBridge(mime);
415 } 446 }
416 447
417 VideoCodecBridge* VideoCodecBridge::Create(const VideoCodec codec) { 448 VideoCodecBridge* VideoCodecBridge::Create(const VideoCodec codec) {
418 const char* mime = VideoCodecToMimeType(codec); 449 const std::string mime = VideoCodecToMimeType(codec);
419 return mime ? new VideoCodecBridge(mime) : NULL; 450 return mime.empty() ? NULL : new VideoCodecBridge(mime);
420 } 451 }
421 452
422 bool MediaCodecBridge::RegisterMediaCodecBridge(JNIEnv* env) { 453 bool MediaCodecBridge::RegisterMediaCodecBridge(JNIEnv* env) {
423 return RegisterNativesImpl(env); 454 return RegisterNativesImpl(env);
424 } 455 }
425 456
426 } // namespace media 457 } // namespace media
OLDNEW
« no previous file with comments | « media/base/android/media_codec_bridge.h ('k') | media/base/android/media_drm_bridge.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698