回收者视图始终将项目放在顶部

时间:2018-08-02 20:26:42

标签: android android-recyclerview android-jetpack android-paging

我遇到了一个问题,即每次系统从服务中进行更新时,新物品都会放在回收者所在的物品之前。这意味着它将始终处于“终点”。我正在使用PagedList.BoundaryCallback库,但不知道要修复此问题。

这是我的RepoBoundaryCalback

class RepoBoundaryCallback(private val day:String,
                           private val service: PHService,
                           private val cache:PHLocalCache) : PagedList.BoundaryCallback<Post>()  {


    // keep the last requested page.
    // When the request is successful, increment the page number.
    private var lastRequestedPage = 1

    private val _networkErrors = MutableLiveData<String>()

    // LiveData of network errors.
    val networkErrors: LiveData<String>
        get() = _networkErrors

    // avoid triggering multiple requests in the same time
    private var isRequestInProgress = false

    /**
     * This method is called at the very beggining
     */
    override fun onZeroItemsLoaded() {
        requestAndSaveData()
    }

    /**
     * This method will tell when the user reached the end of the recycler view
     */
    override fun onItemAtEndLoaded(itemAtEnd: Post) {

        requestAndSaveData()
        //TODO resolver este bug
        //ele aqui sabe que chegou ao fim , o problema desta API é que nao dá o total de páginas
        // e quando ultrapassa as paginas que deve ela dá dados repetidos
        //  como o onConflit está replace ele está sempre a substituir os items e sempre a actualizar
    }

    /**
     * Requests data from the API and increment the page in case of success
     * Save the fetched data into the database to allow offline usage
     */
    private fun requestAndSaveData(){

        //TODO ao atingir o total de páginas o isRequestInProgress estará a  null(o problema de estar sempre a actualizar vem daqui)
        if (isRequestInProgress) return
        isRequestInProgress = true
        getPosts(service,day,lastRequestedPage,BuildConfig.API_KEY, NETWORK_PAGE_SIZE,{ repos ->
            cache.insert(repos){
                lastRequestedPage++
                isRequestInProgress = false
            }
        },{error ->
            _networkErrors
            isRequestInProgress = false
        })
    }

    /**
     * static block to have the page size to the network calls
     */
    companion object {
        private const val NETWORK_PAGE_SIZE = 10
    }
}

这是我的PostDao,因为我认为订购这些商品应该可以解决

@Dao
interface PostDao {

    @Query("SELECT * FROM product_post ORDER BY votesCount DESC, productName ASC")
    fun loadPosts() : DataSource.Factory<Int,Post>

    @Insert(onConflict = OnConflictStrategy.REPLACE)
    fun insertAll(message: List<Post>)
}

这是我的存储库

class PHRepository (private val service:PHService,
                   private val cache: PHLocalCache) {


    /**
     * Search repositories whose names match the query.
     */
    fun search(day: String): PostResult {

        // Get data source factory from the local cache
        val dataSourceFactory = cache.loadPosts(day)

        // Construct the boundary callback
        val boundaryCallback = RepoBoundaryCallback(day, service,cache)
        val networkErrors = boundaryCallback.networkErrors

        // Get the paged list
        val data = LivePagedListBuilder(dataSourceFactory, DATABASE_PAGE_SIZE)
                .setBoundaryCallback(boundaryCallback)
                .build()

        // Get the network errors exposed by the boundary callback
        return PostResult(data)

    }

    companion object {
        private const val DATABASE_PAGE_SIZE = 20
    }
}

这是我的ViewModel

class PostsViewModel @Inject constructor(private val phRepository: PHRepository) : ViewModel() {

    companion object {
        private const val VISIBLE_THRESHOLD = 5
    }


    private val queryLiveData = MutableLiveData<String>()
    private val repoResult: LiveData<PostResult> = Transformations.map(queryLiveData, {
        phRepository.search(it)
    })

    val repos: LiveData<PagedList<Post>> = Transformations.switchMap(repoResult,
            { it -> it.data })


    /**
     * Search a repository based on a query string.
     */
    fun searchRepo(queryString: String) {
        queryLiveData.postValue(queryString)
    }

    /**
     * Get the last query value.
     */
    fun lastQueryValue(): String? = queryLiveData.value

}

这是我的片段

class PostFragment : BaseFragment<FragmentPostsBinding, PostsViewModel>() {

    companion object {
        fun newInstance() = PostFragment()
    }

    private lateinit var viewModelFrag :PostsViewModel //TODO nao foi inicializado
    private val adapter = PostAdapter()

    override fun layoutToInflate(): Int = R.layout.fragment_posts

    override fun defineViewModel(): PostsViewModel {
        // get the view model
        viewModelFrag = ViewModelProviders.of(this, Injection.provideViewModelFactory(context))
                .get(PostsViewModel::class.java)
        return viewModelFrag
    }

    override fun doOnCreated() {
       initAdapter()
        retrieveData()
    }

    private fun initAdapter() {
        dataBinding.rclChatContent.adapter = adapter
        viewModelFrag.repos.observe(this, Observer<PagedList<Post>> {
            Log.d("Activity", "list: ${it?.size}")
            adapter.submitList(it)
        })
        dataBinding.rclChatContent.layoutManager = LinearLayoutManager(context)
        dataBinding.rclChatContent.addOnItemTouchListener(OnItemTouchListener(context,dataBinding.rclChatContent,
                object : TouchListener {
                    override fun onTouch(view: View?, position: Int?) {
                        val item = adapter.retrieveItem(position?:return)
                        Toast.makeText(context, "Clicou em" + item?.productName  , Toast.LENGTH_LONG).show()
                    }
                    override fun onLongTouch(view: View?, position: Int?) {
                        val item = adapter.retrieveItem(position?:return)
                        Toast.makeText(context, "Clicou longo em" + item?.productName, Toast.LENGTH_LONG).show()
                    }
                }))
    }


    private fun retrieveData() {

        viewModelFrag.searchRepo("2018-07-31")
        adapter.submitList(null)

    }

}

由于有人遇到这个问题,我们可以帮助我吗?

0 个答案:

没有答案