实验三 广播和服务
实验三 广播和服务
首先确定实验目的:
编写广播接收者程序,当收到短信时,对短信广播做出响应:app会启动音乐播放服务。
顺便,写一个按钮,当收到短信广播时,由不可点击切换为可点击,点击按钮,就可以停止音乐播放。
1. 创建广播接受组件:SmsReceiver.java
1.1 创建一个类SmsReceiver继承类BroadcastReceiver
当接收到广播时,执行重写的onReceive()方法
/*
本广播接收者程序分别调用了应用的主Activity程序和播放音乐的服务程序
*/
public class SmsReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Intent serviceIntent = new Intent(context, MyAudioService.class);
//在广播组件里,通过上下文对象启动音乐播放服务组件
context.startService(serviceIntent);
//新建调用Activity组件的意图
Intent activityIntent = new Intent(context, MainActivity.class);
activityIntent.putExtra("iscast", true); //携带数据
//新建栈用来存放被启动的Activity(当已经存在时,只做移动处理)
activityIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
//在广播组件里,通过上下文对象启动Activity组件
context.startActivity(activityIntent);
}
}
而这个广播接收组件是接收谁发出的广播呢?
1.2 注册广播接受程序
在manifests中的application标签内添加receiver标签
name绑定类,intent-filter过滤请求触发广播
<receiver
android:name=".SmsReceiver"
android:enabled="true"
android:exported="true">
<intent-filter>
<action android:name="android.provider.Telephony.SMS_RECEIVED"/>
</intent-filter>
</receiver>
注意其中的intent-filter标签,里面的配置就是用于过滤其中指定的请求,这里的action标签就是用于过滤出短信消息触发广播。
当手机收到短信时,系统发出一个广播,这里receiver所绑定的SmsReceiver类接受到广播,然后执行onReceive()函数。
2. 添加音乐服务文件MyAudioService.java
我们想要收到广播时,播放音乐,那么我们得添加一个音乐服务
2.1 创建一个类MyAudioService继承类Service
public class MyAudioService extends Service {
MediaPlayer mediaPlayer;
@Override
public IBinder onBind(Intent intent) {
return null;
}
@Override
public void onCreate() {
mediaPlayer = MediaPlayer.create(this, R.raw.liyue);//创建音乐服务。播放R.raw中的音乐liyue
mediaPlayer.start();//开始服务
}
@Override
public void onDestroy() {
mediaPlayer.stop();
}
}
2.2 添加音乐文件
然后在广播中执行这个音乐服务程序
Intent serviceIntent = new Intent(context, MyAudioService.class);
//在广播组件里,通过上下文对象启动音乐播放服务组件
context.startService(serviceIntent);
2.3 服务注册
同时注册服务到manifests,在manifests中的application标签内添加service 标签,绑定服务类MyAudioService
<service android:name=".MyAudioService">
</service>
3. 主界面程序:MainActivity
3.1 界面布局
只需要一个按钮,我们先进行页面布局,添加一个button即可
3.2 短信权限注册
然后我们要接受短信,得在manifest手工添加注册短信接收权限
<uses-permission android:name="android.permission.RECEIVE_SMS"/>
而在主界面程序MainActivity需要写检测短信权限(属于危险权限)及请求申请本权限的代码:
public class MainActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
if (ContextCompat.checkSelfPermission(this, Manifest.permission.RECEIVE_SMS) != PackageManager.PERMISSION_GRANTED){
ActivityCompat.requestPermissions(this,new String[]{"android.permission.RECEIVE_SMS"},1);
}
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
switch (requestCode){
case 1:
if(grantResults[0]!=PackageManager.PERMISSION_GRANTED){
Toast.makeText(this, "未授权,无法实现预定的功能!", Toast.LENGTH_SHORT).show();
finish();
}else{
Toast.makeText(this, "请发一条短信验证...", Toast.LENGTH_SHORT).show();
}
}
}
}
3.3 设置按钮逻辑
当未收到短信时打开mainactivity,isCast=false,按钮不可用(不可点击)
当收到短信时,SmsReceiver收到广播,触发onReceive()函数,启动音乐播放服务组件MyAudioService类。并且使用Intent的putExtra()方法,将一个键值对 iscast : true
传给mainactivity,并且再次启动MainActivity,这时iscast=true,按钮可用。
这时点击按钮,触发按钮的监听事件,停止音乐服务。
public class MainActivity extends AppCompatActivity {
private Button btnStop;
private boolean isCast; //是否为广播激活
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
if (ContextCompat.checkSelfPermission(this, Manifest.permission.RECEIVE_SMS) != PackageManager.PERMISSION_GRANTED){
ActivityCompat.requestPermissions(this,new String[]{"android.permission.RECEIVE_SMS"},1);
}
btnStop=findViewById(R.id.btnStop);
Intent intent = getIntent(); //获取广播意图对象
isCast = intent.getBooleanExtra("iscast", false); //默认值为false
btnStop.setEnabled(isCast); //设置停止按钮可用和单击监听
if(isCast) Toast.makeText(this, "正在播放音乐...", Toast.LENGTH_SHORT).show();
btnStop.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v){
//显式服务调用意图(非绑定式)
Intent intent=new Intent(MainActivity.this, MyAudioService.class);
//在Activity组件里,停止音乐播放服务
stopService(intent);
finish(); //销毁本活动
}
});
}
@Override
public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) {
super.onRequestPermissionsResult(requestCode, permissions, grantResults);
switch (requestCode){
case 1:
if(grantResults[0]!=PackageManager.PERMISSION_GRANTED){
Toast.makeText(this, "未授权,无法实现预定的功能!", Toast.LENGTH_SHORT).show();
finish();
}else{
Toast.makeText(this, "请发一条短信验证...", Toast.LENGTH_SHORT).show();
}
}
}
}
4.实验结果
进入程序,按钮为灰色不可用
点击手机模拟器桌面的短信,给5554(自己)发送短信
收到短信,跳转到程序,音乐开始播放
点击停止按钮,音乐停止播放,程序也同时退出。
5 优化及代码仓库地址
这里我们可以更改按钮监听触发的事件
btnStop.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v){
//显式服务调用意图(非绑定式)
Intent intent=new Intent(MainActivity.this, MyAudioService.class);
//在Activity组件里,停止音乐播放服务
stopService(intent);
isCast=false;
btnStop.setEnabled(isCast);
// finish(); //销毁本活动
}
}
这样,点击按钮后就不会退出程序。而会变灰不可用,当又有短信来时,又可以触发音乐服务,按钮可用,再次点击又可以停止音乐服务。
代码仓库地址:
https://gitee.com/hu_hong_tao/android-development-experiment3
本文地址:https://blog.csdn.net/iamsweet/article/details/109633530
下一篇: LifecycleModel 分享
推荐阅读
-
数据库表的查询操作实践演练(实验三)
-
国家金融大数据实验室(深圳):数字经济时代催生独立第三方大数据应用平台
-
实验四---杨辉三角
-
经典问题(c++/python)素数、杨辉三角(金字塔型)、统计单词数、简单计算器、密码安全程度、凯撒密码加密、汉诺塔 (python课设实验实例)-- biaobiao88
-
第一部分day4-三次登录实验、字符编码
-
前端实验讨论:中英文换不换行,超过给定宽度添加三个点点...
-
真相实验室:真假三星曲面面板如何区分?
-
索尼开放自主AI技术 第三方可用于自家产品和服务
-
《数据挖掘导论》实验课——实验三、数据挖掘之决策树
-
泰尔实验室颁发首个折叠屏手机五星证书:三星Galaxy Z Fold3