从通知栏与AsyncTask交互

时间:2014-03-02 07:38:31

标签: android android-asynctask broadcastreceiver android-notifications android-pendingintent

所以我有一个处理上传到服务器的AsyncTask,同时调用NotificationHelper类来更新通知栏以显示当前的上传百分比。这部分工作正常,我唯一的问题是让动作正常工作,并能够使用动作发送的意图(最近的尝试是在父活动中使用广播管理器,但我从来没有得到消息)。如果有人能指出我正确的方向,那将非常感激。

以下是一些代码:

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

    Intent intent = new Intent("com.example.sibmedemo.sibme");
    intent.putExtra("message","pause");
    PendingIntent pIntent = PendingIntent.getActivity(mContext, 0, intent, 0);

    mBuilder = new Notification.Builder(mContext)
            .setContentTitle("Upload File")
            .setContentText("Upload in progress")
            .setSmallIcon(R.drawable.ic_launcher)
            .addAction(R.drawable.ic_launcher,"Pause",pIntent)
            .addAction(R.drawable.ic_launcher,"Cancel",pIntent);

    mBuilder.setProgress(100,0,false);
    mNotificationManager.notify(0,mBuilder.build());

我认为我的主要问题是我无法正确理解pendingIntents如何工作或如何在Android活动中进行交换,这个问题的任何清晰度都会有所帮助。

-------使用解决方案后的工作代码----------- 主要活动-----------

public class FileUploadActivityV2 extends Activity {

public static int flags = 0;
public BroadcastReceiver receiver = new BroadcastReceiver() {
    @Override
    public void onReceive(Context context, Intent intent) {

        Log.i("message", "got a message");

        if(intent.getStringExtra("message").equalsIgnoreCase("pause"))
            flags = 1;

        goAsync();
    }
};

protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_file_upload_activity_v2);

    registerReceiver(receiver, new IntentFilter("sibme"));

    flags = 0;
    (new UploadTask(this)).execute();
}

是的,我知道我想要照顾brodcastReceiver的生命周期,但截至目前,这是可以接受的测试。对于任何想知道的人来说,goAsync()函数是Android API的一部分,并简单地说明一旦接收器调用onReceive函数,将来回收接收器,以便它可以再次使用。

在AsyncTask类中---------

    @Override
    protected Long doInBackground(Integer... integers) {

    while(FileUploadActivityV2.flags == 0)
    {
        try{
            Thread.sleep(1000);
            Log.i("Running", "Running in background");
        }catch(Exception e){

        }
    }

    return null;
}

通知助手类------

    public void createNotification() {
    mNotificationManager = (NotificationManager) mContext.getSystemService(Context.NOTIFICATION_SERVICE);

    Intent intent = new Intent("sibme");
    intent.putExtra("message","pause");
    PendingIntent pIntent = PendingIntent.getBroadcast(mContext, 0, intent, 0);

    mBuilder = new Notification.Builder(mContext)
            .setContentTitle("Upload File")
            .setContentText("Upload in progress")
            .setSmallIcon(R.drawable.ic_launcher)
            .addAction(R.drawable.ic_launcher,"Pause",pIntent)
            .addAction(R.drawable.ic_launcher,"Cancel",pIntent);

    mBuilder.setProgress(100,0,false);
    mNotificationManager.notify(0,mBuilder.build());

}

2 个答案:

答案 0 :(得分:3)

理解PendingIntent很重要。这是Android拥有的强大组件之一,除了通知操作处理之外,它还可以用于很多目的。

您可以将待处理意图视为表示您要执行的操作的对象(发送广播/启动活动/启动服务)+执行此操作的意图。它的强大之处在于你可以向另一个进程/应用程序提供待处理的意图(在你的情况下,另一个进程是操作系统NotificationManager),你可以通过它提供另一个进程来唤醒你的应用程序并自动启动您提供未决意图的意图。

因此,待处理的意图以某种方式在通知中用作"远程监听器"不必为了检测事件而运行(在您的情况下,事件是通知按钮单击)

由于PendingIntent作为在不同应用之间共享的对象的性质 - 您可以通过静态方法(PendingIntent.getService() / PendingIntent.getActivity()等获得引用/创建新方法)返回给您由系统管理的新实例或现有实例。

让我们来看看你的代码:

通过调用PendingIntent.getActivity()创建挂起的意图,AlarmManager可以启动您在意图中提供的特定活动(" com.example.sibmedemo.sibme"在您的情况下)。我想你想要有不同的反应来暂停和取消动作。 这就是为什么你们每个人都需要不同的未决意图。您可以通过多种方式区分这两种行为:

  • 为每一个开始不同的活动/服务或发送广播(PendingIntent.getBroadcast())
  • 开始相同的活动,但请使用different request code

无论如何 - 你必须创建不同的意图和thuss - 两个不同的待定意图来表示你想为不同的动作执行的不同动作。

希望它能帮到你,也许还有其他人。

答案 1 :(得分:2)

要与在后台工作的asynctask交互,那么你可以在publishProgress()中这样做(我从未尝试过)。否则你只需要执行前后执行。如果不是这种情况,我唯一可以提出的是一个类int变量,其值根据用户点击的按钮而改变。然后可以在doInBackground中检查它,并采取适当的措施。