Badge分析&如何逼死处女座

作者: eclipse_xu | 来源:发表于2015-12-07 16:05 被阅读15062次

Badge分析

所谓Badge,原本是iOS上的一个效果,但是被Android抄的多了,也就成了Android的标配。图就不上了,大家都懂的。

应用icon显示角标实际上是在Launcher中实现的,其实不管是角标还是其他对快捷方式的增删改查,都是需要Launcher支持的,应用在增删改查快捷方式和安装、卸载时,都会发出相应的广播,通过这个广播,Launcher会对快捷方式进行修改。

很庆幸,Android原生ROM的Launcher并不具有给icon添加角标的功能,因为Android的设计思想是把所有消息中心都放置在Notification通知栏中,只有iOS这种通知栏半残废的,才会使用角标。这玩意儿,让强迫症患者,完全不能自理,每日陷落在清除小红点的生活中。

很悲剧,Android的AOSP代码被国内各大ROM厂商改的不能自理。很多被修改的ROM都可以支持这种角标的功能,甚至是很多第三方Launcher,也提供了这种功能。其基本原理也是天下一大抄,都是监听发出的广播来进行快捷方式的修改,但是,关键是没有Google亲爹的支持,所有的实现都不统一,大家自己做自己的,没有统一的接口,导致各种碎片化非常严重。

现在原理很清晰了,关键就是要尽可能多的找到这些ROM、Launcher的修改icon的广播。

在调查该问题时,我找到了https://github.com/leolin310148/ShortcutBadger 这个库,很多地方参考了这个库,但是该库由于很久没有维护了,所以我提取了里面收集的一些Badge的方法,并做了完善,这里对作者表示感谢。

各种ROM角标分析

MIUI6&7 Badge

以下内容来自MUI开发者平台:

一、基本介绍

1、默认的情况

当app 向通知栏发送了一条通知 (通知不带进度条并且用户可以删除的),那么桌面app icon角标就会显示1.此时app显示的角标数是和通知栏里app发送的通知数对应的,即向通知栏发送了多少通知就会显示多少角标。

2、通知可以定义角标数

例如 有5封未读邮件,通知栏里只会显示一条通知,但是想让角标显示5. 可以在发通知时加个标示。

修改MIUI的原理是通过反射拿到Notification的私有属性extraNotification,但是这个extraNotification在MIUI系统中重定义了,这个类就是MIUI系统中的android.app.MiuiNotification这个类,这个类里面有个私有属性messageCount,我们只要改变这个messageCount值就能显示的改变app icon的角标数了。

二、实现代码

第三方app需要用反射来调用,参考代码:

/**
 * 设置MIUI的Badge
 *
 * @param context context
 * @param count   count
 */
private static void setBadgeOfMIUI(Context context, int count) {
    Log.d("xys", "Launcher : MIUI");
    NotificationManager mNotificationManager = (NotificationManager) context
            .getSystemService(Context.NOTIFICATION_SERVICE);
    Notification.Builder builder = new Notification.Builder(context)
            .setContentTitle("title").setContentText("text").setSmallIcon(R.mipmap.ic_launcher);
    Notification notification = builder.build();
    try {
        Field field = notification.getClass().getDeclaredField("extraNotification");
        Object extraNotification = field.get(notification);
        Method method = extraNotification.getClass().getDeclaredMethod("setMessageCount", int.class);
        method.invoke(extraNotification, count);
    } catch (Exception e) {
        e.printStackTrace();
    }
    mNotificationManager.notify(0, notification);
}

Sony Badge

https://forsberg.ax/en/blog/android-notification-badge-app-icon-sony/

Samsung Badge

方法一

通过三星Launcher自己的广播,来给应用添加角标:

/**
 * 设置三星的Badge
 *
 * @param context context
 * @param count   count
 */
private static void setBadgeOfSumsung(Context context, int count) {
    // 获取你当前的应用
    String launcherClassName = getLauncherClassName(context);
    if (launcherClassName == null) {
        return;
    }
    Intent intent = new Intent("android.intent.action.BADGE_COUNT_UPDATE");
    intent.putExtra("badge_count", count);
    intent.putExtra("badge_count_package_name", context.getPackageName());
    intent.putExtra("badge_count_class_name", launcherClassName);
    context.sendBroadcast(intent);
}

此方法不需要任何权限,只需要知道App的包名和类名。因此,你当然可以在程序里面给其它任意一个App设置任意数量的角标,而且没有任何提示,是的,很流氓,谁说不是呢,当然别说是我告诉你的,你就所你是百度的。例如:

intent.putExtra("badge_count_package_name", "com.tencent.mobileqq");
    intent.putExtra("badge_count_class_name", "com.tencent.mobileqq.activity.SplashActivity");

将包名和类名用QQ的替换下,然后你就可以随心所欲、为所欲为了。

方法二

https://github.com/shafty023/SamsungBadger

LG Badge

Samsung好基友,三星能用的,LG几乎都可以用,连Bug都一样。

华为EMUI Badge

目前华为的ROM只支持给内置的App添加角标,华为本身没有给出相应的接口。

酷派 Badge

简单粗暴,不支持。我喜欢,类原生。

ZUK ZUI Badge

ZUK作为一个非常小众的手机厂商,居然在网上官方给出了详细的开发者文档,就这一点,很多大厂都该好好打打自己的耳光。

由于实在找不到ZUK的测试机,所以这里给出ZUK的开发者文档,有需要的自己看看吧:

http://developer.zuk.com/detail/12

HTC Badge

HTC虽然没落了,但好歹是第一只Android的寄生兽,好歹也支持下。

Intent intentNotification = new Intent("com.htc.launcher.action.SET_NOTIFICATION");
ComponentName localComponentName = new ComponentName(context.getPackageName(),
        AppInfoUtil.getLauncherClassName(context));
intentNotification.putExtra("com.htc.launcher.extra.COMPONENT", localComponentName.flattenToShortString());
intentNotification.putExtra("com.htc.launcher.extra.COUNT", count);
context.sendBroadcast(intentNotification);

Intent intentShortcut = new Intent("com.htc.launcher.action.UPDATE_SHORTCUT");
intentShortcut.putExtra("packagename", context.getPackageName());
intentShortcut.putExtra("count", count);
context.sendBroadcast(intentShortcut);

其原理同样是使用广播,不解释了。

锤子

锤子很遗憾,使用的是原生Launcher进行的修改,只有System App具有获得角标的权限。

Nova Badge

Nova是一款非常赞的Launcher,作为第三方Launcher,它的使用率非常高(当然是在国外)。该Launcher作为业界良心,提供了content provider供外界调用。与ZUK手机一样,良心大大的好,代码如下:

ContentValues contentValues = new ContentValues();
contentValues.put("tag", context.getPackageName() + "/" +
        AppInfoUtil.getLauncherClassName(context));
contentValues.put("count", count);
context.getContentResolver().insert(Uri.parse("content://com.teslacoilsw.notifier/unread_count"),
        contentValues);

一些好玩的

在知道了一些ROM的生成角标的原理,我们可以做一些好玩的东西。前面在说LG三星Sony的ROM的时候,已经提到了,广播只需要传人包名和启动Activity名就可以给任意一个icon添加角标,因此。。。直接看代码吧:

/**
 * Bug利用测试,请勿滥用
 *
 * @param view view
 */
public void madMode(View view) {
    madMode(99);
}

/**
 * 清除Bug角标
 *
 * @param view view
 */
public void cleanMadMode(View view) {
    madMode(0);
}

/**
 * 获取所有App的包名和启动类名
 *
 * @param count count
 */
private void madMode(int count) {
    Intent intent = new Intent(Intent.ACTION_MAIN, null);
    intent.addCategory(Intent.CATEGORY_LAUNCHER);
    List<ResolveInfo> list = getPackageManager().queryIntentActivities(
            intent, PackageManager.GET_ACTIVITIES);
    for (int i = 0; i < list.size(); i++) {
        ActivityInfo activityInfo = list.get(i).activityInfo;
        String activityName = activityInfo.name;
        String packageName = activityInfo.applicationInfo.packageName;
        BadgeUtil.setBadgeOfMadMode(getApplicationContext(), count, packageName, activityName);
    }
}

非常简单的代码,就是通过PM找出具有启动Intent的Activity,再取出其包名,通过设置来添加角标。效果如图:

device-2015-12-07-141255.png device-2015-12-07-141314.png device-2015-12-07-141337.png

OK,丧心病狂,逼死强迫症处女座。

请勿滥用,由此引起的一切问题,不要找我

请不要提桌面背景!!!

Github

忘记发地址了
https://github.com/xuyisheng/ShortcutHelper

相关文章

网友评论

  • 6a89f5402829:忍不住用华为手机使用华为最新的,华为貌似对此进行屏蔽了
  • 艾特五三:厉害了,有轻度的密集恐惧症
  • captain991:最后两张图简直丧心病狂,摔
  • 逗你玩222:大佬, BadgeUtil.setBadgeCount(getApplicationContext(), 4);这句代码有bug,,,怎么破
  • fa555e6d4d77:请问这篇文章,现在有最新的适配更多手机的icon角标显示的demo吗,我试了其他的网上案例,有很多都不支持,急求,可@1107762647@qq.com,感激涕零,困扰中
    逗你玩222:大佬, BadgeUtil.setBadgeCount(getApplicationContext(), 4);这句代码有bug,,,怎么破
    fa555e6d4d77:@eclipse_xu 我已经放弃挣扎了,通过联系各大平台手机客服了,多谢
    eclipse_xu:@fa555e6d4d77 请放弃。。
  • newstudio:大佬, BadgeUtil.setBadgeCount(getApplicationContext(), 4);这句代码有bug,,,怎么破
  • 98258fa6d4d5:华为的实现方式

    /**
    * 设置华为的Badge
    * 需添加权限:<uses-permission android:name="com.huawei.android.launcher.permission.CHANGE_BADGE" />
    *
    * @param context context
    * @param count count
    */
    public static void setBadgeOfHuawei(Context context, int count) {
    String launcherClassName = com.xys.badge_lib.AppInfoUtil.getLauncherClassName(context);

    if (TextUtils.isEmpty(launcherClassName)) {
    Log.d("BadgeUtil", "Main activity is null");
    return;
    }
    Bundle localBundle = new Bundle();
    localBundle.putString("package", context.getPackageName());
    localBundle.putString("class", launcherClassName);
    localBundle.putInt("badgenumber", count);
    context.getContentResolver().call(Uri.parse("content://com.huawei.android.launcher.settings/badge/"), "change_badge", null, localBundle);
    }
    b0560b63b4cc:@加肠加蛋 就没有一个能适用于大部分手机的方法吗?
  • object_小车:桌面背景好评。
  • 6ca3a27af965:楼主,我用小米测试,如果点了一次显示角标,然后点击程序,取消了后,再点就不显示了,请问你遇到过吗?
    eclipse_xu:@悠闲的鱼102 小米自己不解决 没办法
    6ca3a27af965:@eclipse_xu 有什么好的建议吗?感觉再也不爱安卓了,太坑了,到处都是定制的东西 :joy:
    eclipse_xu:@悠闲的鱼102 小米有bug
  • 76ffef5441ab:照片比 本人显老啊,医生。
    76ffef5441ab:@eclipse_xu 在上次的推广活动,有幸见到传说中的的 android医生 :smirk:
    eclipse_xu:@Android里的海贼王 :wink:
  • dc5ece92c4d5:为什么我运行不了,运行后,所以app都不能点击了
  • NapleC:十万点
  • 红发_SHANKS:我想把手机摔掉
  • 老兔逸想天开:请问下,有没有办法知道安卓这款机器是否成功展示了红点?
  • sharkliu:恩,因图片背景点赞!单单因为背景,楼主不要想太多。。。 :relaxed:
  • hmz:锤子桌面的微信也有角标。。。
  • fancychendong:很般配:smile:
  • a1c235585c67:作为脆皮的单身狗,你这样真的好么
  • 冰冰的冻结:看看你的代码吧
  • OKernel:桌面...你还加了个强制获取焦点...是怕伤害不够么!
  • mrwangyong:单身狗表示已遭受100000点伤害!
  • 程序亦非猿:这1000点伤害 怎么赔?说吧
    eclipse_xu:@程序亦非猿 shanghai - 999 :kissing_heart:
  • 84d71761f1ea: 干(sang)得(xin)漂(bing)亮(kuang) :scream_cat: :gun:
    84d71761f1ea:@licheedev 才发现那个emoji是个cat。。。
  • 脉脉不得语:不仅逼死了处女座还对单身狗造成了10000点伤害😂
    atomic_volatile:作为处女座的我,表示越是提示别在意就会越在意.....已受伤害20000点
    eclipse_xu:@脉脉不得语 说了不要在意背景。。你们 哎
  • ailurus:桌面背景好评。

本文标题:Badge分析&如何逼死处女座

本文链接:https://www.haomeiwen.com/subject/acdehttx.html