效果图:
Android——实现在 Service 中播放音乐_后台播放音乐

Android——实现在 Service 中播放音乐_王睿丶_02

在写代码之前,我先告诉你们一个坑点,我在实现这个功能的时候,在导入raw文件时遇到了一个坑,找不到这个文件夹,如果你们也遇到了这种情况,参考我之前写的一篇博客,即可解决问题 

MusicService.java

public class MusicService extends Service {
    private MediaPlayer mediaPlayer;        //  音乐管理器对象

    @Override
    public IBinder onBind(Intent intent) {
        mediaPlayer.start();                //  开始启动音乐
        mediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {    //  启动音乐后,音乐播放器的监听器
            @Override
            public void onCompletion(MediaPlayer mp) {
                //  循环播放
                try {
                    mediaPlayer.start();                //  不断开始
                }catch (IllegalStateException e){
                    e.printStackTrace();
                }
            }
        });
        //  播放音乐时发生错误的事件处理
        mediaPlayer.setOnErrorListener(new MediaPlayer.OnErrorListener() {
            @Override
            public boolean onError(MediaPlayer mp, int what, int extra) {
                try {
                    mediaPlayer.release();
                }catch (Exception e){
                    e.printStackTrace();
                }
                return false;
            }
        });
        return null;
    }

    @Override
    public void onCreate() {
        super.onCreate();
        mediaPlayer = new MediaPlayer();        //  实例化音乐管理器对象
        mediaPlayer = MediaPlayer.create(MusicService.this,R.raw.ic_bg);    //  拿到资源

        try{
            mediaPlayer.prepare();      //  每一次开始播放(start)前,必须先进行准备(prepare)操作
        }catch (IllegalStateException e){
            e.printStackTrace();
        }catch (IOException e){
            e.printStackTrace();
        }
    }

    @Override
    public boolean onUnbind(Intent intent) {
        //  停止播放,释放资源
        mediaPlayer.stop();         //  停止
        mediaPlayer.release();      //  播放结束后,释放资源
        return super.onUnbind(intent);
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
    }
}

LoginActivity.java

public class LoginActivity extends AppCompatActivity {
    private CheckBox cbMusic;       //  是否播放音乐
    private SharedPreferences sp;       //  轻量级数据库
    private SharedPreferences.Editor editor;    //
    private Button button;          //  登录

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_login);
        sp = getSharedPreferences("user",MODE_PRIVATE);     //  创建一个 user 的表,并实例化这个对象
        cbMusic = findViewById(R.id.cb_music);
        if (sp.getBoolean("isMusic", false)) {      //  进入到数据库中查询,如果值为真,默认勾选复选框
            cbMusic.setChecked(true);
        }

        cbMusic.setOnCheckedChangeListener(new CompoundButton.OnCheckedChangeListener() {           //  复选框的监听事件
            @Override
            public void onCheckedChanged(CompoundButton buttonView, boolean isChecked) {
                editor = sp.edit();
                editor.putBoolean("isMusic",cbMusic.isChecked());       //  将结果 存到 isMusic 这一列中
                editor.commit();            //  提交事务
            }
        });
        button = findViewById(R.id.btn_deng);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent(LoginActivity.this,MainActivity.class);
                startActivity(intent);
            }
        });
    }
}

MainActivity.java

public class MainActivity extends AppCompatActivity {
    private SharedPreferences sp;
    private boolean isExit = false;
    private Handler handler = new Handler(){
        @Override
        public void handleMessage(Message msg) {        //  异步处理机制销毁整个进程
            super.handleMessage(msg);
            isExit = false;
        }
    };

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        sp = getSharedPreferences("user",MODE_PRIVATE);         //  进入 SharedPreferences 数据库中查找 user 表
        if (sp.getBoolean("isMusic", false)) {          //  查找 isMusic 这列的数据,得到用户是否打钩,打钩返回 true
            Intent intent = new Intent(MainActivity.this,MusicService.class);       //  在服务中播放音乐
            ServiceConnection connection = new ServiceConnection() {
                @Override
                public void onServiceConnected(ComponentName name, IBinder service) {

                }

                @Override
                public void onServiceDisconnected(ComponentName name) {

                }
            };
            bindService(intent,connection,Service.BIND_AUTO_CREATE);    //  通过 bindService 方式 启动 Service
        }
    }

    /**
     *      基于 Handler 实现用户连续点击两次返回键退出程序的功能,立即终止整个进程办法是
     *      在 finish 方法执行后,立即调用 System.exit(0) 方法终止整个进程
     */
    public boolean onKeyDown(int keyCode, KeyEvent event){
        if (keyCode == KeyEvent.KEYCODE_BACK){
            if (!isExit){
                isExit = true;
                Toast.makeText(getApplicationContext(),"再按一次退出程序",Toast.LENGTH_LONG).show();
                handler.sendEmptyMessageDelayed(0,2000);
            }else{
                MainActivity.this.finish();     //  进入销毁的排队序列
                System.exit(0);         //  终止整个进程
            }
            return false;
        }
        return super.onKeyDown(keyCode,event);
    }
}

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".MainActivity">
</RelativeLayout>

activity_login.xml

<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    tools:context=".LoginActivity">

    <CheckBox
        android:id="@+id/cb_music"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerInParent="true"
        android:text="播放音乐"/>

    <Button
        android:id="@+id/btn_deng"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_centerHorizontal="true"
        android:layout_marginTop="40dp"
        android:textSize="20dp"
        android:text="登录"/>

</RelativeLayout>