gpt4 book ai didi

java - 将 Paging Library 3 与来自 Java 的 LiveData 结合使用

转载 作者:行者123 更新时间:2023-12-02 12:40:11 25 4
gpt4 key购买 nike

我想将 Paging Library 3 与来自 Java 的 LiveData 结合使用。 documentation解释了如何使用 Guava Futures、RxJava Singles 和 Kotlin Coroutines,但没有说明如何将其与来自 Java 的 LiveData 一起使用。我大概可以 各种PagingSource 类提供loadloadSingleloadFuture

Kotlin 中的 load 示例使用协程改造加载数据,因此可以返回一个 LoadResult 对象。但是对于 LiveData,我需要从改造中进行异步调用并在 LiveData 对象上设置值。 LiveData 没有单独的 load 实用方法,就像 RxJavaGuava 一样。那么,如何使用 Java 中的 LiveData 实现此目的?

package org.metabrainz.mobile.data.repository;

import androidx.annotation.NonNull;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.MutableLiveData;
import androidx.paging.PagingSource;

import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.metabrainz.mobile.data.sources.Constants;
import org.metabrainz.mobile.data.sources.api.MusicBrainzServiceGenerator;
import org.metabrainz.mobile.data.sources.api.SearchService;
import org.metabrainz.mobile.data.sources.api.entities.mbentity.MBEntity;
import org.metabrainz.mobile.data.sources.api.entities.mbentity.MBEntityType;
import org.metabrainz.mobile.presentation.features.adapters.ResultItem;
import org.metabrainz.mobile.presentation.features.adapters.ResultItemUtils;

import java.util.ArrayList;
import java.util.List;

import kotlin.coroutines.Continuation;
import okhttp3.ResponseBody;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;

public class SearchPagingSource extends PagingSource<Integer, ResultItem> {

@NonNull
private final static SearchService service = MusicBrainzServiceGenerator
.createService(SearchService.class, true);
@NonNull
private MBEntityType entity;
@NonNull
private String searchTerm;

public SearchPagingSource(@NonNull MBEntityType entity, @NonNull String searchTerm) {
this.entity = entity;
this.searchTerm = searchTerm;
}

@NotNull
@Override
public LiveData<LoadResult<Integer, ResultItem>> load(@NotNull LoadParams<Integer> loadParams,
@NotNull Continuation<? super LoadResult<Integer, ResultItem>> continuation) {

Integer pageSize = loadParams.getLoadSize();
Integer offset = loadParams.getKey() == null ? 0 : loadParams.getKey();

MutableLiveData<LoadResult<Integer, ResultItem>> resultsLiveData = new MutableLiveData<>();
service.searchEntity(entity.name, searchTerm, pageSize.toString(),
String.valueOf(offset * pageSize))
.enqueue(new Callback<ResponseBody>() {
@Override
public void onResponse(@NonNull Call<ResponseBody> call,
@NonNull Response<ResponseBody> response) {
try {
List<ResultItem> data = ResultItemUtils
.getJSONResponseAsResultItemList(response.body().string(), entity);

LoadResult.Page<Integer, ResultItem> loadResult
= new LoadResult.Page<>(data, Math.max(0, offset - pageSize),
offset + pageSize, LoadResult.Page.COUNT_UNDEFINED,
LoadResult.Page.COUNT_UNDEFINED);
resultsLiveData.setValue(loadResult);
} catch (Exception e) {
e.printStackTrace();
LoadResult.Error<Integer, ResultItem> error = new LoadResult.Error<>(e);
resultsLiveData.setValue(error);
}
}

@Override
public void onFailure(@NonNull Call<ResponseBody> call, @NonNull Throwable t) {

}
});
return resultsLiveData;
}


}

但是这会在运行时崩溃

org.metabrainz.android E/AndroidRuntime: FATAL EXCEPTION: main
Process: org.metabrainz.android, PID: 2222
java.lang.ClassCastException: androidx.lifecycle.MutableLiveData cannot be cast to androidx.paging.PagingSource$LoadResult
at androidx.paging.PageFetcherSnapshot.doInitialLoad(PageFetcherSnapshot.kt:302)
at androidx.paging.PageFetcherSnapshot$pageEventFlow$1.invokeSuspend(PageFetcherSnapshot.kt:149)
at androidx.paging.PageFetcherSnapshot$pageEventFlow$1.invoke(Unknown Source:10)
at androidx.paging.CancelableChannelFlowKt$cancelableChannelFlow$1.invokeSuspend(CancelableChannelFlow.kt:35)
at androidx.paging.CancelableChannelFlowKt$cancelableChannelFlow$1.invoke(Unknown Source:10)
at kotlinx.coroutines.flow.ChannelFlowBuilder.collectTo$suspendImpl(Builders.kt:327)
at kotlinx.coroutines.flow.ChannelFlowBuilder.collectTo(Unknown Source:0)
at kotlinx.coroutines.flow.internal.ChannelFlow$collectToFun$1.invokeSuspend(ChannelFlow.kt:33)
at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:56)
at kotlinx.coroutines.EventLoop.processUnconfinedEvent(EventLoop.common.kt:69)
at kotlinx.coroutines.DispatchedContinuationKt.resumeCancellableWith(DispatchedContinuation.kt:321)
at kotlinx.coroutines.intrinsics.CancellableKt.startCoroutineCancellable(Cancellable.kt:26)
at kotlinx.coroutines.CoroutineStart.invoke(CoroutineStart.kt:109)
at kotlinx.coroutines.AbstractCoroutine.start(AbstractCoroutine.kt:158)
at kotlinx.coroutines.BuildersKt__Builders_commonKt.launch(Builders.common.kt:54)
at kotlinx.coroutines.BuildersKt.launch(Unknown Source:1)
at kotlinx.coroutines.BuildersKt__Builders_commonKt.launch$default(Builders.common.kt:47)
at kotlinx.coroutines.BuildersKt.launch$default(Unknown Source:1)
at androidx.lifecycle.BlockRunner.maybeRun(CoroutineLiveData.kt:174)
at androidx.lifecycle.CoroutineLiveData.onActive(CoroutineLiveData.kt:240)
at androidx.lifecycle.LiveData$ObserverWrapper.activeStateChanged(LiveData.java:437)
at androidx.lifecycle.LiveData$LifecycleBoundObserver.onStateChanged(LiveData.java:395)
at androidx.lifecycle.LifecycleRegistry$ObserverWithState.dispatchEvent(LifecycleRegistry.java:361)
at androidx.lifecycle.LifecycleRegistry.forwardPass(LifecycleRegistry.java:300)
at androidx.lifecycle.LifecycleRegistry.sync(LifecycleRegistry.java:339)
at androidx.lifecycle.LifecycleRegistry.moveToState(LifecycleRegistry.java:145)
at androidx.lifecycle.LifecycleRegistry.handleLifecycleEvent(LifecycleRegistry.java:131)
at androidx.lifecycle.ReportFragment.dispatch(ReportFragment.java:68)
at androidx.lifecycle.ReportFragment.dispatch(ReportFragment.java:144)
at androidx.lifecycle.ReportFragment.onStart(ReportFragment.java:109)
at android.app.Fragment.performStart(Fragment.java:2637)
at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:1312)
at android.app.FragmentManagerImpl.moveFragmentToExpectedState(FragmentManager.java:1549)
at android.app.FragmentManagerImpl.moveToState(FragmentManager.java:1611)
at android.app.FragmentManagerImpl.dispatchMoveToState(FragmentManager.java:3039)
at android.app.FragmentManagerImpl.dispatchStart(FragmentManager.java:2996)
at android.app.FragmentController.dispatchStart(FragmentController.java:189)
at android.app.Activity.performStart(Activity.java:7007)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2867)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2986)
at android.app.ActivityThread.-wrap11(Unknown Source:0)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1671)
at android.os.Handler.dispatchMessage(Handler.java:108)
at android.os.Looper.loop(Looper.java:206)
at android.app.ActivityThread.main(ActivityThread.java:6784)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:240)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:852)

最佳答案

我已经打开了一个功能请求,要求将 LiveData Paging Source 与 Paging Library 一起发送。我收到了 Google 开发人员的以下回复。

The Java Guava samples on d.android.com are for Guava + LiveData, in the coroutine equivalent we use: Guava's ListenableFuture as an async primitive that returns a single result (equivalent to a Coroutine or RxJava Single), and LiveData for multiple results / stream of results (equivalent of Kotlin Flow, or RxJava Observable).

如果我想使用 LiveData,建议我在以下代码 fragment 的行中编写一些内容。

abstract class SearchPagingSource extends RxPagingSource<Integer, ResultItem>() {

@NotNull
public abstract LiveData<LoadResult<Integer, ResultItem>> loadLiveData(params: LoadParams<Key>);

@NotNull
@Override
public Single<LoadResult<Integer, ResultItem>> loadSingle(@NotNull LoadParams<Integer> loadParams) {
return loadLiveData(params).toRxJavaSingle(); // You must implement this bit!
}
}

上面代码段中使用的 LiveData 应该是 SingleLiveEvent

PS:如果有更多的开发人员提出要求,Google 开发人员愿意重新考虑他们在库中运送它的立场。相关的 Google 问题跟踪票是 this .

关于java - 将 Paging Library 3 与来自 Java 的 LiveData 结合使用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62895817/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com