Android广播学习(二)——自定义广播

本节新建一个项目day09_MyBroadcastReceiver,记为项目一

Android 8.0及以上 在xml中注册的广播,在接收的时候收到了额外的限制,如果你的app目标等级是26及以上,将无法接收到xml注册的广播,这是google 为了app注册的静态广播导致耗电加的限制。

既然不能静态注册,那么有啥可用的注册方法呢?

一、无需注册就能发送定向发送广播

定向发送广播,广播接收器无需注册【静态注册和动态注册都不需要】,必须指定本包的的广播接收器,无法向其他应用发送广播

1、创建广播接收器

MyBroadcastReceiver.java

public class MyBroadcastReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        Toast.makeText(context,"自定义广播接收器已经接收到消息", Toast.LENGTH_LONG).show();
    }
}

2、主布局修改

没啥好说的,就一个按钮

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical" android:layout_width="match_parent"
    android:layout_height="match_parent">
    
    <Button
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="发送广播"
        android:id="@+id/button"/>

</LinearLayout>

3、主活动

 public class MainActivity extends AppCompatActivity {

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

        Button button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent();
                //第一个参数为包的路径,第二个参数为接收器名
                intent.setComponent(new ComponentName(getPackageName(), "com.example.day09_mybroadcastreceiver.MyBroadcastReceiver"));
                sendBroadcast(intent);
            }
        });
    }
}

一定要指定接收器的位置,而且这条广播是通过Intent进行传递的,所以还可以在Intent中携带一些数据传递给广播接收器。

4、运行

在这里插入图片描述

本节新建一个项目day09_MyBroadcastReceiver2,记为项目二

二、动态注册发送不定向广播

1、创建广播接收器

public class AnotherBroadCastReceiver extends BroadcastReceiver {

    @Override
    public void onReceive(Context context, Intent intent) {
        Toast.makeText(context, "收到不定向广播消息", Toast.LENGTH_LONG).show();
    }
}

主活动

public class MainActivity extends AppCompatActivity {
//    设置为静态可以解决重复注册的问题
    static AnotherBroadCastReceiver anotherBroadCastReceiver;

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

        IntentFilter intentFilter = new IntentFilter();
        intentFilter.addAction("MyBroadcast");
        if (anotherBroadCastReceiver == null) {
            anotherBroadCastReceiver = new AnotherBroadCastReceiver();
            registerReceiver(anotherBroadCastReceiver, intentFilter);
        }
    }
}

再去修改项目一的主活动:

public class MainActivity extends AppCompatActivity {

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

        Button button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent("MyBroadcast");
                sendBroadcast(intent);
            }
        });
    }
}

2、测试广播接收器

这里的不定向指没有指明广播接收器,而是由动态注册的广播接收器接收广播,广播接收器必须在代码中动态注册,【可以取消注册,但取消注册后,无法在应用关闭后响应内容】
修改项目day09_MyBroadcastReceiver的主活动,添加

将两个项目安装在同一台虚拟机内,然后依次启动项目2,项目1

启动项目2:
在这里插入图片描述
项目1发送一条广播,项目2可以接收:
在这里插入图片描述
关闭项目2,再发送广播就不能接收到了:
在这里插入图片描述
由此可见,动态注册的广播接收器只能在活动启动时接收广播

3、有序广播设置

懒得再运行了,凑合看吧:

public class MainActivity extends AppCompatActivity {
//    设置为静态可以解决重复注册的问题
    static AnotherBroadCastReceiver anotherBroadCastReceiver;

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

        if (anotherBroadCastReceiver == null) {
            IntentFilter intentFilter = new IntentFilter();
            intentFilter.addAction("MyBroadcast");
            // setPriority()设置权限大小
            intentFilter.setPriority(1000);
            anotherBroadCastReceiver = new AnotherBroadCastReceiver();
            registerReceiver(anotherBroadCastReceiver, intentFilter);
            Toast.makeText(this, "2 完成注册", Toast.LENGTH_LONG).show();
        }
    }
}

发送广播用sendOrderedBroadcast()方法目的一个参数仍然是Intent,第二个参数是和权限相关的字符串,填写null就行了。
有序广播可以被截断,用abortBroadcast()等方法。
【参考资料】

三、本地广播

本地广播和这篇文章的定向广播几乎完全一样,发送的广播不会离开本程序,其他程序的广播也不会到本程序的内部,而且同样高效【但具体哪个更高效还没测试】,相比之下,本文的定向广播使用起来更加简单。

但本地广播也有自己的优势,比如可以使本地的多个广播接收器都接收一个广播,而定向广播每次都要一个一个指定接收器~

代码直接改项目1的定向广播的代码。

1、引入依赖库

implementation 'androidx.localbroadcastmanager:localbroadcastmanager:1.0.0'

2、其他

主活动修改

 public class MainActivity extends AppCompatActivity {
     private IntentFilter intentFilter;
     private LocalReceiver localReceiver;
     private LocalBroadcastManager localBroadcastManger;

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

//        获取实例
        localBroadcastManger = localBroadcastManger.getInstance(this);
        Button button = (Button) findViewById(R.id.button);
        button.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                Intent intent = new Intent("LocalBroadcast");
                // 发送广播
                localBroadcastManger.sendBroadcast(intent);
            }
        });
        
//        注册广播
        intentFilter = new IntentFilter();
        intentFilter.addAction("LocalBroadcast");
        localReceiver = new LocalReceiver();
        localBroadcastManger.registerReceiver(localReceiver, intentFilter);
    }

     @Override
     protected void onDestroy() {
         super.onDestroy();
         localBroadcastManger.unregisterReceiver(localReceiver);
     }

     private class LocalReceiver extends BroadcastReceiver {
         @Override
         public void onReceive(Context context, Intent intent) {
             Toast.makeText(context, "已接收到本地广播!",Toast.LENGTH_LONG).show();
         }
     }
 }

3、运行

在这里插入图片描述

  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 3
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值