gpt4 book ai didi

android - AudioTrack:从一个线程开始调用

转载 作者:行者123 更新时间:2023-11-29 16:16:35 34 4
gpt4 key购买 nike

我在静态模式下使用 AudioTrack 一遍又一遍地再现相同的信号。

我按照这里的示例进行操作,有时效果很好,但有时会抛出此错误并且没有声音:

AudioTrack: start called from a thread
01-23 15:26:16.902: W/libutils.threads(1133): Thread (this=0x3973b8): don't call waitForExit() from this Thread object's thread. It's a guaranteed deadlock!

这是源代码。我试图确保调用停止并为下一次“播放”执行重新加载数据。

     public class SoundPlayer {
// originally from http://marblemice.blogspot.com/2010/04/generate-and-play-tone-in-android.html
private int numSamples;
private double sample[];
private byte generatedSnd[];
private AudioTrack audioTrack;

public SoundPlayer(float duration, int sampleRate, double freqOfTone) {
super();
this.numSamples = (int) (duration * sampleRate);
this.sample = new double[numSamples];
this.generatedSnd = new byte[2 * numSamples];
// fill out the array
for (int i = 0; i < numSamples; ++i) {
sample[i] = Math.sin(2 * Math.PI * i / (sampleRate / freqOfTone));
}
// convert to 16 bit pcm sound array
// assumes the sample buffer is normalised.
int idx = 0;
for (final double dVal : sample) {
// scale to maximum amplitude
final short val = (short) ((dVal * 32767));
// in 16 bit wav PCM, first byte is the low order byte
generatedSnd[idx++] = (byte) (val & 0x00ff);
generatedSnd[idx++] = (byte) ((val & 0xff00) >>> 8);

}
audioTrack = new AudioTrack(AudioManager.STREAM_MUSIC,
sampleRate, AudioFormat.CHANNEL_CONFIGURATION_MONO,
AudioFormat.ENCODING_PCM_16BIT, numSamples,
AudioTrack.MODE_STATIC);
audioTrack.write(generatedSnd, 0, generatedSnd.length);
}

public void playSound() {
if ( audioTrack.getPlayState() == (AudioTrack.PLAYSTATE_PLAYING | AudioTrack.PLAYSTATE_PAUSED )) {
audioTrack.stop();
audioTrack.reloadStaticData();
}
Log.i("Audio", "playState: " + audioTrack.getPlayState());
audioTrack.play();
audioTrack.stop();
audioTrack.reloadStaticData();
}

}

如果我们打开android源码,里面解释的不多:

void AudioTrack::start()
{
sp<AudioTrackThread> t = mAudioTrackThread;

LOGV("start");
if (t != 0) {
if (t->exitPending()) {
if (t->requestExitAndWait() == WOULD_BLOCK) {
LOGE("AudioTrack::start called from thread");
return;
}
}
t->mLock.lock();
}

有人知道怎么处理吗?

最佳答案

我曾经遇到过类似的问题。

简单地说,如果您碰巧有东西在多个线程中运行,您必须确保创建 AudioTrack 并调用 play()它的 stop() 必须发生在同一个线程中。

但是,这并不意味着您也必须在该线程中创建音频样本。如果您使用静态音频数据 (AudioTrack.MODE_STATIC),您可以在别处预加载或生成它们,然后在应用的整个生命周期中多次使用它。

关于android - AudioTrack:从一个线程开始调用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8976491/

34 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com