需求
1、订单提示自动播放,在任何界面均自动播放。
2、当有新订单进入时,语音自动播放,文案「您有新的外卖订单,请注意查看」
3、当有订单超时未接单时,语音自动播放,文案「您有订单已超时,请注意查看」
4、提示规则:同状态语音插队提示,不同状态语音排队提示。不同状态提示,按书顺序播放。例如:正在播放新订单提示,若有新的「新订单」则直接播放最新的新订单语音。
若有新的「超时未接单」语音,则等当前新订单语音播放完毕后,再播放超时未接单语音。
实现
使用SoundPool实现语音提示。
public class SoundUtil {
public static boolean open = false;//开通微店
public static float voiceVolume;//音量
public static boolean newOrderVoice;//新订单语音
public static boolean timeoutOrderVoice;//超时未接单语音
//新订单语音播放中
public static boolean soundNewPlaying = false;
//超时订单语音播放中
public static boolean soundTimeoutPlaying = false;
public static SoundHandler soundHandler;
//
public final static int SOUND_NEW_ORDER = 1;
public final static int SOUND_TIMEOUT_ORDER = 2;
public final static int SOUND_DELAY_NEW_ORDER = 3;
public final static int SOUND_DELAY_TIMEOUT = 4;
//有另外一个语音要播放,需等待5秒
public final static long delay = 5000;
/**
* 资源信息初始化,在打开APP时调用。我是在登陆成功后调用的。
*/
public static void init(Context context) {
//读取SP缓存的语音设置信息
SharedPreferences sp = context.getSharedPreferences(SPUtils.FILLNAME, Context.MODE_PRIVATE);
//音量
voiceVolume = (float) SPUtils.get(sp, SPConstants.KEY_WD_VOICE_VOLUME, 1.0f);
//新订单语音,播放或静音
newOrderVoice = (boolean) SPUtils.get(sp, SPConstants.KEY_WD_VOICE_NEW, true);
//超时未接单语音,播放或静音
timeoutOrderVoice = (boolean) SPUtils.get(sp, SPConstants.KEY_WD_VOICE_TIMEOUT, true);
soundHandler = new SoundHandler();
//加载语音资源
initSound();
}
/**
* 释放资源,关闭APP后调用。我是在退出登录后调用的。
*/
public static void release() {
if (null != soundHandler) {
soundHandler.removeCallbacksAndMessages(null);
soundHandler = null;
}
if (null != mSoundPool) {
mSoundPool.release();
mSoundPool = null;
}
}
/**
* 播放提示音,新的语音要播放时,要延迟5秒。
*
*/
private static void playing(int msg) {
if (null == soundHandler) {
soundHandler = new SoundHandler();
}
switch (msg) {
//新订单
case SOUND_NEW_ORDER:
//有语音在播放时,等待5秒后再去播放语音
if (soundTimeoutPlaying || soundNewPlaying) {
soundHandler.sendEmptyMessageDelayed(SOUND_DELAY_NEW_ORDER, delay);
} else {
soundNewPlaying = true;
mSoundPool.play(mNewOrderSoundResId, voiceVolume, voiceVolume, 1, 0, 1);
soundHandler.sendEmptyMessageDelayed(msg, delay);
}
break;
//超时订单
case SOUND_TIMEOUT_ORDER:
//有语音在播放时,等待5秒后再去播放语音
if (soundTimeoutPlaying || soundNewPlaying) {
soundHandler.sendEmptyMessageDelayed(SOUND_DELAY_TIMEOUT, delay);
} else {
soundTimeoutPlaying = true;
mSoundPool.play(mTimeoutSoundResId, voiceVolume, voiceVolume, 1, 0, 1);
soundHandler.sendEmptyMessageDelayed(msg, delay);
}
break;
}
}
private static SoundPool mSoundPool;
private static int mNewOrderSoundResId;//新订单语音
private static int mTimeoutSoundResId;//超时订单语音
/**
* 加载语音资源
**/
private static void initSound() {
mSoundPool = new SoundPool(1, AudioManager.STREAM_VOICE_CALL, 5);
mNewOrderSoundResId = mSoundPool.load(RegisterApplication.getContext(), R.raw.neworder, 1);
mTimeoutSoundResId = mSoundPool.load(RegisterApplication.getContext(), R.raw.timeout, 1);
}
/**
* 播放语音提示
*/
public static synchronized void playSound(String wdOrderStatus) {
if (StringUtils.equals(WDEnum.MERCHANT_NEW_ORDER.name(), wdOrderStatus) &&
newOrderVoice) {
//新订单
playing(SOUND_NEW_ORDER);
} else if ((StringUtils.equals(WDEnum.ORDER_TIMEOUT_REFUND.name(), wdOrderStatus) ||
StringUtils.equals(WDEnum.MERCHANT_TIMEOUT_REFUNDING.name(), wdOrderStatus)) &&
timeoutOrderVoice) {
//超时未接单
playing(SOUND_TIMEOUT_ORDER);
}
}
static class SoundHandler extends Handler {
@Override
public void handleMessage(Message msg) {
super.handleMessage(msg);
switch (msg.what) {
case SOUND_NEW_ORDER:
soundNewPlaying = false;
break;
case SOUND_TIMEOUT_ORDER:
soundTimeoutPlaying = false;
break;
case SOUND_DELAY_NEW_ORDER:
playing(SOUND_NEW_ORDER);
break;
case SOUND_DELAY_TIMEOUT:
playing(SOUND_TIMEOUT_ORDER);
break;
}
}
}
}
如果有其他更好的实现逻辑的朋友们,请不吝赐教,谢谢。