I've been browsing the net for an answer but i can't find it myself despite reading the developer guides on the official android documentation site and code snippets from all over the Internet.
I've been practicing creating notifications on a new clean project, and despite creating a notification channel and the notification itself I still can't get it to run and get a message saying: "Failed to post notification on null channel". But im creating the channel, and assigning it to my notification just like it says everywhere. Im completely out of ideas and honestly i've been browsing stack for at least few hours now and every answer looks the same but it really didn't help me at all, so maybe if someone who's better than a begginer looks at my code can tell me what's wrong with my code? It's annoying because notifications are an important part of a project im working on, and it stopped me in my tracks.
public class MainActivity extends AppCompatActivity {
NotificationCompat.Builder notification;
private static final int NOTIFICATION_ID = 1;
private static final String NOTIFICATION_CHANNEL_ID = "my_notification_channel";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
notification = new NotificationCompat.Builder(this);
notification.setAutoCancel(true);
findViewById(R.id.buckysButton).setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
createNotification(view);
}
});
}
public void createNotification(View view){
NotificationManager nm = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
NotificationChannel notificationChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, "My Notifications", NotificationManager.IMPORTANCE_DEFAULT);
notificationChannel.setDescription("Channel description");
notificationChannel.enableLights(true);
notificationChannel.setLightColor(Color.RED);
notificationChannel.setVibrationPattern(new long[]{0, 1000, 500, 1000});
notificationChannel.enableVibration(true);
nm.createNotificationChannel(notificationChannel);
}
notification.setSmallIcon(R.drawable.ic_priority_high_black_24px);
notification.setTicker("Ticker");
notification.setWhen(System.currentTimeMillis());
notification.setContentTitle("Title");
notification.setContentText("Body Body Body Body Body Body Body Body Body ");
notification.setChannel(NOTIFICATION_CHANNEL_ID);
notification.build();
Intent intent = new Intent(this, MainActivity.class);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
notification.setContentIntent(pendingIntent);
nm.notify(NOTIFICATION_ID, notification.build());
}}
By the way I'm developing for Android minimum level of 5.1 and I have been wondering if it's really necessary to put channels in my application, but I did it anyways since when im trying to do it without them I'm still getting exactly the same error.
EDIT: Im still struggling with this issue. Do I have to do something in the gradle files to be able to pass two arguments into the NotificationCompat.Builder constructor? It wont let me do it no matter what i do, i think thats the main problem here.
NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID)
Doesnt do it for me, it still doesnt want to take the channel_id as an argument.
new NotificationCompat.Builder(this);
is deprecated, try using
NotificationCompat.Builder mBuilder = new NotificationCompat.Builder(this, NOTIFICATION_CHANNEL_ID)
Here's a sample code, create a NotificationHelper class as follows,
import android.app.NotificationChannel;
import android.app.NotificationManager;
import android.content.Context;
import android.content.ContextWrapper;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Color;
import android.provider.Settings;
import android.support.v4.app.NotificationCompat;
import android.support.v4.content.ContextCompat;
public class NotificationHelper extends ContextWrapper {
private NotificationManager mNotificationManager;
private final String MY_CHANNEL = "my_channel";
private final long[] vibrationScheme = new long[]{200, 400};
/**
* Registers notification channels, which can be used later by individual notifications.
*
* #param context The application context
*/
public NotificationHelper(Context context) {
super(context);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O) {
// Create the channel object with the unique ID MY_CHANNEL
NotificationChannel myChannel =
new NotificationChannel(
MY_CHANNEL,
getResources().getString(R.string.notification_channel_title),
NotificationManager.IMPORTANCE_DEFAULT);
// Configure the channel's initial settings
myChannel.setLightColor(Color.GREEN);
myChannel.setVibrationPattern(vibrationScheme);
// Submit the notification channel object to the notification manager
getNotificationManager().createNotificationChannel(myChannel);
}
}
/**
* Build you notification with desired configurations
*
*/
public NotificationCompat.Builder getNotificationBuilder(String title, String body, Intent pendingIntent) {
Bitmap notificationLargeIconBitmap = BitmapFactory.decodeResource(
getApplicationContext().getResources(),
R.mipmap.ic_launcher);
return new NotificationCompat.Builder(getApplicationContext(), MY_CHANNEL)
.setSmallIcon(R.drawable.ic_notification_icon)
.setLargeIcon(notificationLargeIconBitmap)
.setContentTitle(title)
.setContentText(body)
.setSound(Settings.System.DEFAULT_NOTIFICATION_URI)
.setVibrate(vibrationScheme)
.setStyle(new NotificationCompat.BigTextStyle().bigText(body))
.setColor(ContextCompat.getColor(getApplicationContext(), R.color.colorPrimary))
.setContentIntent(pendingIntent)
.setAutoCancel(true);
}
public NotificationManager getNotificationManager() {
if (mNotificationManager == null) {
mNotificationManager =
(NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
}
return mNotificationManager;
}
}
and then use it as follows,
NotificationHelper notificationHelper = new NotificationHelper(context);
NotificationCompat.Builder builder = notificationHelper.getNotificationBuilder(title, message);
notificationHelper.getNotificationManager().notify(notificationID, builder.build());
Ok, maybe I'm bit late, but...
Try to shorten your channelId string.
Now it
private static final String NOTIFICATION_CHANNEL_ID = "my_notification_channel";
Try
private static final String NOTIFICATION_CHANNEL_ID = "my_channel";
For me it was a very strange bug. When channelId was too long it don't show notification on my device.
Edit:
It was not too long or too short, just some string got banned in system. Also it not showed in Android notification settings screen.
I've found out what was missing. I was using android studio 2.3.3 instead of the newest 3.0.1 so I couldn't import some of the new functions through Gradle.
After that i only had to change my dependencies classpath to 'com.android.tools.build:gradle:3.0.1' and the problem was gone.
Thanks for help.
Related
Google made a huge breaking change in Oreo - they stopped notifications from working in all apps. I'm now dealing with changing all my apps but I'm left with a couple problems . . .
The notification now gets posted and when the user touches the notification it properly triggers the app. However, (1) the notification does not disappear. To get rid of it the user must delete it. Also (2) the dots on my app icon stay at One after posting several notifications.
I'm using the following notification helper class I found posted by Bipin Pandey:
public class NotificationHelper {
private Context mContext;
private NotificationManager mNotificationManager;
private NotificationCompat.Builder mBuilder;
public static final String NOTIFICATION_CHANNEL_ID = "10001";
public NotificationHelper(Context context) {
mContext = context;
}
/**
* Create and push the notification
*/
public void createNotification(String title, String message)
{
/**Creates an explicit intent for an Activity in your app**/
Intent resultIntent = new Intent(mContext , MainActivity.class);
resultIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
PendingIntent resultPendingIntent = PendingIntent.getActivity(mContext,
0 /* Request code */, resultIntent,
PendingIntent.FLAG_UPDATE_CURRENT);
mBuilder = new NotificationCompat.Builder(mContext);
mBuilder.setSmallIcon(R.drawable.ticon);
mBuilder.setContentTitle(title)
.setContentText(message)
.setAutoCancel(false)
.setSound(Settings.System.DEFAULT_NOTIFICATION_URI)
.setContentIntent(resultPendingIntent);
mNotificationManager = (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.O)
{
int importance = NotificationManager.IMPORTANCE_HIGH;
NotificationChannel notificationChannel = new NotificationChannel(NOTIFICATION_CHANNEL_ID, "NOTIFICATION_CHANNEL_NAME", importance);
notificationChannel.enableLights(true);
notificationChannel.setLightColor(Color.RED);
notificationChannel.enableVibration(true);
notificationChannel.setVibrationPattern(new long[]{100, 200, 300, 400, 500, 400, 300, 200, 400});
assert mNotificationManager != null;
mBuilder.setChannelId(NOTIFICATION_CHANNEL_ID);
mNotificationManager.createNotificationChannel(notificationChannel);
}
assert mNotificationManager != null;
mNotificationManager.notify(0 /* Request Code */, mBuilder.build());
}
}
The following code executes this helper class
NotificationHelper myNotify = new NotificationHelper(context);
myNotify.createNotification("New Message",mesText);
You set setAutoCancel(false), so the notification is correctly not automatically being cancelled when you trigger it. Remove that line if you want tapping on the notification to remove the notification (and the dots associated with the notifications).
You have kept setAutoCancel property as false. So notification won't be dismissed when the user touches it. This is for situations when you want to handle removing the notification at your own end.
Remove that line from your NotificationBuilder and your logic should work as expected.
Description of the Method :
public Notification.Builder setAutoCancel (boolean autoCancel)
Make this notification automatically dismissed when the user touches it.
Read more about Notification Auto Cancel here :
https://developer.android.com/reference/android/app/Notification.Builder.html#setAutoCancel(boolean)
I have followed this tutorial and when I try to send a message from Firebase console, onMessageReceived were called and createNotification were performed, no notification prompt shows up.
It suppose to prompt this but it didn't
Below is my MyAndroidFirebaseMsgService code
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.graphics.BitmapFactory;
import android.media.RingtoneManager;
import android.net.Uri;
import android.support.v4.app.NotificationCompat;
import android.util.Log;
import com.google.firebase.messaging.FirebaseMessagingService;
import com.google.firebase.messaging.RemoteMessage;
import java.util.HashMap;
public class MyAndroidFirebaseMsgService extends FirebaseMessagingService
{
private static final String TAG = "MyAndroidFCMService";
#Override
public void onMessageReceived(RemoteMessage remoteMessage) {
//Log data to Log Cat
Log.d(TAG, "From: " + remoteMessage.getFrom());
Log.d(TAG, "Notification Message Body: " + remoteMessage.getNotification().getBody());
//create notification
createNotification(remoteMessage.getNotification().getBody());
}
private void createNotification( String messageBody)
{
Intent intent = new Intent( this , ResultActivity.class );
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
PendingIntent resultIntent = PendingIntent.getActivity( this , 0, intent, PendingIntent.FLAG_ONE_SHOT);
Uri notificationSoundURI = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
NotificationCompat.Builder mNotificationBuilder = new NotificationCompat.Builder( this)
.setSmallIcon(R.mipmap.ic_launcher)
.setContentTitle("Test Notification")
.setContentText(messageBody)
.setAutoCancel( false )
.setSound(notificationSoundURI)
.setContentIntent(resultIntent);
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
notificationManager.notify(0, mNotificationBuilder.build());
}
}
Finally found that the notification were actually only appeared on the android drop down menu instead of popping up due to my device is running Android 4. I test again with Android 5 device and the notification pop up just like the tutorial.
Maybe you were missing notification notify.
Please try bellow code. it's working properly
//This method is only generating push notification
//It is same as we did in earlier posts
private void sendNotification(RemoteMessage remoteMessage) {
Intent resultIntent = new Intent(this, MenuBarActivity.class);
resultIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
HashMap<String, String> dataMap = new HashMap<String, String>(remoteMessage.getData());
resultIntent.putExtra(Constant.KEY_MESSAGE_BODY, dataMap);
resultIntent.putExtra(Constant.KEY_IS_NOTIFICATION, true);
PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, resultIntent,
PendingIntent.FLAG_ONE_SHOT);
Uri defaultSoundUri = RingtoneManager.getDefaultUri(RingtoneManager.TYPE_NOTIFICATION);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
.setSmallIcon(R.mipmap.ic_launcher)
.setContentTitle(getString(R.string.app_name))
.setStyle(new NotificationCompat.BigTextStyle().bigText(remoteMessage.getData().get(Constant.KEY_BODY)))
.setContentText(remoteMessage.getData().get(Constant.KEY_BODY))
.setAutoCancel(true)
.setLargeIcon(BitmapFactory.decodeResource(getResources(), R.mipmap.ic_launcher))
.setSound(defaultSoundUri);
// if (!BaseActivity.isInForeground()) {
notificationBuilder.setContentIntent(pendingIntent);
// }
// Generate ID
long time = new Date().getTime();
String tmpStr = String.valueOf(time);
String last4Str = tmpStr.substring(tmpStr.length() - 5);
int notificationId = Integer.valueOf(last4Str);
// Sets an ID for the notification
// int notificationId = Constant.NOTIFICATION_ID;
// Gets an instance of the NotificationManager service
NotificationManager mNotifyMgr = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
// Builds the notification and issues it.
mNotifyMgr.notify(notificationId, notificationBuilder.build());
}
I am trying to build a notification method that would result in a notification appearing on the locked screen when a particular beacon is detected. My understanding is that I need to include .setVisibility(0) in the following code:
public void showNotification(Beacon beacon) {
Resources r = getResources();
int random = (int)System.currentTimeMillis();
Notification notification = new NotificationCompat.Builder(this)
.setSmallIcon(android.R.drawable.ic_popup_reminder)
.setContentTitle("Beacons Found")
.setContentText(beacon.getID().toString())
.setVisibility(0) // allow notification to appear on locked screen
.setAutoCancel(true)
.build();
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
notificationManager.notify(random, notification);
}
I have the above code, but when I run it it says "Cannot find symbol method setVisibility(int)". I have done some research online and it seems I need to import these:
import android.support.v4.app.NotificationCompat;
import android.app.Notification;
import android.app.NotificationManager;
Even if I include these imports, I still get the same error message. Can anyone help? Thanks!!
setVisibility() was added in Api 21 According to documentation I found may try this.
if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.LOLLIPOP) {
Notification notification = new NotificationCompat.Builder(this)
.setSmallIcon(android.R.drawable.ic_popup_reminder)
.setContentTitle("Beacons Found")
.setContentText(beacon.getID().toString())
.setVisibility(0) // allow notification to appear on locked screen
.setAutoCancel(true)
.build();
NotificationManager notificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
notificationManager.notify(random, notification);
}
I building a notifiaction with NotificationCompat.Builder and to show it I need to notify NotificationManager about new notifation, so I'm calling
NotificationManager mNotifyMgr = (NotificationManager) cont.getSystemService(Context.NOTIFICATION_SERVICE);
mNotifyMgr.notify(SOME_INT_NUMBER, builder.build());
but eclipse marks "notif(..)" as error with caption:
The method notify() in the type Object is not applicable for the arguments (int, Notification)
And I'm pretty sure notif(int, Notification) exists:
http://developer.android.com/reference/android/app/NotificationManager.html
Can somebody explain what I'm doing wrong?
EDIT:
I discovered also I can't import android.app.NotificationManager, due to:
The import android.app.NotificationManager conflicts with a type defined in the same file
I am using the Notification Compat Builder and Notification Manager to generate notifications and it works just fine for me. Pasting the working code below, check if you have missed out something:
import android.app.NotificationManager;
import android.support.v4.app.NotificationCompat;
final int notificationID = (int)System.currentTimeMillis();
final int icon = R.drawable.nf_notification;
final NotificationManager notificationManager = (NotificationManager)context
.getSystemService(Context.NOTIFICATION_SERVICE);
final NotificationCompat.Builder builder = new NotificationCompat.Builder(context).setSmallIcon(icon)
.setContentTitle(title).setStyle(new NotificationCompat.BigTextStyle().bigText(message))
.setContentIntent(intent).setAutoCancel(true).setContentText(message);
notificationManager.notify(notificationID, builder.build());
This is my code:
NotificationManager mNotificationManager = (NotificationManager) c.getSystemService(ns);
//Instantiate the notification
CharSequence tickerText = "Hello";
long when = System.currentTimeMillis();
Notification.Builder builder = new Notification.Builder(c)
.setTicker(tickerText)
.setWhen(when)
.setContentTitle("Test Notification")
.setContentText(arg1.getStringExtra("info"))
.setSmallIcon(R.drawable.ic_launcher)
.setAutoCancel(true);
Notification notification = builder.getNotification();
mNotificationManager.notify(88, notification);
It works find, but using Notification notification = builder.getNotification(); is deprecated. as I should be doing Notification notification = builder.build();.
Problem is Eclipse isn't recognizing it as such, meaning it won't let me compile. The doc is clear that build() exists and its the preferred method, but its not working on my end. I would like to use non-deprecated code, so any help will be much appreciated.
imports
import android.app.Notification;
import android.app.Notification.Builder;
import android.app.NotificationManager;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.util.Log;
Be aware that import android.app.Notification.Builder; is saying its not being used.
If you want develop for version SDK lower than 11, you can use this code instead android.app.Notification.Builder class for creation notification:
private void createNotification(){
NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
Notification notification = new Notification(R.drawable.ic_launcher, "Hello", System.currentTimeMillis());
Intent notificationIntent = new Intent(this, YourActivity.class);
Random r = new Random();
int notificationId = r.nextInt();
notificationIntent.putExtra("n_id", notificationId);
PendingIntent contentIntent = PendingIntent.getActivity(this, notificationId, notificationIntent, PendingIntent.FLAG_UPDATE_CURRENT);
notification.defaults |= Notification.DEFAULT_SOUND;
notification.setLatestEventInfo(this, "Party", "Welcome!", contentIntent);
mNotificationManager.notify(notificationId, notification);
}
You can cancel this notification in YourActivity like this:
public class YourActivity extends Activity{
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.your_activity);
int notificationId = getIntent().getIntExtra("n_id", -1);
if (notificationId!=-1) {
NotificationManager mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
mNotificationManager.cancel(notificationId);
}
}
}
This only happens when, You are compiling your app code against the version which does not hold required method/api (in your case it is build()).
If build is not available in the version you are compiling with, I will suggest you to compile with higher version of Android, You always have minimum sdk version in manifest for backward compatibility.
Thanks