功能描述

  类似支付宝收款时候的语音播报功能:当别人扫描你的收款码,你收到钱之后,就会听到“支付宝到账12.55元”的语音播报。

  要解决的问题

  1.播放单个语音文件

  2.播放完单个语音文件之后立即播放下一条,这样才能连续

  3.当多个完整的语音序列都需要播报时的处理(比如支付宝短时间内收到多条收款推送)

  实现思路

  播放单个文件选择MediaPlayer

  首先创建一个MediaPlayer实例

 MediaPlayer player = new MediaPlayer();

  然后设置数据源,这里数据源从assets中获取,当然也可以将语音文件放在raw文件夹里

  fd = FileUtils.getAssetFileDescription(path);
  player.setDataSource(fd.getFileDescriptor(), fd.getStartOffset(),fd.getLength());

  然后调用 prepareAsync() 方法,异步加载,并设置监听,加载完毕之后开始播放(与 prepare 方法区别开来)

  player.prepareAsync();
  player.setOnPreparedListener(new MediaPlayer.OnPreparedListener() { 
  @Override
   public void onPrepared(MediaPlayer mp) { 
   mp.start();
    }
    });

  由于播放的语音文件不止一个,因此需要监听播放完成的状态,在播放完成之后播放下一条语音

player.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
                        @Override
                        public void onCompletion(MediaPlayer mp) {
                            mp.reset();
                            counter[0]++;
                            if (counter[0] < list.size()) {
                                try {
                                    AssetFileDescriptor fileDescriptor = FileUtils.getAssetFileDescription(String.format("sound/tts_%s.mp3", list.get(counter[0])));
                                    mp.setDataSource(fileDescriptor.getFileDescriptor(), fileDescriptor.getStartOffset(), fileDescriptor.getLength());
                                    mp.prepare();
                                } catch (IOException e) {
                                    e.printStackTrace();
                                    latch.countDown();
                                }
                            } else {
                                mp.release();
                                latch.countDown();
                            }
                        }
                    });

  短时间多次播报请求,开采用同步方式进行,一条播完播放下一条,这里采用

  synchronized + notifyAll() 实现,当然也可以用别的方法。

  代码封装

  功能代码分为两部分,一部分是语音序列组成的 List,这里是 VoiceTemplate;

  一部分是播放的功能封装,接收 List,然后播放语音,这里叫做 VoiceSpeaker;

  详细代码见文末。

  代码使用

  比如要播放“支付宝到账十二点一三元”,代码如下

final List<String> list = new VoiceTemplate()
                .prefix("success")
                .numString("12.13")
                .suffix("yuan")
                .gen();
VoiceSpeaker.getInstance().speak(list);

  源码

  KTools:

  https://link.jianshu.com/?t=https://github.com/jiangkang/KTools

https://github.com/jiangkang/KTools/blob/master/app/src/main/java/com/jiangkang/ktools/audio/VoiceSpeaker.java

https://github.com/jiangkang/KTools/blob/master/app/src/main/java/com/jiangkang/ktools/audio/VoiceTemplate.java

  作者:姜康

  链接:https://www.jianshu.com/p/df2022b3937d

  声明:本文是 姜康 原创。转载请联系作者获得授权。