Stagefright中关于audio的部分由AudioPlayer处理,输出使用AudioSink 或AudioTrack。
- status_t AwesomePlayer::play_l() {
- ...
- if (mAudioSource != NULL) {
- if (mAudioPlayer == NULL) {
- if (mAudioSink != NULL) {
- mAudioPlayer = new AudioPlayer(mAudioSink, this);
- mAudioPlayer->setSource(mAudioSource);
- ...
- }
- ...
- }
AwesomePlayer在initAudioDecoder方法中建立audio decoder
status_t AwesomePlayer::initAudioDecoder() {
...
if (!strcasecmp(mime, MEDIA_MIMETYPE_AUDIO_RAW)) {
mAudioSource = mAudioTrack;
} else {
mAudioSource = OMXCodec::Create(
mClient.interface(), mAudioTrack->getFormat(),
false, // createEncoder
mAudioTrack);
}
...
}
当调用play_l方法的时候建立AudioPlayer,并把Audio Decoder[mAudioSource]传递给它
AudioPlayer在调用start方法的时候会开启audioSink,并传递回调函数AudioSinkCallback
- status_t AudioPlayer::start(bool sourceAlreadyStarted) {
- ...
- if (mAudioSink.get() != NULL) {
- status_t err = mAudioSink->open(
- mSampleRate, numChannels, AudioSystem::PCM_16_BIT,
- DEFAULT_AUDIOSINK_BUFFERCOUNT,
- &AudioPlayer::AudioSinkCallback, this);
- ...
- mAudioSink->start();
- ...
- }
之后AudioSink会在需要Sample数据的时候回调AudioSinkCallback,要求将size大小Sample数据填充到buffer。这里调用fillBuffer函数从audio decoder读取解码后的Sample数据。
- size_t AudioPlayer::AudioSinkCallback(
- MediaPlayerBase::AudioSink *audioSink,
- void *buffer, size_t size, void *cookie) {
- AudioPlayer *me = (AudioPlayer *)cookie;
-
- LOGI("[%s:%d]_____ enter AudioPlayer::AudioSinkCallback size = %d"
- , __FUNCTION__, __LINE__, size);
-
- return me->fillBuffer(buffer, size);
- }
-
- void AudioPlayer::AudioCallback(int event, void *info) {
- if (event != AudioTrack::EVENT_MORE_DATA) {
- return;
- }
- AudioTrack::Buffer *buffer = (AudioTrack::Buffer *)info;
- size_t numBytesWritten = fillBuffer(buffer->raw, buffer->size);
- buffer->size = numBytesWritten;
- }
-
- size_t AudioPlayer::fillBuffer(void *data, size_t size) {
- ...
- size_t size_done = 0;
- size_t size_remaining = size;
- while (size_remaining > 0) {
- ...
- err = mSource->read(&mInputBuffer, &options);
- ...
- memcpy((char *)data + size_done,
- (const char *)mInputBuffer->data() + mInputBuffer->range_offset(),
- copy);
- mInputBuffer->set_range(mInputBuffer->range_offset() + copy,
- mInputBuffer->range_length() - copy);
- size_done += copy;
- size_remaining -= copy;
- ...
- }
- ...
- }
这里的mSource实际上是decoder,其read方法会调用mAudioTrack的read方法获取DataSource的未解码数据,然后解码,返回解码后的数据。
总流程如下
- AudioSink
- |
- +- AudioPlayer#AudioSinkCallback
- |
- +- AudioDecoder#read
- |
- +- Extractor::MediaSource#read
参考
(shaobin0604) |