VideoEditorPlayer.cpp revision 1c97d9ab52a288d24ea54499de435277cc1a3d68
1/* 2 * Copyright (C) 2011 NXP Software 3 * Copyright (C) 2011 The Android Open Source Project 4 * 5 * Licensed under the Apache License, Version 2.0 (the "License"); 6 * you may not use this file except in compliance with the License. 7 * You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 */ 17 18#define LOG_NDEBUG 1 19#define LOG_TAG "VideoEditorPlayer" 20#include <utils/Log.h> 21 22#include "VideoEditorPlayer.h" 23#include "PreviewPlayer.h" 24 25#include <media/Metadata.h> 26#include <media/stagefright/MediaExtractor.h> 27 28namespace android { 29 30VideoEditorPlayer::VideoEditorPlayer() 31 : mPlayer(new PreviewPlayer) { 32 33 LOGV("VideoEditorPlayer"); 34 mPlayer->setListener(this); 35} 36 37VideoEditorPlayer::~VideoEditorPlayer() { 38 LOGV("~VideoEditorPlayer"); 39 40 reset(); 41 mVeAudioSink.clear(); 42 43 delete mPlayer; 44 mPlayer = NULL; 45} 46 47status_t VideoEditorPlayer::initCheck() { 48 LOGV("initCheck"); 49 return OK; 50} 51 52 53status_t VideoEditorPlayer::setAudioPlayer(VideoEditorAudioPlayer *audioPlayer) { 54 return mPlayer->setAudioPlayer(audioPlayer); 55} 56 57 58status_t VideoEditorPlayer::setDataSource( 59 const char *url, const KeyedVector<String8, String8> *headers) { 60 LOGI("setDataSource('%s')", url); 61 62 return mPlayer->setDataSource(url, headers); 63} 64 65//We donot use this in preview, dummy implimentation as this is pure virtual 66status_t VideoEditorPlayer::setDataSource(int fd, int64_t offset, 67 int64_t length) { 68 LOGE("setDataSource(%d, %lld, %lld) Not supported", fd, offset, length); 69 return (!OK); 70} 71 72status_t VideoEditorPlayer::setVideoISurface(const sp<ISurface> &surface) { 73 LOGV("setVideoISurface"); 74 75 mPlayer->setISurface(surface); 76 return OK; 77} 78 79status_t VideoEditorPlayer::setVideoSurface(const sp<Surface> &surface) { 80 LOGV("setVideoSurface"); 81 82 mPlayer->setSurface(surface); 83 return OK; 84} 85 86status_t VideoEditorPlayer::prepare() { 87 LOGV("prepare"); 88 return mPlayer->prepare(); 89} 90 91status_t VideoEditorPlayer::prepareAsync() { 92 return mPlayer->prepareAsync(); 93} 94 95status_t VideoEditorPlayer::start() { 96 LOGV("start"); 97 return mPlayer->play(); 98} 99 100status_t VideoEditorPlayer::stop() { 101 LOGV("stop"); 102 return pause(); 103} 104 105status_t VideoEditorPlayer::pause() { 106 LOGV("pause"); 107 return mPlayer->pause(); 108} 109 110bool VideoEditorPlayer::isPlaying() { 111 LOGV("isPlaying"); 112 return mPlayer->isPlaying(); 113} 114 115status_t VideoEditorPlayer::seekTo(int msec) { 116 LOGV("seekTo"); 117 status_t err = mPlayer->seekTo((int64_t)msec * 1000); 118 return err; 119} 120 121status_t VideoEditorPlayer::getCurrentPosition(int *msec) { 122 LOGV("getCurrentPosition"); 123 int64_t positionUs; 124 status_t err = mPlayer->getPosition(&positionUs); 125 126 if (err != OK) { 127 return err; 128 } 129 130 *msec = (positionUs + 500) / 1000; 131 return OK; 132} 133 134status_t VideoEditorPlayer::getDuration(int *msec) { 135 LOGV("getDuration"); 136 137 int64_t durationUs; 138 status_t err = mPlayer->getDuration(&durationUs); 139 140 if (err != OK) { 141 *msec = 0; 142 return OK; 143 } 144 145 *msec = (durationUs + 500) / 1000; 146 return OK; 147} 148 149status_t VideoEditorPlayer::reset() { 150 LOGV("reset"); 151 mPlayer->reset(); 152 return OK; 153} 154 155status_t VideoEditorPlayer::setLooping(int loop) { 156 LOGV("setLooping"); 157 return mPlayer->setLooping(loop); 158} 159 160player_type VideoEditorPlayer::playerType() { 161 LOGV("playerType"); 162 return STAGEFRIGHT_PLAYER; 163} 164 165status_t VideoEditorPlayer::suspend() { 166 LOGV("suspend"); 167 return mPlayer->suspend(); 168} 169 170status_t VideoEditorPlayer::resume() { 171 LOGV("resume"); 172 return mPlayer->resume(); 173} 174 175status_t VideoEditorPlayer::invoke(const Parcel &request, Parcel *reply) { 176 return INVALID_OPERATION; 177} 178 179void VideoEditorPlayer::setAudioSink(const sp<AudioSink> &audioSink) { 180 MediaPlayerInterface::setAudioSink(audioSink); 181 182 mPlayer->setAudioSink(audioSink); 183} 184 185status_t VideoEditorPlayer::getMetadata( 186 const media::Metadata::Filter& ids, Parcel *records) { 187 using media::Metadata; 188 189 uint32_t flags = mPlayer->flags(); 190 191 Metadata metadata(records); 192 193 metadata.appendBool( 194 Metadata::kPauseAvailable, 195 flags & MediaExtractor::CAN_PAUSE); 196 197 metadata.appendBool( 198 Metadata::kSeekBackwardAvailable, 199 flags & MediaExtractor::CAN_SEEK_BACKWARD); 200 201 metadata.appendBool( 202 Metadata::kSeekForwardAvailable, 203 flags & MediaExtractor::CAN_SEEK_FORWARD); 204 205 metadata.appendBool( 206 Metadata::kSeekAvailable, 207 flags & MediaExtractor::CAN_SEEK); 208 209 return OK; 210} 211 212status_t VideoEditorPlayer::loadEffectsSettings( 213 M4VSS3GPP_EffectSettings* pEffectSettings, int nEffects) { 214 LOGV("loadEffectsSettings"); 215 return mPlayer->loadEffectsSettings(pEffectSettings, nEffects); 216} 217 218status_t VideoEditorPlayer::loadAudioMixSettings( 219 M4xVSS_AudioMixingSettings* pAudioMixSettings) { 220 LOGV("VideoEditorPlayer: loadAudioMixSettings"); 221 return mPlayer->loadAudioMixSettings(pAudioMixSettings); 222} 223 224status_t VideoEditorPlayer::setAudioMixPCMFileHandle( 225 M4OSA_Context pAudioMixPCMFileHandle) { 226 227 LOGV("VideoEditorPlayer: loadAudioMixSettings"); 228 return mPlayer->setAudioMixPCMFileHandle(pAudioMixPCMFileHandle); 229} 230 231status_t VideoEditorPlayer::setAudioMixStoryBoardParam( 232 M4OSA_UInt32 audioMixStoryBoardTS, 233 M4OSA_UInt32 currentMediaBeginCutTime, 234 M4OSA_UInt32 primaryTrackVolValue) { 235 236 LOGV("VideoEditorPlayer: loadAudioMixSettings"); 237 return mPlayer->setAudioMixStoryBoardParam(audioMixStoryBoardTS, 238 currentMediaBeginCutTime, primaryTrackVolValue); 239} 240 241status_t VideoEditorPlayer::setPlaybackBeginTime(uint32_t msec) { 242 LOGV("setPlaybackBeginTime"); 243 return mPlayer->setPlaybackBeginTime(msec); 244} 245 246status_t VideoEditorPlayer::setPlaybackEndTime(uint32_t msec) { 247 LOGV("setPlaybackEndTime"); 248 return mPlayer->setPlaybackEndTime(msec); 249} 250 251status_t VideoEditorPlayer::setStoryboardStartTime(uint32_t msec) { 252 LOGV("setStoryboardStartTime"); 253 return mPlayer->setStoryboardStartTime(msec); 254} 255 256status_t VideoEditorPlayer::setProgressCallbackInterval(uint32_t cbInterval) { 257 LOGV("setProgressCallbackInterval"); 258 return mPlayer->setProgressCallbackInterval(cbInterval); 259} 260 261status_t VideoEditorPlayer::setMediaRenderingMode( 262 M4xVSS_MediaRendering mode, 263 M4VIDEOEDITING_VideoFrameSize outputVideoSize) { 264 265 LOGV("setMediaRenderingMode"); 266 return mPlayer->setMediaRenderingMode(mode, outputVideoSize); 267} 268 269status_t VideoEditorPlayer::resetJniCallbackTimeStamp() { 270 LOGV("resetJniCallbackTimeStamp"); 271 return mPlayer->resetJniCallbackTimeStamp(); 272} 273 274status_t VideoEditorPlayer::setImageClipProperties( 275 uint32_t width, uint32_t height) { 276 return mPlayer->setImageClipProperties(width, height); 277} 278 279status_t VideoEditorPlayer::readFirstVideoFrame() { 280 return mPlayer->readFirstVideoFrame(); 281} 282 283status_t VideoEditorPlayer::getLastRenderedTimeMs(uint32_t *lastRenderedTimeMs) { 284 mPlayer->getLastRenderedTimeMs(lastRenderedTimeMs); 285 return NO_ERROR; 286} 287 288/* Implementation of AudioSink interface */ 289#undef LOG_TAG 290#define LOG_TAG "VeAudioSink" 291 292int VideoEditorPlayer::VeAudioOutput::mMinBufferCount = 4; 293bool VideoEditorPlayer::VeAudioOutput::mIsOnEmulator = false; 294 295VideoEditorPlayer::VeAudioOutput::VeAudioOutput() 296 : mCallback(NULL), 297 mCallbackCookie(NULL) { 298 mTrack = 0; 299 mStreamType = AudioSystem::MUSIC; 300 mLeftVolume = 1.0; 301 mRightVolume = 1.0; 302 mLatency = 0; 303 mMsecsPerFrame = 0; 304 mNumFramesWritten = 0; 305 setMinBufferCount(); 306} 307 308VideoEditorPlayer::VeAudioOutput::~VeAudioOutput() { 309 close(); 310} 311 312void VideoEditorPlayer::VeAudioOutput::setMinBufferCount() { 313 314 mIsOnEmulator = false; 315 mMinBufferCount = 4; 316} 317 318bool VideoEditorPlayer::VeAudioOutput::isOnEmulator() { 319 320 setMinBufferCount(); 321 return mIsOnEmulator; 322} 323 324int VideoEditorPlayer::VeAudioOutput::getMinBufferCount() { 325 326 setMinBufferCount(); 327 return mMinBufferCount; 328} 329 330ssize_t VideoEditorPlayer::VeAudioOutput::bufferSize() const { 331 332 if (mTrack == 0) return NO_INIT; 333 return mTrack->frameCount() * frameSize(); 334} 335 336ssize_t VideoEditorPlayer::VeAudioOutput::frameCount() const { 337 338 if (mTrack == 0) return NO_INIT; 339 return mTrack->frameCount(); 340} 341 342ssize_t VideoEditorPlayer::VeAudioOutput::channelCount() const 343{ 344 if (mTrack == 0) return NO_INIT; 345 return mTrack->channelCount(); 346} 347 348ssize_t VideoEditorPlayer::VeAudioOutput::frameSize() const 349{ 350 if (mTrack == 0) return NO_INIT; 351 return mTrack->frameSize(); 352} 353 354uint32_t VideoEditorPlayer::VeAudioOutput::latency () const 355{ 356 return mLatency; 357} 358 359float VideoEditorPlayer::VeAudioOutput::msecsPerFrame() const 360{ 361 return mMsecsPerFrame; 362} 363 364status_t VideoEditorPlayer::VeAudioOutput::getPosition(uint32_t *position) { 365 366 if (mTrack == 0) return NO_INIT; 367 return mTrack->getPosition(position); 368} 369 370status_t VideoEditorPlayer::VeAudioOutput::open( 371 uint32_t sampleRate, int channelCount, int format, int bufferCount, 372 AudioCallback cb, void *cookie) { 373 374 mCallback = cb; 375 mCallbackCookie = cookie; 376 377 // Check argument "bufferCount" against the mininum buffer count 378 if (bufferCount < mMinBufferCount) { 379 LOGV("bufferCount (%d) is too small and increased to %d", 380 bufferCount, mMinBufferCount); 381 bufferCount = mMinBufferCount; 382 383 } 384 LOGV("open(%u, %d, %d, %d)", sampleRate, channelCount, format, bufferCount); 385 if (mTrack) close(); 386 int afSampleRate; 387 int afFrameCount; 388 int frameCount; 389 390 if (AudioSystem::getOutputFrameCount(&afFrameCount, mStreamType) != 391 NO_ERROR) { 392 return NO_INIT; 393 } 394 if (AudioSystem::getOutputSamplingRate(&afSampleRate, mStreamType) != 395 NO_ERROR) { 396 return NO_INIT; 397 } 398 399 frameCount = (sampleRate*afFrameCount*bufferCount)/afSampleRate; 400 401 AudioTrack *t; 402 if (mCallback != NULL) { 403 t = new AudioTrack( 404 mStreamType, 405 sampleRate, 406 format, 407 (channelCount == 2) ? 408 AudioSystem::CHANNEL_OUT_STEREO : AudioSystem::CHANNEL_OUT_MONO, 409 frameCount, 410 0 /* flags */, 411 CallbackWrapper, 412 this); 413 } else { 414 t = new AudioTrack( 415 mStreamType, 416 sampleRate, 417 format, 418 (channelCount == 2) ? 419 AudioSystem::CHANNEL_OUT_STEREO : AudioSystem::CHANNEL_OUT_MONO, 420 frameCount); 421 } 422 423 if ((t == 0) || (t->initCheck() != NO_ERROR)) { 424 LOGE("Unable to create audio track"); 425 delete t; 426 return NO_INIT; 427 } 428 429 LOGV("setVolume"); 430 t->setVolume(mLeftVolume, mRightVolume); 431 mMsecsPerFrame = 1.e3 / (float) sampleRate; 432 mLatency = t->latency(); 433 mTrack = t; 434 return NO_ERROR; 435} 436 437void VideoEditorPlayer::VeAudioOutput::start() { 438 439 LOGV("start"); 440 if (mTrack) { 441 mTrack->setVolume(mLeftVolume, mRightVolume); 442 mTrack->start(); 443 mTrack->getPosition(&mNumFramesWritten); 444 } 445} 446 447void VideoEditorPlayer::VeAudioOutput::snoopWrite( 448 const void* buffer, size_t size) { 449 // Visualization buffers not supported 450 return; 451 452} 453 454ssize_t VideoEditorPlayer::VeAudioOutput::write( 455 const void* buffer, size_t size) { 456 457 LOG_FATAL_IF(mCallback != NULL, "Don't call write if supplying a callback."); 458 459 //LOGV("write(%p, %u)", buffer, size); 460 if (mTrack) { 461 snoopWrite(buffer, size); 462 ssize_t ret = mTrack->write(buffer, size); 463 mNumFramesWritten += ret / 4; // assume 16 bit stereo 464 return ret; 465 } 466 return NO_INIT; 467} 468 469void VideoEditorPlayer::VeAudioOutput::stop() { 470 471 LOGV("stop"); 472 if (mTrack) mTrack->stop(); 473} 474 475void VideoEditorPlayer::VeAudioOutput::flush() { 476 477 LOGV("flush"); 478 if (mTrack) mTrack->flush(); 479} 480 481void VideoEditorPlayer::VeAudioOutput::pause() { 482 483 LOGV("VeAudioOutput::pause"); 484 if (mTrack) mTrack->pause(); 485} 486 487void VideoEditorPlayer::VeAudioOutput::close() { 488 489 LOGV("close"); 490 delete mTrack; 491 mTrack = 0; 492} 493 494void VideoEditorPlayer::VeAudioOutput::setVolume(float left, float right) { 495 496 LOGV("setVolume(%f, %f)", left, right); 497 mLeftVolume = left; 498 mRightVolume = right; 499 if (mTrack) { 500 mTrack->setVolume(left, right); 501 } 502} 503 504// static 505void VideoEditorPlayer::VeAudioOutput::CallbackWrapper( 506 int event, void *cookie, void *info) { 507 //LOGV("VeAudioOutput::callbackwrapper"); 508 if (event != AudioTrack::EVENT_MORE_DATA) { 509 return; 510 } 511 512 VeAudioOutput *me = (VeAudioOutput *)cookie; 513 AudioTrack::Buffer *buffer = (AudioTrack::Buffer *)info; 514 515 size_t actualSize = (*me->mCallback)( 516 me, buffer->raw, buffer->size, me->mCallbackCookie); 517 518 buffer->size = actualSize; 519 520 if (actualSize > 0) { 521 me->snoopWrite(buffer->raw, actualSize); 522 } 523} 524 525status_t VideoEditorPlayer::VeAudioOutput::dump(int fd, const Vector<String16>& args) const 526{ 527 const size_t SIZE = 256; 528 char buffer[SIZE]; 529 String8 result; 530 531 result.append(" VeAudioOutput\n"); 532 snprintf(buffer, SIZE-1, " stream type(%d), left - right volume(%f, %f)\n", 533 mStreamType, mLeftVolume, mRightVolume); 534 result.append(buffer); 535 snprintf(buffer, SIZE-1, " msec per frame(%f), latency (%d)\n", 536 mMsecsPerFrame, mLatency); 537 result.append(buffer); 538 ::write(fd, result.string(), result.size()); 539 if (mTrack != 0) { 540 mTrack->dump(fd, args); 541 } 542 return NO_ERROR; 543} 544 545int VideoEditorPlayer::VeAudioOutput::getSessionId() { 546 547 return mSessionId; 548} 549 550} // namespace android 551