我正在尝试使用robospice实现一个非常简单的案例:登录屏幕。单击登录按钮时,将显示加载动画并使用SpiceManager.execute(..)
进行请求(当然,不进行缓存。由于这是登录请求,我每次都需要对服务器进行实际调用)。
因此,要处理屏幕轮换等,Activity.onStart()
我应该使用SpiceManager.addListenerIfPending(..)
,如果请求实际上是未决的,我应该显示加载动画而不做任何实际请求。
问题是:PendingRequestListener
没有onRequestExists()
方法。它只有onRequestNotFound()
。
一种可能(但不令人满意)的解决方案是始终绘制加载屏幕,然后调用addListenerIfPending(..)
,然后在onRequestNotFound()
中删除加载动画。如果没有真正的请求,这会产生“闪烁”加载屏幕,这看起来非常糟糕。实现所需行为的正确方法是什么?
答案 0 :(得分:0)
好的,如果谷歌引导任何人在这里。 适当的解决方案: 实际上,此功能已经在库中。有一个方法在挂起请求WAS时被调用,它只是......没有。
你需要:
创建自己的扩展PendingRequestListener
的界面:
public interface MyPendingRequestListener<T> extends PendingRequestListener<T> {
void onRequestAggregated();
}
注意:在通过Robospice进行请求时,您需要使用实现此接口的请求侦听器。
创建自己的实现RequestListenerNotifier
的类。我通过复制粘贴DefaultRequestListenerNotifier
(我无法扩展它,因为方法post(..)
是私有的)来做到这一点,因为它包含其他情况下的porper通知实现。例如,MyRequestListenerNotifier
。
覆盖方法notifyListenersOfRequestAggregated
:
@Override
public <T> void notifyListenersOfRequestAggregated(final CachedSpiceRequest<T> request, Set<RequestListener<?>> listeners) {
post(new AggregatedRunnable(listeners), request.getRequestCacheKey());
}
private static class AggregatedRunnable implements Runnable {
private final Set<RequestListener<?>> listeners;
public AggregatedRunnable(final Set<RequestListener<?>> listeners) {
this.listeners = listeners;
}
@Override
public void run() {
if (listeners == null) {
return;
}
Ln.v("Notifying " + listeners.size() + " listeners of request aggregated");
synchronized (listeners) {
for (final RequestListener<?> listener : listeners) {
if (listener != null && listener instanceof MyPendingRequestListener) {
Ln.v("Notifying %s", listener.getClass().getSimpleName());
((MyPendingRequestListener<?>) listener).onRequestAggregated();
}
}
}
}
}
扩展SpiceService并覆盖以下方法(您需要使用此自定义服务而不是标准的robospice服务):
protected RequestListenerNotifier createRequestRequestListenerNotifier() {
return new MyRequestListenerNotifier();
}
就是这样。现在,当您使用addListenerIfPending
时,将在找到待处理请求时调用onRequestAggregated()
。
重要提示:这仅在您执行请求时使用缓存键时才有效。例如,您可以使用空字符串(但 NOT null)作为缓存键。
示例:
//doing request for the first time
spiceManager.execute(request, "", DurationInMillis.ALWAYS_EXPIRED, requestListener);
//...
//checking if request is pending e.g. when activity is restarted
spiceManager.addListenerIfPending(responseClass, "", requestListener);