我正在尝试更改音频播放器的uri,而不会破坏已实现的SLPlayItf
对象。
我在代码中有这样的东西:
static SLDataSource audioSrcOne;
static SLDataLocator_URI locUriOne;
void initialize_player_with_streamOne()
{
...
locUriOne.locatorType = SL_DATALOCATOR_URI;
locUriOne.URI = (SLchar *) streamOne->utf8;
SLDataFormat_MIME format_mime = { SL_DATAFORMAT_MIME, NULL, SL_CONTAINERTYPE_UNSPECIFIED };
audioSrcOne.pLocator = (void *)&locUriOne;
audioSrcOne.pFormat = (void *)&format_mime;
...
result = ( *engine->engineEngine )->CreateAudioPlayer( engine->engineEngine, &( streamOne->playerObject ), &audioSrcOne, &audioSnkOne, 3, idm, reqm );
assert( SL_RESULT_SUCCESS == result );
...
}
我认为SLDataSource
和SLDataLocator_URI
是作为指针发送给OpenSL的。如果我只是改变了它,那么新的网址就会被设置。
LOGV("STREAM ONE RESET - Configuring audio source %s", streamOne->utf8 );
locUriOne.URI = (SLchar *) streamOne->utf8;
LOGV("STREAM ONE RESET - %s", locUriOne.URI );
即使我可以看到URI指向新的char数组,但音频播放器仍在播放旧的。
有没有人知道如何在不破坏它的情况下更换音频播放器的当前网址?
PS:在更改URL之前,我正在向缓冲区和播放器对象发送SL_PLAYER_STOPPED。还清除缓冲区。但这并没有解决问题。
PSS:你会问我为什么不摧毁旧的音频播放器并创建一个新的音频播放器。那么答案是,样板太大了,不能破坏和创造。加上破坏/创造需要花费太多时间来满足我的口味。我更喜欢重新使用当前创建的对象。而且,当我创建第二个音频播放器时,我无法破坏第一个音频播放器。本机Destroy()
命令挂起线程,代码不再响应。
答案 0 :(得分:0)
我一直在挖掘opensl的来源,在IEngine.c文件中,我找到了这段代码:
// Check the source and sink parameters against generic constraints,
// and make a local copy of all parameters in case other application threads
// change memory concurrently.
result = checkDataSource("pAudioSrc", pAudioSrc, &thiz->mDataSource,
DATALOCATOR_MASK_URI | DATALOCATOR_MASK_ADDRESS |
DATALOCATOR_MASK_BUFFERQUEUE
#ifdef ANDROID
| DATALOCATOR_MASK_ANDROIDFD | DATALOCATOR_MASK_ANDROIDSIMPLEBUFFERQUEUE
| DATALOCATOR_MASK_ANDROIDBUFFERQUEUE
#endif
, DATAFORMAT_MASK_MIME | DATAFORMAT_MASK_PCM);
if (SL_RESULT_SUCCESS != result) {
break;
}
... ...
// It would be unsafe to ever refer to the application pointers again
pAudioSrc = NULL;
pAudioSnk = NULL;
如代码所示,复制音频源,然后为了线程安全而将传入指针设置为null。因此,似乎无法动态更改SLPlayItf的音频源。