【问题标题】:Android listener / callback How to?Android监听器/回调如何?
【发布时间】:2014-11-18 07:47:24
【问题描述】:

我有一个生成位图的 pojo 方法。完成后,我想将位图扔到 UI 活动中。这是一个示例,但这里是:

private void sendBitmap(Bitmap bitmap) {
    // TODO - I'm in the pojo where I want to send the bitmap
}

仅供参考:我要通知的 UI 活动在我的项目之外。我的意思是,我的项目是一个 SDK,因此其他开发人员会在它可用时立即获取此信息。


我一直试图弄清楚这一点,但有些困惑。

  1. 我需要一个“回调”接口吗?
  2. 还是“监听器”接口?
  3. 或两者兼而有之?

我在 MyActivity 中创建了一个回调接口。到目前为止,一切都很好。这是目前的样子:

import android.graphics.Bitmap;

public class MyActivity {

//  protected void whateverOtherMethods (Bundle savedInstanceState) 
//  {
//      .
//      .
//      .
//      .
//      .
//      .
//      
//  }

    /**
     * Callback interface used to supply a bitmap.
     */
    public interface MyCallback {
        public void onBitmapReady(Bitmap bitmap);
    }
}

演示应用的 DoSomethingActivity 可以实现我创建的回调接口。这是演示应用的 DoSomethingActivity 中回调的实现:

private final MyCallback myCallback = new MyCallback() {

    @Override
    public void onBitmapReady(Bitmap bitmap) {
        // TODO - do something with the bitmap
    }
};

我缺少通知回调的步骤是什么?也许我几乎拥有它,但我很困惑,所以我在这里寻求一点帮助。


更新:

好的,我已将回调“BitmapCallback”接口的“实现”添加到 pojo 中。这里是:

public class ProcessImage implements BitmapCallback {

/**
 * pojo method to return bitmap
 */
private void sendBitmap() {
    this.onBitmapReady(bitmap);
}

@Override
public void onBitmapReady(Bitmap bitmap) {
    // we still need to send the bitmap to cusomer App.

}

我无法从 SDK Activity 中移动回调定义,因为我希望客户的应用程序在其代码中实现回调,以便在位图返回给客户的应用程序时对其进行处理。

这是我的Activity中的回调接口:

public interface BitmapCallback {

    public void onBitmapReady(Bitmap processedBitmapy);
}

这是客户应用程序中的实现:

private final BitmapCallback bitmapCallback = new BitmapCallback()  
{

    @Override
    public void onBitmapReady(Bitmap bitmap) {
        // TODO Auto-generated method stub          
    }
};

称我为笨蛋,但我很难理解这一点。

【问题讨论】:

  • 你在寻找什么事件来回调?如果它的单击事件,您应该查看 OnClickListener,您可以在其中调用自定义侦听器。 developer.android.com/reference/android/view/…
  • 为什么投反对票?这是基于正在更改的某些位图的回调。它与 UI 无关。

标签: java android callback listener


【解决方案1】:

你快到了。你只需要告诉你的POJO 回调实例。首先,我强烈建议您将接口定义移到POJO 中(因为从概念上讲,它与该对象的作用比与您的活动更多)或使接口成为独立类型。 POJO 不应该知道客户端类中定义的类型。

那么你有一个选择:

  1. 使用侦听器模式:在您的POJO 中添加一个字段来存储回调实例(或者如果您想支持回调多个侦听器,则可以使用更复杂的东西)和设置侦听器的方法。当您创建或设置POJO 时,从您的活动(或任何适当的地方)调用该方法。
  2. 使用回调模式:使用回调参数增强相关 API 方法。

在任何一种情况下,当位图准备好后,您就可以将位图返回到活动中。

编辑

这是一个如何构建的示例。您尚未提供有关如何创建 POJO 或调用处理的任何信息,因此我发明了一些东西作为示例。它假设处理发生在一个单独的线程中,完成后将回调活动。您可以根据需要进行修改。 (特别是,如果POJO 同步完成工作,这会简单得多。此外,最好使用AsyncTaskLoader 而不是普通的普通线程,以便它与Activity 生命周期正确交互。 )

BitmapCallback.java

public interface BitmapCallback {
    public void onBitmapReady(Bitmap processedBitmap);
}

MyActivity.java

public class MyActivity extends Activity implements BitmapCallback {
    Handler mHandler; // initialize this in onCreate
    . . .

    public void onRequestImage() {
        ProcessImage processor = new ProcessImage();
        getImage(this /* , other actual args */);
    }

    @Override
    public void onBitmapReady(final Bitmap processedBitmap) {
        // since this may be called from a non-UI thread, we can't update
        // the UI directly.
        mHandler.post(new Runnable() {
            @Override
            public void run() {
                // handle the bitmap (update the UI, etc.)
            }
        });
    }
}

ProcessImage.java

public class ProcessImage {
    public void getAnImage(final BitmapCallback callback /* , other formal args */) {
        new Thread() {
            @Override
            public void run() {
                Bitmap bitmap;
                . . . // do the work
                // then deliver the results
                callback.onBitmapReady(bitmap);
            }
        }.start();
    }
}

【讨论】:

  • 首先,我要感谢您提供的信息。我仍在为此苦苦挣扎。请参阅上面问题末尾添加的我的 UPDATE
  • @Lucy - 你的逻辑倒退了。应该实现回调功能的是活动,而不是 pojo。该功能的定义不应与活动的定义相关联;否则 pojo 将依赖于活动,这是不可取的。我添加了一个具体的例子来说明我的意思。
【解决方案2】:

在你的 pojo 类中创建你的监听器实例

MyCallback callback;

并在 sendBitmap 方法中设置 onBitmapReady 以通知活动

private void sendBitmap(Bitmap bitmap) {
    // TODO - I'm in the pojo where I want to send the bitmap
    callback.onBitmapReady();
}

【讨论】:

  • 没那么容易。实例为空,您无法实例化接口。当我终于明白这一点时,我会感到比现在还要愚蠢。感谢您的帮助。
【解决方案3】:

事实证明,为了使回调从意图内部工作,我需要使回调可序列化。在尝试之后并继续得到一个错误,反映 Activity 试图以某种方式序列化自身,这导致应用程序崩溃。

所以我回到了全智者 Ted Hopp。根据 Ted 的建议,我最终使用了广播。在此处查看主题:how to use LocalBroadcastManager?

很好的建议,泰德,这解决了我的问题。

经验教训:如果您尝试使用从 SDK 回调到“外部”应用程序并遇到问题,请尝试查看广播。

【讨论】:

    猜你喜欢
    • 2014-12-13
    • 2012-09-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-05-20
    • 2017-06-11
    相关资源
    最近更新 更多