232

我的应用程序生成通知,但我为该通知设置的图标没有显示。相反,我得到一个白色方块。

我尝试调整图标的 png 大小(尺寸 720x720、66x66、44x44、22x22)。奇怪的是,当使用较小的尺寸时,白色方块会更小。

我已经用谷歌搜索了这个问题,以及生成通知的正确方法,从我读过的内容来看,我的代码应该是正确的。可悲的是,事情并非如此。

我的手机是装有 Android 5.1.1 的 Nexus 5。这个问题也出现在模拟器上,一个带有 Android 5.0.1 的三星 Galaxy s4 和一个带有 Android 5.0.1 的摩托罗拉 Moto G(我都借了,现在没有)

通知代码如下,以及两个屏幕截图。如果您需要更多信息,请随时询问。

谢谢你们。

@SuppressLint("NewApi") private void sendNotification(String msg, String title, String link, Bundle bundle) {
    NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
    Intent resultIntent = new Intent(getApplicationContext(), MainActivity.class);
    resultIntent.putExtras(bundle);
    PendingIntent contentIntent = PendingIntent.getActivity(this, 0,
            resultIntent, Intent.FLAG_ACTIVITY_NEW_TASK);
    Notification notification;
    Uri sound = Uri.parse("android.resource://" + getPackageName() + "/" + R.raw.notificationsound);
    notification = new Notification.Builder(this)
                .setSmallIcon(R.drawable.lg_logo)
                .setContentTitle(title)
                .setStyle(new Notification.BigTextStyle().bigText(msg))
                .setAutoCancel(true)
                .setContentText(msg)
                .setContentIntent(contentIntent)
                .setSound(sound)
                .build();
    notificationManager.notify(0, notification);
}

不打开通知 打开的通知

4

21 回答 21

208

原因:对于 5.0 Lollipop,“通知图标必须全白”。

如果我们通过将 target SDK 设置为 20 来解决白色图标问题,我们的应用将不会以 Android Lollipop 为目标,这意味着我们无法使用 Lollipop 特定的功能。

目标 SDK 21 的解决方案

如果要支持 Lollipop Material Icons,请为 Lollipop 及以上版本制作透明图标。请参考以下内容: https ://design.google.com/icons/

请查看http://developer.android.com/design/style/iconography.html,我们将看到白色样式是通知在 Android Lollipop 中的显示方式。

在 Lollipop 中,Google 还建议我们使用一种将显示在白色通知图标后面的颜色。参考链接:https ://developer.android.com/about/versions/android-5.0-changes.html

无论我们想在哪里添加颜色 https://developer.android.com/reference/android/support/v4/app/NotificationCompat.Builder.html#setColor(int)

低于和高于 Lollipop OS 版本的 Notification Builder 的实现将是:

Notification notification = new NotificationCompat.Builder(this);
if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
    notification.setSmallIcon(R.drawable.icon_transperent);
    notification.setColor(getResources().getColor(R.color.notification_color));
} else { 
    notification.setSmallIcon(R.drawable.icon);
} 

注意: setColor 仅在 Lollipop 中可用,它只影响图标的背景。

彻底解决你的问题!!

于 2015-06-12T04:46:43.653 回答
86

如果您使用的是 Google Cloud Messaging,则仅通过更改图标无法解决此问题。例如,这将不起作用:

 Notification notification  = new Notification.Builder(this)
                .setContentTitle(title)
                .setContentText(text)
                .setSmallIcon(R.drawable.ic_notification)
                .setContentIntent(pIntent)
                .setDefaults(Notification.DEFAULT_SOUND|Notification.DEFAULT_LIGHTS|Notification.DEFAULT_VIBRATE)
                .setAutoCancel(true)
                .build();

即使ic_notification 是透明的和白色的。它还必须在 Manifest 元数据中定义,如下所示:

  <meta-data android:name="com.google.firebase.messaging.default_notification_icon"

            android:resource="@drawable/ic_notification" />

元数据位于application标签下,以供参考。

于 2017-12-30T19:34:59.597 回答
42

我真的建议遵循Google 的设计指南

上面写着“通知图标必须全白”。

于 2015-06-12T04:55:47.760 回答
37

在 Android Manifest 中声明此代码:

<meta-data android:name="com.google.firebase.messaging.default_notification_icon" 

android:resource="@drawable/ic_stat_name" />

我希望这对你有用。

于 2017-04-24T13:16:15.717 回答
34

(Android Studio 3.5)如果您使用的是最新版本的 Android Studio,您可以生成通知图像。右键单击您的 res 文件夹 > New > Image Asset。然后,您将看到配置图像资产,如下图所示。将图标类型更改为通知图标。您的图像必须是白色和透明的。此配置图像资产将强制执行该规则。 重要提示:如果您希望图标用于云/推送通知,则必须在应用程序标签下添加元数据才能使用新创建的通知图标。配置图像资产

  <application>
      ...
      <meta-data android:name="com.google.firebase.messaging.default_notification_icon"
          android:resource="@drawable/ic_notification" />
于 2019-08-29T17:41:21.977 回答
16
 <meta-data android:name="com.google.firebase.messaging.default_notification_icon"

        android:resource="@drawable/ic_notification" />

在应用程序块的 manifest.xml 文件中添加这一行。

于 2018-07-10T12:56:04.013 回答
10

我们可以这样做:

创建通知生成器的新对象并setSmallIcon()使用通知生成器对象调用,如下面的代码所示。

创建一个方法,我们将在其中检查我们正在安装我们的应用程序的操作系统版本。如果它低于 Lolipop 即 API 21,那么它将采用带有背景颜色的普通应用程序图标,否则它将采用没有任何背景的透明应用程序图标。因此使用 os version >= 21 的设备将使用setColor()Notification builder 类的方法设置图标的背景颜色。

示例代码:

NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this);

notificationBuilder.setSmallIcon(getNotificationIcon(notificationBuilder));

private int getNotificationIcon(NotificationCompat.Builder notificationBuilder) {

   if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
             int color = 0x008000;
             notificationBuilder.setColor(color);
             return R.drawable.app_icon_lolipop_above;

    } 
    return R.drawable.app_icon_lolipop_below;
}
于 2015-11-09T12:01:09.620 回答
10

试试这个

我遇到了同样的问题,我尝试了很多答案,但没有得到任何解决方案,最后我找到了解决问题的方法。

- 制作具有透明背景的通知图标。应用程序的宽度和高度必须如下所示,并将所有这些粘贴到您的项目->应用程序->src->main->res

  • MDPI 24*24

  • HDPI 36*36

  • XHDPI 48*48

  • XXHDPI 72*72


在上面粘贴下面这一行之后你的 onMessageReceived 方法


Intent intent = new Intent(this, News.class);
            intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
            PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent,
                    PendingIntent.FLAG_ONE_SHOT);
            Uri defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
            NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this);
            if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP)
            {
                notificationBuilder.setSmallIcon(R.drawable.notify)
                                      //            .setContentTitle(title)
                            //                        .setContentText(message)
                        .setAutoCancel(true)
                        .setSound(defaultSoundUri)
                        .setContentIntent(pendingIntent);
            } else
                {
                    notificationBuilder.setSmallIcon(R.drawable.notify)
                       //                                .setContentTitle(title)
                        //                        .setContentText(message)
                            .setAutoCancel(true)
                            .setSound(defaultSoundUri)
                            .setContentIntent(pendingIntent);
            }
            NotificationManager notificationManager =
                    (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
            notificationManager.notify(0, notificationBuilder.build());

不要忘记在清单文件中添加此代码

<meta-data 
android:name="com.google.firebase.messaging.default_notification_icon" 
android:resource="@drawable/app_icon" />
于 2017-08-01T07:16:15.397 回答
9

我已经通过将以下代码添加到清单来解决问题,

    <meta-data
        android:name="com.google.firebase.messaging.default_notification_icon"
        android:resource="@drawable/ic_stat_name" />

    <meta-data
        android:name="com.google.firebase.messaging.default_notification_color"
        android:resource="@color/black" />

ic_stat_nameAndroid Studio 上创建的位置右键单击 res >> New >>Image Assets >> IconType(Notification)

我必须在服务器 php 端使用通知有效负载再做一步

$message = [
    "message" => [
        "notification" => [
            "body"  => $title , 
            "title" => $message
        ],

        "token" => $token,

    "android" => [
           "notification" => [
            "sound"  => "default",
            "icon"  => "ic_stat_name"
            ]
        ],

       "data" => [
            "title" => $title,
            "message" => $message
         ]


    ]
];

注意部分

    "android" => [
           "notification" => [
            "sound"  => "default",
            "icon"  => "ic_stat_name"
            ]
        ]

其中图标名称"icon" => "ic_stat_name"应与清单上的设置相同。

于 2019-04-02T08:06:53.120 回答
7

如果您想提供棒棒糖支持通知图标,请制作两种类型的通知图标:

  1. 正常通知图标:适用于以下棒棒糖版本。
  2. 带有透明背景的通知图标:棒棒糖及以上版本。

现在根据操作系统版本在运行时为通知生成器设置适当的图标:

NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(this);
if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
    mBuilder.setSmallIcon(R.drawable.ic_push_notification_transperent);
} else {
    mBuilder.setSmallIcon(R.drawable.ic_push_notification);
}
于 2015-06-12T05:23:18.940 回答
7

最后我得到了这个问题的解决方案。

仅当应用程序根本未运行时才会出现此问题。(既不在后台也不在前台)。当应用程序在前台或后台运行时,通知图标会正确显示。(不是白色方块)

所以我们要设置的是后端API中通知图标的配置与前端相同。

在前端,我们使用了React Native,对于推送通知,我们使用了react-native-fcm npm 包

FCM.on("notification", notif => {
   FCM.presentLocalNotification({
       body: notif.fcm.body,
       title: notif.fcm.title,
       big_text: notif.fcm.body,
       priority: "high",
       large_icon: "notification_icon", // notification icon
       icon: "notification_icon",
       show_in_foreground: true,
       color: '#8bc34b',
       vibrate: 300,
       lights: true,
       status: notif.status
   });
});

我们使用使用Node.js的fcm-push npm 包作为推送通知的后端,并将有效负载结构设置如下。

{
  to: '/topics/user', // required
  data: {
    id:212,
    message: 'test message',
    title: 'test title'
  },
  notification: {
    title: 'test title',
    body: 'test message',
    icon : 'notification_icon', // same name as mentioned in the front end
    color : '#8bc34b',
    click_action : "BROADCAST"
  }
}

它基本上搜索存储在我们的Android系统中本地的notification_icon图像。

于 2017-03-30T16:03:47.700 回答
5

通知是灰度的,如下所述。尽管其他人已经写过,但它们并不是非黑即白的。您可能已经看到具有多种阴影的图标,例如网络强度条。

在 API 21 (Lollipop 5.0) 之前,彩色图标有效。您可以强制您的应用程序以 API 20 为目标,但这会限制您的应用程序可用的功能,因此不建议这样做。您可以测试正在运行的 API 级别并适当地设置彩色图标或灰度图标,但这可能不值得。在大多数情况下,最好使用灰度图标。

图像有四个通道,RGBA(红/绿/蓝/alpha)。对于通知图标,Android 会忽略 R、G 和 B 通道。唯一重要的通道是 Alpha,也称为不透明度。使用可让您控制绘图颜色的 Alpha 值的编辑器设计您的图标。

Alpha 值如何生成灰度图像:

  • Alpha = 0(透明)- 这些像素是透明的,显示背景颜色。
  • Alpha = 255(不透明)——这些像素是白色的。
  • Alpha = 1 ... 254 — 这些像素正是您所期望的,提供透明和白色之间的阴影。

改变它setColor

  • 打电话NotificationCompat.Builder.setColor(int argb)。从文档中Notification.color

    标准样式模板在呈现此通知时应用的强调色(一个 ARGB 整数,如 Color 中的常量)。当前的模板设计通过在此颜色的字段顶部覆盖图标图像(以白色印刷)来构建彩色标题图像。Alpha 分量被忽略。

    我对 setColor 的测试表明 Alpha 组件未被忽略。较高的 Alpha 值会将像素变为白色。较低的 Alpha 值将像素转换为通知区域中的背景颜色(我的设备上为黑色),或下拉通知中的指定颜色。

于 2017-01-25T19:10:52.877 回答
4

解决此问题的要求:

  1. 图像格式:32 位 PNG(带 alpha)

  2. 图像应该是透明的

  3. 透明色指数:白色 (FFFFFF)

来源: http: //gr1350.blogspot.com/2017/01/problem-with-setsmallicon.html

于 2017-01-27T09:53:41.760 回答
4

我找到了一个链接,我们可以在其中生成我们自己的白色图标,

尝试此链接以生成启动器图标的白色图标。

打开此链接并上传您的 ic_launcher 或通知图标

于 2018-06-01T10:47:30.180 回答
3

对于自定义的本地通知,在 AndroidManifest.xml 添加以下元数据然后它将起作用。

 <application
    android:name="xxxxxx"
        android:label="xxxxxx"
        android:icon="@mipmap/ic_launcher"
        
        >

       <meta-data
                android:name="your_apps_bundle_id.default_notification_icon"
                android:resource="@drawable/ic_notif" />

......
于 2021-01-13T12:45:10.640 回答
2

我在 android 8.0 上有类似的问题。尝试使用白色图标资源。当我尝试使用彩色图像作为图标时,我有白色方块,当我将它替换为白色图标时,它就开始工作了。

于 2018-05-03T07:14:13.703 回答
1

您可以为不同的版本使用不同的图标。只需在您的图标上设置逻辑,如下所示:

int icon = Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP ? R.drawable.colored_: R.drawable.white_tint_icon_for_lolipop_or_upper;
于 2016-10-21T15:22:57.557 回答
1

对于 SDK >= 23,请添加 setLargeIcon

notification = new Notification.Builder(this)
            .setSmallIcon(R.drawable.ic_launcher)
            .setLargeIcon(context.getResources(), R.drawable.lg_logo))
            .setContentTitle(title)
            .setStyle(new Notification.BigTextStyle().bigText(msg))
            .setAutoCancel(true)
            .setContentText(msg)
            .setContentIntent(contentIntent)
            .setSound(sound)
            .build();
于 2017-01-16T06:43:01.410 回答
1

当您想要保留彩色图标时 - 解决方法
将颜色略有不同的像素添加到图标中。
在我的情况下,一个带有阴影和光线的黑色图标。当添加深蓝色像素时,它可以工作。

于 2017-12-05T15:45:28.340 回答
1

要减少 SDK 特定版本,您可以简单地执行以下操作:(将 '#' 替换为 '0x')

Notification notification = new NotificationCompat.Builder(this);
notification.setSmallIcon(R.drawable.icon_transperent);
notification.setColor(0x169AB9); //for color: #169AB9
于 2019-09-27T06:51:18.767 回答
0

我只是将我的png转换为透明的png,然后图标与图片的形状相同,但颜色不同

于 2020-11-20T05:48:50.510 回答