Issue
I have a Notification, that supports a private and a public version. The private version is shown as bigTextStyle. The icon for both versions is generated as LayerDrawable which is then converted to a bitmap. This works nice on all devices. Except on one Huawei Ascent Mate 7 that was forged in hell. (Android 4.4.2, EMUI 3.0)
In the not expanded Version it looks as it should. Round circle, fitting icon.
But in the expanded version, it looks as if it was cut out of a scaled version of the icon.
For the icon I do following:
Drawable background = ContextCompat.getDrawable(this, R.drawable.shape_notification_circle);
if (background != null) {
PorterDuffColorFilter filter = new PorterDuffColorFilter(ThemeManager.getInstance().getTheme()
.getColorMainDark(), PorterDuff.Mode.SRC_ATOP);
background.setColorFilter(filter);
}
Drawable[] layers = {background, ContextCompat.getDrawable(this, icon)};
//icon is an int, containing the resource id
LayerDrawable layerDrawable = new LayerDrawable(layers);
int padding = dpToPx(24);
layerDrawable.setLayerInset(1, padding, padding, padding, padding);
Bitmap iconBitmap = drawableToBitmap(layerDrawable);
the method drawableToBitmap:
public static Bitmap drawableToBitmap(Drawable drawable) {
Bitmap bitmap;
if (drawable instanceof BitmapDrawable) {
BitmapDrawable bitmapDrawable = (BitmapDrawable) drawable;
if (bitmapDrawable.getBitmap() != null) {
return bitmapDrawable.getBitmap();
}
}
if (drawable.getIntrinsicWidth() <= 0 || drawable.getIntrinsicHeight() <= 0) {
bitmap = Bitmap.createBitmap(1, 1, Bitmap.Config.ARGB_8888); // Single color bitmap will be created of
// 1x1 pixel
} else {
bitmap = Bitmap.createBitmap(drawable.getIntrinsicWidth(), drawable.getIntrinsicHeight(), Bitmap.Config
.ARGB_8888);
}
Canvas canvas = new Canvas(bitmap);
drawable.setBounds(0, 0, canvas.getWidth(), canvas.getHeight());
drawable.draw(canvas);
return bitmap;
}
The Layout of shape_notification_circle
<?xml version="1.0" encoding="utf-8"?>
<shape xmlns:android="http://schemas.android.com/apk/res/android"
android:shape="oval">
<solid android:color="#666666"/>
<size
android:width="48dp"
android:height="48dp"/>
</shape>
The icon drawable:
<?xml version="1.0" encoding="UTF-8"?>
<vector android:height="48dp"
android:viewportHeight="1000.0"
android:viewportWidth="1000.0"
android:width="48dp"
xmlns:android="http://schemas.android.com/apk/res/android">
<path
android:fillColor="#FFFFFF"
android:pathData="M500,609.8l-75.20001,-72.79999l-299.69998,252.79999l749.80005,0l-299.7,-252.79999z"/>
<path
android:fillColor="#FFFFFF"
android:pathData="M122.6,210.2l377.4,365l377.40002,-365z"/>
<path
android:fillColor="#FFFFFF"
android:pathData="M406.3,519.7l-300.9,-292.2l0,546.3z"/>
<path
android:fillColor="#FFFFFF"
android:pathData="M894.6,773.8l0,-546.3l-300.89996,292.2z"/>
</vector>
And finally, the creation of the notification. (notificationBuilder and notificationBuilderPublic used to be different, but are now same, except for the different bigTextStyle)
// @formatter:off
NotificationCompat.Builder notificationBuilderPublic = new NotificationCompat.Builder(this)
.setLargeIcon(iconBitmap)
.setSmallIcon(R.drawable.ic_notification_launcher)
.setColor(ThemeManager.getInstance().getTheme().getColorAccent())
.setDefaults(Notification.DEFAULT_ALL)
.setContentTitle(getString(R.string.app_name))
.setContentText(title)
.setAutoCancel(true)
.setContentIntent(pendingIntent)
.setCategory(category)
.setPriority(priority)
.setVisibility(NotificationCompat.VISIBILITY_PUBLIC)
;
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
.setLargeIcon(iconBitmap)
.setSmallIcon(R.drawable.ic_notification_launcher)
.setColor(ThemeManager.getInstance().getTheme().getColorAccent())
.setDefaults(Notification.DEFAULT_ALL)
.setContentTitle(getString(R.string.app_name))
.setContentText(title)
.setAutoCancel(true)
.setContentIntent(pendingIntent)
.setCategory(category)
.setPriority(priority)
.setVisibility(visibility)
;
// @formatter:on
notificationBuilder.setStyle(new NotificationCompat.BigTextStyle().bigText(text)
.setBigContentTitle(getString(R.string.app_name)).setSummaryText(extraSummary));
notificationBuilder.setPublicVersion(notificationBuilderPublic.build());
notificationManager.notify(pushId + "|" + ownermoduleid + "|" + fid, type.getId(), notificationBuilder.build());
What am I doing wrong?
EDIT: Added layout and icon XML
Solution
Finally I found... well, I will not call it a solution... a workaround. It seems, that setting insets on the layers of the LayerDrawable will cause the image to grow in size. Some devices seem to crop images instead of fitting them, if they are too large.
That leads me to resizing the iconBitmap before setting it as LargeIcon.
Bitmap iconBitmap = scaleDown(drawableToBitmap(layerDrawable), dpToPx(48), true);
And the scaling function
public Bitmap scaleDown(Bitmap source, int size, boolean filter) {
return Bitmap.createScaledBitmap(source, size, size, filter);
}
This does still not work completely flawless. When expanding the notification, the image is a tiny bit smaller, but that is ok for me. Still better than cropped.
I still don't know, why this happens only when expanding the view. Maybe the guys at Huawei implemented the BigTextStyle different from the normal style. Or maybe it is just some black magic...
If someone comes up with a better solution, I will accept that one.
Answered By - AlbAtNf
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.