如何使用 RemoteViews 更新通知? [英] How to update Notification with RemoteViews?

查看:45
本文介绍了如何使用 RemoteViews 更新通知?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用 RemoteViews 来自自定义 Service,它在前台模式下运行通知(即,只要通知对用户可见,服务将保持活动状态).通知设置为正在进行,因此用户无法将其刷掉.

I'm creating a notification with RemoteViews from a custom Service, which is running with notification in a foreground mode (that is, service will remain active as long as notification is visible to user). Notification is set as Ongoing so user cannot swipe it off.

我想更改例如 ImageView 中显示的位图,包含在远程视图的布局中或更改 TextView 中的文本值.远程视图中的布局使用 XML 布局文件设置.

I'd like to change for example bitmap shown in ImageView, contained within remote view's layout or change text value in a TextView. Layout in remote view is set with XML layout file.

我的问题是,一旦通知被创建并对用户可见,如果我调用任何 RemoteViews 的函数,如 setImageViewResource() 改变 中显示的 BitmapImageView,变化不可见,除非我调用 setImageViewResource() 之后调用:

My problem is that once notification is created and visible to user, if I call any of RemoteViews's functions like setImageViewResource() to change Bitmap shown in an ImageView, the change is not visible, unless I do call setImageViewResource() I call afterwards:

NotificationManager.notify( id, notification );

Service.startForeground(id,notification);

虽然这对我来说听起来不对.我不敢相信要在已创建的通知中更新 RemoteViews UI,我必须重新初始化通知.如果我在通知中有 Button 控件,它会在触摸和释放时自动更新.所以必须有一种方法来正确地做到这一点,但我不知道如何.

This doesn't sound right to me though. I can't believe that to update RemoteViews UI in a notification that is already created, I have to re-initialize notification. If I have Button control in a notification, it updates itself on touch and release. So there's gotta be a way to do this properly, but I don't know how.

这是我的代码,它在我的 Service 实例中创建通知:

Here is my code which creates notification inside my Service instance:

this.notiRemoteViews = new MyRemoteViews(this,this.getApplicationContext().getPackageName(),R.layout.activity_noti1);

Notification.Builder notibuilder = new Notification.Builder(this.getApplicationContext());
notibuilder.setContentTitle("Test");
notibuilder.setContentText("test");
notibuilder.setSmallIcon(R.drawable.icon2);
notibuilder.setOngoing(true);

this.manager = (NotificationManager)this.getSystemService(Context.NOTIFICATION_SERVICE);
this.noti = notibuilder.build();
this.noti.contentView = this.notiRemoteViews;
this.noti.bigContentView = this.notiRemoteViews;
this.startForeground(NOTIFICATION_ID, this.noti);

强制" UI 更改为通知的功能:

And function that 'forces' UI changes to notification:

public void updateNotiUI(){
    this.startForeground(NOTIFICATION_ID, this.noti);
}

MyRemoteViews 类中,当需要时,我这样做是为了对 UI 进行更改:

Within MyRemoteViews class, when required, I do this to make changes to UI:

this.setImageViewResource(R.id.iconOFF, R.drawable.icon_off2);
this.ptMyService.updateNotiUI();

谁能告诉我更新通知中 RemoteViews 的 UI 组件的正确方法是什么?

Can anyone tell me what is the correct way of updating UI components of a RemoteViews in the notification?

推荐答案

这里有一个使用 RemoteViews 更新通知的详细示例:

Here's a detail example for you to update the notification using RemoteViews:

private static final int NOTIF_ID = 1234;
private NotificationCompat.Builder mBuilder;
private NotificationManager mNotificationManager;
private RemoteViews mRemoteViews;
private Notification mNotification;
...

// call this method to setup notification for the first time
private void setUpNotification(){

    mNotificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

    // we need to build a basic notification first, then update it
    Intent intentNotif = new Intent(this, MainActivity.class);
    intentNotif.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
    PendingIntent pendIntent = PendingIntent.getActivity(this, 0, intentNotif, PendingIntent.FLAG_UPDATE_CURRENT);

    // notification's layout
    mRemoteViews = new RemoteViews(getPackageName(), R.layout.custom_notification_small);
    // notification's icon
    mRemoteViews.setImageViewResource(R.id.notif_icon, R.drawable.ic_launcher);
    // notification's title
    mRemoteViews.setTextViewText(R.id.notif_title, getResources().getString(R.string.app_name));
    // notification's content
    mRemoteViews.setTextViewText(R.id.notif_content, getResources().getString(R.string.content_text));

    mBuilder = new NotificationCompat.Builder(this);

    CharSequence ticker = getResources().getString(R.string.ticker_text);
    int apiVersion = Build.VERSION.SDK_INT;

    if (apiVersion < VERSION_CODES.HONEYCOMB) {
        mNotification = new Notification(R.drawable.ic_launcher, ticker, System.currentTimeMillis());
        mNotification.contentView = mRemoteViews;
        mNotification.contentIntent = pendIntent;

        mNotification.flags |= Notification.FLAG_NO_CLEAR; //Do not clear the notification
        mNotification.defaults |= Notification.DEFAULT_LIGHTS;

        // starting service with notification in foreground mode
        startForeground(NOTIF_ID, mNotification);

    }else if (apiVersion >= VERSION_CODES.HONEYCOMB) {
        mBuilder.setSmallIcon(R.drawable.ic_launcher)
                .setAutoCancel(false)
                .setOngoing(true)
                .setContentIntent(pendIntent)
                .setContent(mRemoteViews)
                .setTicker(ticker);

        // starting service with notification in foreground mode
        startForeground(NOTIF_ID, mBuilder.build());
    }
}

// use this method to update the Notification's UI
private void updateNotification(){

    int api = Build.VERSION.SDK_INT;
    // update the icon
    mRemoteViews.setImageViewResource(R.id.notif_icon, R.drawable.icon_off2);
    // update the title
    mRemoteViews.setTextViewText(R.id.notif_title, getResources().getString(R.string.new_title));
    // update the content
    mRemoteViews.setTextViewText(R.id.notif_content, getResources().getString(R.string.new_content_text));

    // update the notification
    if (api < VERSION_CODES.HONEYCOMB) {
        mNotificationManager.notify(NOTIF_ID, mNotification);
    }else if (api >= VERSION_CODES.HONEYCOMB) {
        mNotificationManager.notify(NOTIF_ID, mBuilder.build());
    }
}

通知的布局,即res/layout/custom_notification_small.xml:

<!-- We have to set the height to 64dp, this is the rule of the small notification -->
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="64dp"
    android:orientation="horizontal"
    android:id="@+id/notif_small"
    android:background="@drawable/notification_background">

    <ImageView
        android:id="@+id/notif_icon"
        android:contentDescription="@string/notif_small_desc"
        android:layout_width="47dp"
        android:layout_height="wrap_content"
        android:layout_centerVertical="true"
        android:layout_alignParentLeft="true"
        android:src="@drawable/ic_launcher"
        android:layout_marginLeft="7dp"
        android:layout_marginRight="9dp"/>

    <TextView
        android:id="@+id/notif_title"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@id/notif_icon"
        android:singleLine="true"
        android:paddingTop="8dp"
        android:textSize="17sp"
        android:textStyle="bold"
        android:textColor="#000000"
        android:text="@string/app_name"/>

    <TextView
        android:id="@+id/notif_content"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_toRightOf="@id/notif_icon"
        android:paddingBottom="9dp"
        android:layout_alignParentBottom="true"
        android:singleLine="true"
        android:textSize="13sp"
        android:textColor="#575757"
        android:text="Content" />
</RelativeLayout>

希望这个例子对你有很大帮助!

Hope this example helps you a lot!

注意:您无法在蜂窝前版本上更新自定义 NotificationCompat,因此我添加了一种在蜂窝前版本上更新它的替代方法,即首先检查 API 级别并使用已弃用的 <代码>通知代替.

NOTE: You can't update the custom NotificationCompat on pre-Honeycomb, so I added an alternative way to update it on pre-Honeycomb, i.e. checking the API level first and use the deprecated Notification instead.

这篇关于如何使用 RemoteViews 更新通知?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆