Android基础——Notification 8.0适配详解

1. Android 8.0 系统通知栏适配

NotificationChannel是android8.0新增的特性,如果App的targetSDKVersion>=26,没有设置channel通知渠道的话,就会导致通知无法展示。

什么是通知渠道呢?顾名思义,就是每条通知都要属于一个对应的渠道。每个App都可以自由地创建当前App拥有哪些通知渠道,但是这些通知渠道的控制权都是掌握在用户手上的。用户可以自由地选择这些通知渠道的重要程度,是否响铃、是否振动、或者是否要关闭这个渠道的通知。

拥有了这些控制权之后,用户就再也不用害怕那些垃圾推送消息的打扰了,因为用户可以自主地选择自己关心哪些通知、不关心哪些通知。例如高德地图,你只想收到骑行提醒、个人消息提醒,不想收到运营活动提醒等,可以创建相应的通知渠道,将运营互动通知渠道关闭,则既可以接收到关心的通知,又不会接收到那些我不关心的通知。对于App来说,通知渠道划分需仔细考究,一旦创建就不能再修改。

在这里插入图片描述

1.1 创建通知渠道

如果你的项目targetSdkVersion指定到了26或者更高,则必须要对Notification进行适配。

public class MainActivity extends AppCompatActivity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            String channelId = "chat";
            String channelName = "聊天消息";
            int importance = NotificationManager.IMPORTANCE_HIGH;
            createNotificationChannel(channelId, channelName, importance);

            channelId = "subscribe";
            channelName = "订阅消息";
            importance = NotificationManager.IMPORTANCE_DEFAULT;
            createNotificationChannel(channelId, channelName, importance);
        }
    }


    @TargetApi(Build.VERSION_CODES.O)
    private void createNotificationChannel(String channelId, String channelName, int importance) {
        NotificationChannel channel = new NotificationChannel(channelId, channelName, importance);
        NotificationManager notificationManager = (NotificationManager) getSystemService(
                NOTIFICATION_SERVICE);
        notificationManager.createNotificationChannel(channel);
    }
}

备注

  • 首先要做版本判断,低版本是没有通知渠道这个功能,不做系统版本检查的话会在低版本手机上造成崩溃
  • 创建一个渠道至少需要:渠道ID渠道名称重要等级这三个参数,渠道ID要保证全局唯一性;渠道名称是展示给用户看的,需要能够表达清楚这个渠道用途。重要等级不同决定通知的不同行为,替代了低版本的PRIORITY,用户可以随时手动更改某个渠道的重要等级。

现在就可以运行一下代码了,运行成功之后我们关闭App,进入到设置 -> 应用 -> 通知当中,可以看到我们创建的两个通知渠道已经显示出来了。

1.2 展示通知

发送通知与低版本的操作几乎没有差别,主要差异在在构建通知对象的时候,需要多传入一个通知渠道ID,表示这条通知是属于哪个渠道的。

代码示例如下:

<?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="wrap_content"
        android:layout_height="wrap_content"
        android:text="发送聊天消息"
        android:onClick="sendChatMsg"
        />

    <Button
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:text="发送订阅消息"
        android:onClick="sendSubscribeMsg"
        />
</LinearLayout>
public class MainActivity extends AppCompatActivity {

    ...

    public void sendChatMsg(View view) {
        NotificationManager manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        Notification notification = new NotificationCompat.Builder(this, "chat")
                .setContentTitle("收到一条聊天消息")
                .setContentText("今天中午吃什么?")
                .setWhen(System.currentTimeMillis())
                .setSmallIcon(R.drawable.icon)
                .setLargeIcon(BitmapFactory.decodeResource(getResources(), R.drawable.icon))
                .setAutoCancel(true)
                .build();
        manager.notify(1, notification);
    }

    public void sendSubscribeMsg(View view) {
        NotificationManager manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        Notification notification = new NotificationCompat.Builder(this, "subscribe")
                .setContentTitle("收到一条订阅消息")
                .setContentText("地铁沿线30万商铺抢购中!")
                .setWhen(System.currentTimeMillis())
                .setSmallIcon(R.drawable.icon)
                .setLargeIcon(BitmapFactory.decodeResource(getResources(), R.drawable.icon))
                .setAutoCancel(true)
                .build();
        manager.notify(2, notification);
    }
}

1.3 管理通知渠道

Android赋予了开发者读取通知渠道配置的权限,如果我们某个功能必须按照指定要求来配置通知渠道才能使用,那么就可以提示用户去手动更改通知渠道配置。

public class MainActivity extends AppCompatActivity {

    ...

    public void sendChatMsg(View view) {
        NotificationManager manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
            NotificationChannel channel = manager.getNotificationChannel("chat");
            if (channel.getImportance() == NotificationManager.IMPORTANCE_NONE) {
                Intent intent = new Intent(Settings.ACTION_CHANNEL_NOTIFICATION_SETTINGS);
                intent.putExtra(Settings.EXTRA_APP_PACKAGE, getPackageName());
                intent.putExtra(Settings.EXTRA_CHANNEL_ID, channel.getId());
                startActivity(intent);
                Toast.makeText(this, "请手动将通知打开", Toast.LENGTH_SHORT).show();
            }
        }

        Notification notification = new NotificationCompat.Builder(this, "chat")
                ...
                .build();
        manager.notify(1, notification);
    }

    ...

}

通过getNotificationChannel()方法获取到了NotificationChannel对象,然后就可以读取该渠道下的所有配置。这里我们判断如果通知渠道的importance等于IMPORTANCE_NONE,就说明用户将该渠道的通知给关闭了,这时会跳转到通知的设置界面提醒用户手动打开。

除此之外,,Android8.0还赋予我们删除通知渠道的功能,只需要执行如下代码:

NotificationManager manager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
manager.deleteNotificationChannel(channelId);

但是这个功能非常不建议大家使用。因为Google为了防止应用程序随意地创建垃圾通知渠道,会在通知设置界面显示所有被删除的通知渠道数量,如下图所示:

在这里插入图片描述
这种界面展示是非常不美观的,建议一开始就仔细规划好通知渠道,不要轻易使用删除功能。

猜你喜欢

转载自blog.csdn.net/weixin_43499030/article/details/90290166