我在我的应用中使用FCM。我遵循了Firebase文档,所有内容似乎都按预期工作。
我可以在应用程序被杀死时在后台和前台接收消息通知。
现在我想通过添加一些应用偏好来完全控制用户。
我知道如何在应用程序被杀或在前台时执行此操作。我正在考虑访问FirebaseMessagingService中的sharedprefs,以查看应用是否应显示通知并检查要使用的铃声。除非有通用的方法来设置这些参数,例如从所有通知中“取消订阅”或更改我不知道的应用默认通知铃声?
但是,由于通知被传送到设备的系统托盘,我不知道如何在应用程序处于后台时收到的通知中执行此操作。 任何人都有任何想法或可以指出我的一些文件...我没有找到任何关于此的信息?
答案 0 :(得分:1)
默认情况下,通知会影响每个用户。如果您希望允许用户选择停用所有通知(或某些通知子集),则应使用topic messaging:默认情况下,您需要为所有通知subscribeToTopic()
如果用户选择退出通知,则您需要拨打unsubscribeToTopic()
。
通过向主题发送通知,只有订阅的用户才会收到该通知。
notification payload support documentation解释了如何在Android上添加sound
参数来覆盖铃声,这可以是应用程序res/raw
目录中捆绑的任何声音。
应该注意的是,控制台中不支持这些功能,但要求您创建自己的Firebase Cloud Messaging Server
答案 1 :(得分:1)
由于firebase通知服务有2个对象1st是"数据"第二个是"通知",当您从firebase控制台发送推送时,它会在" notification"中发送数据。宾语。当您在FirebaseMessagingService.class中处理通知时,您正在使用NotificationBuilder创建自定义通知。当应用程序处于后台时,您将无法通过"通知"创建通知。宾语。因此,您的自定义通知将不会出现在通知托盘中,您需要从后端发送通知并在"数据"中发送通知内容。宾语。您每次都可以自定义通知。 请参考以下内容:https://firebase.google.com/docs/cloud-messaging/android/send-multiple
答案 2 :(得分:0)
用户可以停用应用设置中的所有通知。
您可以按自己的说法使用共享偏好设置。就一般方法而言,你应该研究@ianhanniballake的答案。
用户可以从应用设置
更改通知铃声
对于默认铃声,请参阅此link。此链接中的第3个答案还说明了如何从应用程序的设置活动中调出声音选择器。如果您想要自定义声音,请参阅this。
当然,您必须存储用户首选项,这样您才不会每次都要求用户选择声音。
还有一件事,因为您正在使用服务,因此您不必每次都能访问共享首选项以查找要播放的声音,您可以将选项存储在任何变量中。每当用户更改notif-sound时,您可以设置监听器或{停止服务 - >更新偏好 - >重启服务}。确保每次服务启动时都会读取首选项。
答案 3 :(得分:0)
在this AndroidHive 教程中,您可以找到我们如何更改特定应用的铃声,以及当应用处于前台且应用处于后台时如何处理通知。
$lastId = null;
foreach($items as $item){
/*get total num for rowspan*/
$group = $buyer->get_total_rowspan($obj->id, $obj->supplier);
echo '<tr>
<td>$item->id</td>
<td>$item->name</td>
<td>$item->supplier</td>';
if($lastId != $group->Id){
<td rowspan="$group->countRow"><a>Manage</a></td>
}
echo '</tr>'
$lastId = $group->Id;
}
当发送通知类型消息时,firebase会在应用程序处于后台时自动显示通知。如果应用程序位于前台,handleNotification()方法将处理通知消息。
@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
......
// Check if message contains a notification payload.
if (remoteMessage.getNotification() != null) {
Log.e(TAG, "Notification Body: " + remoteMessage.getNotification().getBody());
handleNotification(remoteMessage.getNotification().getBody());
}
}
您可以在此处理自定义通知声音
private void handleNotification(String message) {
if (!NotificationUtils.isAppIsInBackground(getApplicationContext())) {
// app is in foreground, broadcast the push message
Intent pushNotification = new Intent(Config.PUSH_NOTIFICATION);
pushNotification.putExtra("message", message);
LocalBroadcastManager.getInstance(this).sendBroadcast(pushNotification);
// play notification sound
NotificationUtils notificationUtils = new NotificationUtils(getApplicationContext());
notificationUtils.playNotificationSound();
}else{
// If the app is in background, firebase itself handles the notification
}
}
答案 4 :(得分:0)
当您的应用处于后台或被杀时,Firebase不会调用您的onMessageReceived,并且您无法自定义您的通知。系统生成的通知将显示。
使firebase库在每种情况下调用onMessageReived
a)前景
b)背景
c)被杀
你不能把你的请求中的json密钥“通知”放到firebase api中,而是使用“data”,见下文。
例如,以下消息不会调用onMessagereceived()
{
"to": "/topics/test",
"notification": {
"title" : "title",
"text": "data!",
"icon": "ic_notification"
}
}
但这将有效
{
"to": "/topics/test",
"data": {
"text":"text",
"title":"",
"line1":"testline",
"line2":"test"
}
}
请看此链接:https://firebase.google.com/docs/cloud-messaging/concept-options 它有firebase消息类型的详细描述 例如:
@Override
public void onMessageReceived(RemoteMessage remoteMessage) {
Log.d(TAG, "From: " + remoteMessage.getFrom());
// Check if message contains a data payload.
if (remoteMessage.getData().size() > 0) {
Log.d(TAG, "Message data payload: " + remoteMessage.getData());
}
if(remoteMessage.getData().get("state").toString().equals("Request")){
sendNotification(remoteMessage.getData().get("body").toString(), remoteMessage.getData().get("message").toString(), remoteMessage.getData().get("state").toString(),Activity_name.class);
}
}
private void sendNotification(String messageBody, String data, String state,Class<?> activityCompat) {
int requestID = (int) System.currentTimeMillis();
Intent intent = new Intent(this, activityCompat);
Bundle bundle = new Bundle();
bundle.putString("message", data);
bundle.putString("state", state);
intent.putExtras(bundle);
PendingIntent pendingIntent = PendingIntent.getActivity(this, requestID, intent, PendingIntent.FLAG_UPDATE_CURRENT);
NotificationCompat.Builder notificationBuilder = new NotificationCompat.Builder(this)
.setSmallIcon(R.drawable.small_logo)
.setContentTitle("Title")
.setContentText(messageBody).setContentIntent(pendingIntent)
.setAutoCancel(true)
.setStyle(new NotificationCompat.BigTextStyle()
.bigText(messageBody))
.setTicker(messageBody);
NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);
notificationBuilder.getNotification().flags |= Notification.FLAG_AUTO_CANCEL;
Notification notification = notificationBuilder.build();
notificationManager.notify((int) Calendar.getInstance().getTimeInMillis(), notification);
}