OTTO和其他Activity中的Fragments

7
我昨天开始使用Square的OTTO,到目前为止我有一个良好的开端。
当您的片段已经托管在FragmentActivity中,并且您只需要在由该FragmentActivity托管的Fragment之间进行通信时,Otto可以很好地运作。
当已经托管时,您的#onResume()方法将被调用,Fragment可以在Eventbus上注册自己。
@Override
public void onResume()
{
    super.onResume();
    BusProvider.getInstance().register(this);
}

我的问题:

片段嵌入了一个额外的活动,该活动应通过Eventbus接收事件,如下所示:

public AnotherFragmentHostedInSomeActivity extends Fragment
{
         .....

    @Subscribe
    public void onSomethingHappend(final Event event)
    {

          final SomeObject deliveredObject = event.getSomeObject();

但是如果您想调用托管片段的另一个活动,似乎情况仍然很复杂,就像这段代码那样:

public class SomeFragmentSendingDataToAnotherFragment extends Fragment
{
            ...
    private void sendData()
    {
            final Intent intent = new Intent(applicationContext, SomeActivity.class);
            applicationContext.startActivity(intent);                                 
            BusProvider.getInstance().post(new Event(someObject));

正如你可能已经看到的那样,这段代码有点不可靠。启动一个Activity,然后向该Activity托管的Fragment发送数据是行不通的,因为生命周期的原因。所以Activity被创建,Fragments也被创建。在某个时候,onResume方法被调用,因此Fragment可以使用@Subscribe注册自己。但是所有这些都发生在事件已经通过EventBus发布之后。因此,感兴趣的Fragment永远不会被EventBus调用。
有人知道如何以聪明的方式解决这个问题吗?
一些额外的信息: 昨天我尝试了OTTO。这个问题只在我的项目中出现,当我需要将数据发送到另一个Activity时,这在我的情况下总是发生在智能手机上运行应用程序时,而不是平板电脑上。在我使用Intent和Parcelable发送所有数据之前,Otto可以减少编写Parcelable对象的需求,因此我想走这条路。
感谢答案
3个回答

16

当第二个Activity启动时,原始的Activity已经不存在了。正如其他人指出的那样,如果您想要从一个Activity传递数据到另一个Activity,使用Intents可能是最好的方法。

如果您真的需要一个事件总线,您需要一个对象,即使在第一个Activity消失后也能保持活动状态。在Android中,这与应用程序上下文相关联,或者如果使用Dagger或Guice,则是@Singleton。

这个单例对象是您使用Otto的@Produce注释的地方。当第二个Activity订阅总线时,它将接收来自该@Produce方法的所有数据。


谢谢Eric澄清这一点。我对Bus的功能有不同的印象。生命周期在这里根本没有发挥作用。因此,我仍然需要知道我的Fragment是否处于某种平板电脑或手机“模式”中,以触发事件。 - Kitesurfer

1

您可以查看Jake Wharton在Otto Github issue上发布的答案。 您可以使用@Producer。

当您进行HTTP请求并将响应缓存在某个地方(例如,员工列表)时。大多数人会启动一个请求,并在某个回调上直接操作其活动。问题出现在此处,当设备旋转时,在onPause和onResume之间发生回调。相反,您可以在总线上返回HTTP调用结果时发布事件,以便任何正在监听的人都会收到它并将其发送到缓存中。然后,如果有新的订阅者对响应感兴趣,您可以有一个生产者与缓存交谈以生成HTTP调用的结果。这样,当您暂停活动(并注销)并且调用返回时,一旦您恢复(并重新注册),您的生产者将被调用,并通知活动。


0

你尝试过使用@Produce注解吗?当你的第二个Activity中的Fragment在总线上注册自己时,任何具有相应@Produce方法的@Subscribe方法都将被运行。


我试过了。我还添加了一些DeadObject Subscriber,以获取所有未送达的对象。我仍然看到它被调用了。我深入挖掘了OTTO代码。 对于我来说,问题看起来像是Activity异步启动到OTTO,某个时候onResume被调用,但在这种情况下太晚了。 我认为我必须延迟对OTTO的post调用,才能使其正常工作,但这也很棘手。IntentTool.showForecastActivity(getSherlockActivity().getApplicationContext()); BusProvider.getInstance().post(new Event(object)); - Kitesurfer
在我看来,你似乎在错误地使用事件总线。如果你需要在 Activity 启动时发布一个事件,请通过 Intent 传递数据。 - SeanPONeil
好的,我以前做过这个。如果你想保持简单,我希望尽可能使用总线。否则,我还有两种方法负责处理传入的数据。 - Kitesurfer
如果您想在Fragment创建时立即响应事件,请使用@Produces方法。 - SeanPONeil

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接