1

我使用 android.provider.MediaStore.Audio.Media.EXTERNAL_CONTENT_URI 意图从 SD 卡加载音乐文件。

Intent tmpIntent1 = new Intent(Intent.ACTION_PICK, android.provider.MediaStore.Audio.Media.EXTERNAL_CONTENT_URI);
startActivityForResult(tmpIntent1, 0);

并在 onActivityResult

Uri mediaPath = Uri.parse(data.getData().toString());
MediaPlayer mp = MediaPlayer.create(this, mediaPath);
mp.start();

现在 MediaPlayer 以立体声播放音频。有没有办法在应用程序本身中将选定的音乐/音频文件或立体声输出转换为单声道?

我查找了SoundPoolAudioTrack的 API ,但没有找到如何将 mp3 文件音频转换为单声道。

像 PowerAMP 这样的应用程序有那些 Stereo <-> Mono 开关,当按下时会立即将输出音频转换为单声道信号并再次返回,它们是如何做到的?

4

2 回答 2

3

您是否分别加载 .wav- 文件 PCM- 数据?如果是这样,那么您可以轻松读取每个通道的每个样本,将它们叠加并除以通道数量以获得单声道信号。

如果您以交错签名短片的形式存储立体声信号,则计算生成的单声道信号的代码可能如下所示:

    short[] stereoSamples;//get them from somewhere

    //output array, which will contain the mono signal
    short[] monoSamples= new short[stereoSamples.length/2];
    //length of the .wav-file header-> 44 bytes
    final int HEADER_LENGTH=22;

    //additional counter
    int k=0;


    for(int i=0; i< monoSamples.length;i++){
        //skip the header andsuperpose the samples of the left and right channel
        if(k>HEADER_LENGTH){
        monoSamples[i]= (short) ((stereoSamples[i*2]+ stereoSamples[(i*2)+1])/2);
        }
        k++;
    }

我希望,我能够帮助你。

最好的问候, G_J

于 2013-06-28T18:24:21.163 回答
1

首先,获取一个编码器来将您的音频文件转换为短数组(short[])。

然后通过拆分流将短数组转换为单声道。

然后平均拆分流。

short[] stereo  = new short[BUF_SIZE];
short[] monoCh1 = new short[BUF_SIZE/2];
short[] monoCh2 = new short[BUF_SIZE/2];
short[] monoAvg = new short[BUF_SIZE/2];

stereo = sampleBuffer.getBuffer(); //get the raw S16 PCM buffer here

 for( int i=0 ; i < stereo.length ; i+=2 )
 {
     monoCh1[i/2] = (short) stereo[i];
     monoCh2[i/2] = (short) stereo[i+1];
     monoAvg[i/2] = (short) ( ( stereo[i] + stereo[i+1] ) / 2 );
 }

现在你有:

来自通道 1(左通道)的 PCM 单声道流monoCh1

来自通道 2(右通道)的 PCM 单声道流monoCh2

PCM 单声道流来自平均两个通道monoAvg

于 2020-10-31T01:49:07.110 回答