Hey everyone,

The requirement was to make a custom notification since the android's 
default notification only allows for an image. So I went through on how to 
attach a custom UI for notification when expanded, the ready answer was to 
create a custom view and pass to the notification manager and allowed from 
API level 16.
So I did one and here the my layout xml code - filename: 
notification_custom_view_new:

<RelativeLayout 
xmlns:android="http://schemas.android.com/apk/res/android"android:layout_width="match_parent"android:layout_height="match_parent"android:background="@color/GhostWhite";>
<RelativeLayout
    android:id="@+id/header"
    android:layout_width="match_parent"
    android:layout_height="65dp">

    <ImageView
        android:id="@+id/big_icon"
        android:layout_width="40dp"
        android:layout_height="40dp"
        android:layout_centerVertical="true"
        android:layout_marginLeft="12dp"
        android:scaleType="fitCenter" />

    <LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_alignBottom="@+id/big_icon"
        android:layout_alignTop="@+id/big_icon"
        android:layout_toRightOf="@+id/big_icon"
        android:gravity="center_vertical"
        android:orientation="horizontal"
        android:paddingLeft="16dp"
        android:paddingRight="16dp"
        android:weightSum="2">

        <LinearLayout
            android:layout_width="0dp"
            android:layout_height="wrap_content"
            android:layout_weight="1.6"
            android:orientation="vertical">

            <TextView
                android:id="@+id/title"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:ellipsize="end"
                android:maxLines="1"
                android:text="Title"
                android:textColor="@color/colorBlackDimText"
                android:textSize="16sp"
                android:textStyle="bold" />

            <TextView
                android:id="@+id/message"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:ellipsize="end"
                android:maxLines="2"
                android:paddingTop="2dp"
                android:text="message"
                android:textColor="@color/colorBlackDimText"
                android:textSize="14sp" />

        </LinearLayout>

        <LinearLayout
            android:layout_width="0dp"
            android:layout_height="match_parent"
            android:layout_weight="0.4"
            android:gravity="center">

            <TextView
                android:id="@+id/time"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:ellipsize="end"
                android:maxLines="2"
                android:padding="8dp"
                android:text="24:59"
                android:textColor="@color/colorBlackDimText"
                android:textSize="12sp" />

        </LinearLayout>

    </LinearLayout>
</RelativeLayout>
<View
    android:id="@+id/shadow"
    android:layout_width="match_parent"
    android:layout_height="5dp"
    android:layout_below="@+id/header"
    android:background="@drawable/shadow" />
<ImageView
    android:id="@+id/big_picture"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:layout_below="@+id/header"
    android:src="@drawable/vector_icon_collections"
    android:minHeight="240dp"
    android:scaleType="fitCenter" /></RelativeLayout>


The way I referenced it in code:

private RemoteViews assignRemote(Bitmap bitmap, String title, String message
){
  RemoteViews expandedView = new RemoteViews(Application.getInstance().
getPackageName(), R.layout.notification_custom_view_new);
  expandedView.setTextViewText(R.id.title, title);
  expandedView.setTextViewText(R.id.message, message); expandedView.
setImageViewBitmap(R.id.big_picture, bitmap);
  expandedView.setImageViewResource(R.id.big_icon, R.mipmap.ic_launcher);
  expandedView.setTextViewText(R.id.time, getOnlyHrsMin());
  return expandedView;
}


assigning customview to notification manager:

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
        notification.bigContentView = assignRemote(bitmap, title, message);
    }

But this gave me error saying bad notification, I have identified over 15+ 
same question here on stackoverflow without a right answer.. Some suggest 
it to be a resource missing and hence the error. I am sure from my end none 
of the values are null nor resources missing errors are not there in my 
remote view that is passed.

Any help will be appreciated and also I have tried for around a couple of 
days to track the error but nothing good seems to happen. Please help me!

Screenshot attached for layout UI.. also find the NotificatioUtils and 
layout xml files attached for reference.

Thanks
DJphy



-- 
You received this message because you are subscribed to the Google Groups 
"Android Developers" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to android-developers+unsubscr...@googlegroups.com.
To post to this group, send email to android-developers@googlegroups.com.
Visit this group at https://groups.google.com/group/android-developers.
To view this discussion on the web visit 
https://groups.google.com/d/msgid/android-developers/1cc8ccad-f636-4558-9be8-5a83d5598012%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Attachment: notification_custom_view_new.xml
Description: XML document

package com.goldadorn.main.dj.support.gcm;

import android.app.ActivityManager;
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.ComponentName;
import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.media.Ringtone;
import android.media.RingtoneManager;
import android.net.Uri;
import android.os.Build;
import android.support.v7.app.NotificationCompat;
import android.text.Html;
import android.text.TextUtils;
import android.util.Log;
import android.util.Patterns;
import android.widget.RemoteViews;

import com.goldadorn.main.R;
import com.goldadorn.main.activities.Application;
import com.goldadorn.main.dj.utils.Constants;
import com.goldadorn.main.dj.utils.DateTimeUtils;
import com.goldadorn.main.dj.utils.IntentKeys;

import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.URL;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

/**
 * Created by COMP on 2/25/2016.
 */
public class NotificationUtils {

    private static String TAG = NotificationUtils.class.getSimpleName();

    private static Context mContext;

    public NotificationUtils() {
    }

    public NotificationUtils(Context mContext) {
        this.mContext = mContext;
    }

    public void showNotificationMessage(String title, String message, String timeStamp, Intent intent) {
        showNotificationMessage(title, message, timeStamp, intent, null);
    }

    public void showNotificationMessage(final String title, final String message, final String timeStamp, Intent intent, String imageUrl) {
        // Check for empty push message
        if (TextUtils.isEmpty(message))
            return;


        // notification icon
        final int icon = R.mipmap.ic_launcher;

        intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
        intent.putExtra(IntentKeys.PUSH_NOTIFICATION_CALL, Constants.GCM_CALL);
        final PendingIntent resultPendingIntent =
                PendingIntent.getActivity(
                        mContext,
                        0,
                        intent,
                        PendingIntent.FLAG_CANCEL_CURRENT
                );

        final NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(
                mContext);

        final Uri alarmSound = Uri.parse(ContentResolver.SCHEME_ANDROID_RESOURCE
                + "://" + mContext.getPackageName() + "/raw/notification");

        if (!TextUtils.isEmpty(imageUrl)) {

            if (imageUrl != null && imageUrl.length() > 4 && Patterns.WEB_URL.matcher(imageUrl).matches()) {

                Bitmap bitmap = getBitmapFromURL(imageUrl);

                if (bitmap != null) {
                    showBigNotification(bitmap, mBuilder, icon, title, message, timeStamp, resultPendingIntent, alarmSound);
                } else {
                    showSmallNotification(mBuilder, icon, title, message, timeStamp, resultPendingIntent, alarmSound);
                }
            }
        } else {
            showSmallNotification(mBuilder, icon, title, message, timeStamp, resultPendingIntent, alarmSound);
            playNotificationSound();
        }
    }


    private void showSmallNotification(NotificationCompat.Builder mBuilder, int icon, String title,
                                       String message, String timeStamp, PendingIntent resultPendingIntent, Uri alarmSound) {

        NotificationCompat.InboxStyle inboxStyle = new NotificationCompat.InboxStyle();

        if (Config.appendNotificationMessages) {
            // store the notification in shared pref first
            Application.getInstance().getPrefManager().clearNotificationMsgs();
            Application.getInstance().getPrefManager().addNotification(message);

            // get the notifications from shared preferences
            String oldNotification = Application.getInstance().getPrefManager().getNotifications();

            List<String> messages = Arrays.asList(oldNotification.split("\\|"));

            for (int i = messages.size() - 1; i >= 0; i--) {
                Log.d("djgcm","messgaes: "+messages.get(i));
                inboxStyle.addLine(messages.get(i));
            }
        } else {
            inboxStyle.addLine(message);
        }

        Notification notification;
        notification = mBuilder.setSmallIcon(iconToUse()).setTicker(title).setWhen(0)
                .setAutoCancel(true)
                .setContentTitle(title)
                .setContentIntent(resultPendingIntent)
                .setSound(alarmSound)
                .setLights(Color.WHITE, 1500, 2000)
                .setStyle(inboxStyle)
                .setWhen(getTimeMilliSec(timeStamp))
                .setSmallIcon(iconToUse())
                .setLargeIcon(BitmapFactory.decodeResource(mContext.getResources(), icon))
                .setContentText(message)
                .build();

        NotificationManager notificationManager = (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
        notificationManager.notify(Config.NOTIFICATION_ID, notification);
    }

    private void showBigNotification(Bitmap bitmap, NotificationCompat.Builder mBuilder, int icon,
                                     String title, String message, String timeStamp, PendingIntent resultPendingIntent, Uri alarmSound) {
        NotificationCompat.BigPictureStyle bigPictureStyle = new NotificationCompat.BigPictureStyle();
        bigPictureStyle.setBigContentTitle(title);
        bigPictureStyle.setSummaryText(Html.fromHtml(message).toString());
        bigPictureStyle.bigPicture(bitmap);
        Notification notification;
        notification = mBuilder.setSmallIcon(icon).setTicker(title).setWhen(0)
                .setAutoCancel(true)
                .setContentTitle(title)
                .setContentIntent(resultPendingIntent)
                .setSound(alarmSound)
                .setLights(Color.WHITE, 1500, 2000)
                //.setStyle(bigPictureStyle)
                .setWhen(getTimeMilliSec(timeStamp))
                .setSmallIcon(iconToUse())
                .setLargeIcon(BitmapFactory.decodeResource(mContext.getResources(), icon))
                .setContentText(message)
                .build();

        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) {
            notification.bigContentView = assignRemote(bitmap, title, message);
        }

        NotificationManager notificationManager = (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
        notificationManager.notify(Config.NOTIFICATION_ID_BIG_IMAGE, notification);
    }

    private RemoteViews assignRemote(Bitmap bitmap, String title, String message){
        RemoteViews expandedView = new RemoteViews(Application.getInstance().getPackageName(),
                R.layout.notification_custom_view_new);
        Log.d("djgcm","title, msg, big_pic, time: "+title+" "+message+" "+bitmap+" "+getOnlyHrsMin());
        expandedView.setTextViewText(R.id.title, title);
        expandedView.setTextViewText(R.id.message, message);
        expandedView.setImageViewBitmap(R.id.big_picture, bitmap);
        expandedView.setImageViewResource(R.id.big_icon, R.mipmap.ic_launcher);
        expandedView.setTextViewText(R.id.time, getOnlyHrsMin());
        return expandedView;
    }

    private int iconToUse(){
        if (Constants.CURRENT_API_LEVEL >= Build.VERSION_CODES.LOLLIPOP){
            return R.mipmap.ic_launcher_silhoute;
        }
        return R.mipmap.ic_launcher;
    }

    /*private int getNotificationIcon() {
        boolean useWhiteIcon = (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.LOLLIPOP);
        return useWhiteIcon ? R.drawable.icon_silhouette : R.drawable.ic_launcher;
    }*/

    /**
     * Downloading push notification image before displaying it in
     * the notification tray
     */
    public Bitmap getBitmapFromURL(String strURL) {
        try {
            URL url = new URL(strURL);
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
            connection.setDoInput(true);
            connection.connect();
            InputStream input = connection.getInputStream();
            Bitmap myBitmap = BitmapFactory.decodeStream(input);
            return myBitmap;
        } catch (IOException e) {
            e.printStackTrace();
            return null;
        }
    }

    // Playing notification sound
    public void playNotificationSound() {
        try {
            Uri alarmSound = Uri.parse(ContentResolver.SCHEME_ANDROID_RESOURCE
                    + "://" + Application.getInstance().getApplicationContext().getPackageName() + "/raw/notification");
            Ringtone r = RingtoneManager.getRingtone(Application.getInstance().getApplicationContext(), alarmSound);
            r.play();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    /**
     * Method checks if the app is in background or not
     */
    public static boolean isAppIsInBackground(Context context) {
        boolean isInBackground = true;
        ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE);
        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.KITKAT_WATCH) {
            List<ActivityManager.RunningAppProcessInfo> runningProcesses = am.getRunningAppProcesses();
            for (ActivityManager.RunningAppProcessInfo processInfo : runningProcesses) {
                if (processInfo.importance == ActivityManager.RunningAppProcessInfo.IMPORTANCE_FOREGROUND) {
                    for (String activeProcess : processInfo.pkgList) {
                        if (activeProcess.equals(context.getPackageName())) {
                            isInBackground = false;
                        }
                    }
                }
            }
        } else {
            List<ActivityManager.RunningTaskInfo> taskInfo = am.getRunningTasks(1);
            ComponentName componentInfo = taskInfo.get(0).topActivity;
            if (componentInfo.getPackageName().equals(context.getPackageName())) {
                isInBackground = false;
            }
        }

        return isInBackground;
    }

    // Clears notification tray messages
    public static void clearNotifications() {
        NotificationManager notificationManager = (NotificationManager) Application.getInstance().getSystemService(Context.NOTIFICATION_SERVICE);
        notificationManager.cancelAll();
    }

    public static long getTimeMilliSec(String timeStamp) {
        //SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        try {
            return System.currentTimeMillis();
        } catch (Exception e) {
            e.printStackTrace();
        }
        return 0;
    }


    public static String getOnlyHrsMin(){
        Calendar calendar = Calendar.getInstance();
        calendar.setTimeInMillis(System.currentTimeMillis());
        int hour = calendar.get(Calendar.HOUR_OF_DAY);
        int min = calendar.get(Calendar.MINUTE);
        return hour+":"+min;
    }
}

Reply via email to