我是靠谱客的博主 威武心情,最近开发中收集的这篇文章主要介绍Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放

最开始遇到这个问题的思路是在选择音乐时发送一条广播给music然后让它暂停音乐

代码如下:

public class MainActivity extends AppCompatActivity {
    private static boolean flagMusic;
    private AudioManager audioManager = null;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
        boolean vIsActive = audioManager.isMusicActive();
        if (vIsActive) {
            Toast.makeText(getApplicationContext(), "有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = true;//记录音乐播放状态 true为正在播放 ,反之
            pauseMusic();//暂停音乐播放
        } else {
            Toast.makeText(getApplicationContext(), "没有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = false;
        }
    }

    private void pauseMusic() {
        Intent freshIntent = new Intent();
        freshIntent.setAction("com.android.music.musicservicecommand.pause");
        freshIntent.putExtra("command", "pause");
        sendBroadcast(freshIntent);
    }

    private void continuMusic() {
        Intent freshIntent = new Intent();
        freshIntent.setAction("com.android.music.musicservicecommand.togglepause");
        freshIntent.putExtra("command", "togglepause");
        sendBroadcast(freshIntent);
    }

    @Override
    protected void onStart() {
        super.onStart();
        audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
        boolean vIsActive = audioManager.isMusicActive();
        if (vIsActive) {
            Toast.makeText(getApplicationContext(), "有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = true;//记录音乐播放状态 true为正在播放 ,反之
            pauseMusic();//暂停音乐播放
        } else {
            Toast.makeText(getApplicationContext(), "没有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = false;
        }
    }

    @Override
    protected void onPause() {
        super.onPause();
        audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
        boolean vIsActive = audioManager.isMusicActive();
        if (!vIsActive) {
            Toast.makeText(getApplicationContext(), "有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = true;//记录音乐播放状态 true为正在播放 ,反之
            continuMusic();//暂停音乐播放
        } else {
            Toast.makeText(getApplicationContext(), "没有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = false;
        }
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        audioManager = (AudioManager) getSystemService(Context.AUDIO_SERVICE);
        boolean vIsActive = audioManager.isMusicActive();
        if (!vIsActive) {
            Toast.makeText(getApplicationContext(), "有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = true;//记录音乐播放状态 true为正在播放 ,反之
            continuMusic();//暂停音乐播放
        } else {
            Toast.makeText(getApplicationContext(), "没有音乐在播放", Toast.LENGTH_SHORT).show();
            flagMusic = false;
        }
    }
}

但是这个只针对自带音乐app生效 所以换了个思路

在设置调节音量的时候获取音频焦点 调节结束的时候松开之后释放音频焦点
这样在调节的时候就可以暂停音乐 松开之后音乐自动就开始播放了

首先在源码中找到对应的类:
/frameworks/base/core/java/android/preference/SeekBarVolumizer.java
类应是调节音量的SeekBar
首先来看Seekar的三个回调函数:

@Override
    public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {

    }

    @Override
    public void onStartTrackingTouch(SeekBar seekBar) {
        mHandler.sendEmptyMessageDelayed(1,500);
        //开始调节SeekBar的时候会调用这里
    }

    @Override
    public void onStopTrackingTouch(SeekBar seekBar) {
    //调节SeekBar结束的时候会调用这里
    }

我们来看一下AOSP中的源码:

public void onProgressChanged(SeekBar seekBar, int progress, boolean fromTouch) {
        if (fromTouch) {
            postSetVolume(progress);
        }
        if (mCallback != null) {
            mCallback.onProgressChanged(seekBar, progress, fromTouch);
        }
    }

    private void postSetVolume(int progress) {
        if (mHandler == null) return;
        // Do the volume changing separately to give responsive UI
        mLastProgress = progress;
        mHandler.removeMessages(MSG_SET_STREAM_VOLUME);
        mHandler.sendMessage(mHandler.obtainMessage(MSG_SET_STREAM_VOLUME));
    }

    public void onStartTrackingTouch(SeekBar seekBar) {
    }

    public void onStopTrackingTouch(SeekBar seekBar) {
        postStartSample();//松开SeekBar的时候播放提示音
    }

方法其实很简单:
在onStartTrackingTouch()的时候获取到音频焦点
在onStopTrackingTouch()时释放焦点
这样在滑动SeekBar的时候后台的音乐会暂停
松开SeekBar的时候音乐就继续播放了,代码如下:

public void onStartTrackingTouch(SeekBar seekBar) {
        mAudioManager.requestAudioFocus(mAudioFocusListener, AudioManager.STREAM_RING, AudioManager.AUDIOFOCUS_GAIN_TRANSIENT);
    }

    public void onStopTrackingTouch(SeekBar seekBar) {
        mAudioManager.abandonAudioFocus(mAudioFocusListener);
        postStartSample();
        Log.e("SeekBarVolumizer","Start to play cue music");
    }
    
    private AudioManager.OnAudioFocusChangeListener mAudioFocusListener = new AudioManager.OnAudioFocusChangeListener() {
        public void onAudioFocusChange(int focusChange) {
            Log.d(TAG, "onAudioFocusChange:" + focusChange );
            switch (focusChange) {
                case AudioManager.AUDIOFOCUS_LOSS:
                case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT:
                case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK:
                    break;
            }
        }
    };
    

但是 当你编译好之后会发现
松开SeekBar的时候 后台的音乐会和调节音量后的提示音一起播放了
原因是因为在系统播放提示音的时候没有去requestAudioFocus()
而直接去播放了提示音
顺着postStartSample();往下找会发现:

private void postStartSample() {
        if (mHandler == null) return;
        mHandler.removeMessages(MSG_START_SAMPLE);
        mHandler.sendMessageDelayed(mHandler.obtainMessage(MSG_START_SAMPLE),
                isSamplePlaying() ? CHECK_RINGTONE_PLAYBACK_DELAY_MS : 0);
    }

发送了一条MSG_START_SAMPLE,最后执行的代码如下:

private void onStartSample() {
        if (!isSamplePlaying()) {
            if (mCallback != null) {
                mCallback.onSampleStarting(this);
            }

            synchronized (this) {
                if (mRingtone != null) {
                    try {
                        mRingtone.setAudioAttributes(new AudioAttributes.Builder(mRingtone
                                .getAudioAttributes())
                                .setFlags(AudioAttributes.FLAG_BYPASS_MUTE)
                                .build());
                        mAudioManager.requestAudioFocus(mAudioFocusListener, AudioManager.STREAM_RING, AudioManager.AUDIOFOCUS_GAIN_TRANSIENT);        //获得音频焦点
                        mRingtone.play();  //播放提示音
                        mHandler.sendMessageDelayed(mHandler.obtainMessage(MSG_INIT_WAITING),1000); //延迟1秒钟之后释放焦点
                    } catch (Throwable e) {
                        Log.w(TAG, "Error playing ringtone, stream " + mStreamType, e);
                    }
                }
            }
        }
    }

handleMessage()如下:

@Override
    public boolean handleMessage(Message msg) {
        switch (msg.what) {
            case MSG_SET_STREAM_VOLUME:
                if (mMuted && mLastProgress > 0) {
                    mAudioManager.adjustStreamVolume(mStreamType, AudioManager.ADJUST_UNMUTE, 0);
                } else if (!mMuted && mLastProgress == 0) {
                    mAudioManager.adjustStreamVolume(mStreamType, AudioManager.ADJUST_MUTE, 0);
                }
                mAudioManager.setStreamVolume(mStreamType, mLastProgress,
                        AudioManager.FLAG_SHOW_UI_WARNINGS);
                break;
            case MSG_START_SAMPLE:
                onStartSample();
                break;
            case MSG_STOP_SAMPLE:
                onStopSample();
                break;
            case MSG_INIT_SAMPLE:
                onInitSample();
                break;
                case MSG_INIT_WAITING:
                mAudioManager.abandonAudioFocus(mAudioFocusListener);
                break;
            default:
                Log.e(TAG, "invalid SeekBarVolumizer message: "+msg.what);
        }
        return true;
    }

这样滑动SeekBar的时候音乐会暂停下来 松开SeekBar之后播放提示音 一秒之后音乐就会继续播放啦
(≧▽≦)

最后

以上就是威武心情为你收集整理的Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放的全部内容,希望文章能够帮你解决Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放Android播放音乐时,在设置中调节铃声大小或者设置铃声的时候提示音与音乐一起播放所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(36)

评论列表共有 0 条评论

立即
投稿
返回
顶部