Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/android/221.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Android smoothScrollToPosition在RecyclerView上闪烁_Android_Android Recyclerview - Fatal编程技术网

Android smoothScrollToPosition在RecyclerView上闪烁

Android smoothScrollToPosition在RecyclerView上闪烁,android,android-recyclerview,Android,Android Recyclerview,我有一个recyclerView,其中列出了在特定事件发生时要滚动到的项目。我使用的是smoothScrollToPosition,但令我惊讶的是,它不仅一点也不平滑,而且我还得到了闪烁效果,就像它必须在实际滚动之前恢复基本位置一样。从这里可以看到效果: 这是正常的行为吗 适配器代码: @ActivityScope class HighlightListAdapter @Inject constructor() : RecyclerView.Adapter<HighlightListAd

我有一个recyclerView,其中列出了在特定事件发生时要滚动到的项目。我使用的是
smoothScrollToPosition
,但令我惊讶的是,它不仅一点也不平滑,而且我还得到了闪烁效果,就像它必须在实际滚动之前恢复基本位置一样。从这里可以看到效果:

这是正常的行为吗

适配器代码:

@ActivityScope
class HighlightListAdapter @Inject constructor() : RecyclerView.Adapter<HighlightListAdapter.ViewHolder>() {

private var highlights: List<Highlight> = emptyList()
private var itemClick: ((Highlight, Int) -> Unit)? = null

private var selectedRow: MutableList<Int> = mutableListOf()

override fun onBindViewHolder(holder: ViewHolder, position: Int) {

    val binding = holder.binding
    val highlight = highlights[position]
    var viewModel = binding.viewModel

    viewModel?.unbind()

    viewModel = HighlightViewModel(highlight)
    binding.viewModel = viewModel
    viewModel.bind()

    if(selectedRow.contains(position)) {
        binding.rootItemView.alpha = 1.0f
    }
    else {
        binding.rootItemView.alpha = 0.5f
    }

    holder.setClickListener(itemClick)
}

override fun getItemCount(): Int = highlights.size

override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
    val binding = DataBindingUtil.inflate<ItemHighlightListBinding>(
            LayoutInflater.from(parent.context),
            R.layout.item_highlight_list,
            parent,
            false
    )
    return ViewHolder(binding)
}

fun updateEvents(highlights: List<Highlight>) {
    this.highlights = highlights
    notifyDataSetChanged()
}


fun setClickListener(itemClick: ((Highlight, Int) -> Unit)?) {
    this.itemClick = itemClick
}


fun enableRow(index: Int) {
    //Clear previous selection (only if we want single selection)
    selectedRow.clear()
    //Select specified row
    selectedRow.add(index)
    //Let the adapter redraw
    notifyDataSetChanged()
}

class ViewHolder(val binding: ItemHighlightListBinding) : RecyclerView.ViewHolder(binding.root) {

    fun setClickListener(callback: ((Highlight, Int) -> Unit)?) {
        binding.viewModel.clicks().subscribe {
            callback?.invoke(binding.viewModel.highlight, adapterPosition)
        }
    }

}

fun getSelected() = selectedRow

}
@ActivityScope
类HighlightListAdapter@Inject构造函数():RecyclerView.Adapter(){
private var highlights:List=emptyList()
私有变量项单击:((高亮显示,Int)->单位)?=null
私有变量selectedRow:MutableList=mutableListOf()
覆盖BindViewHolder(holder:ViewHolder,位置:Int){
val binding=holder.binding
val highlight=突出显示[位置]
var viewModel=binding.viewModel
viewModel?.unbind()
viewModel=高亮显示viewModel(高亮显示)
binding.viewModel=viewModel
viewModel.bind()
if(selectedRow.contains(位置)){
binding.rootItemView.alpha=1.0f
}
否则{
binding.rootItemView.alpha=0.5f
}
holder.setClickListener(itemClick)
}
重写getItemCount():Int=highlights.size
override onCreateViewHolder(父级:ViewGroup,viewType:Int):ViewHolder{
val binding=DataBindingUtil.inflate(
LayoutFlater.from(父上下文),
R.layout.项目突出显示列表,
父母亲
假的
)
返回视图保持器(绑定)
}
趣味更新事件(亮点:列表){
this.highlights=高光
notifyDataSetChanged()
}
趣味设置ClickListener(项单击:((突出显示,Int)->单位)?){
this.itemClick=itemClick
}
趣味使能行(索引:Int){
//清除以前的选择(仅当需要单个选择时)
selectedRow.clear()
//选择指定的行
selectedRow.add(索引)
//让适配器重新绘制
notifyDataSetChanged()
}
类ViewHolder(val绑定:ItemHighlightListBinding):RecyclerView.ViewHolder(binding.root){
有趣的设置ClickListener(回调:((突出显示,Int)->单位)?){
binding.viewModel.clicks().subscribe{
回调?.invoke(binding.viewModel.highlight,adapterPosition)
}
}
}
fun getSelected()=selectedRow
}
布局文件:


我认为问题在于启用行notifyDataSetChanged()。它会刷新整个数据集,从而导致列表的翻转。请尝试此操作

fun enableRow(index: Int) {
//Clear previous selection (only if we want single selection)
selectedRow.clear()
//Select specified row
selectedRow.add(index)
//Let the adapter redraw
notifyItemRangeChanged(index,highlights.size())
}

我认为问题出在enable row notifyDataSetChanged()中。它刷新整个数据集,从而导致列表的翻转。请尝试此操作

fun enableRow(index: Int) {
//Clear previous selection (only if we want single selection)
selectedRow.clear()
//Select specified row
selectedRow.add(index)
//Let the adapter redraw
notifyItemRangeChanged(index,highlights.size())
}

发布一些代码。发布你的适配器代码完成,不确定是否有帮助。发布一些代码。发布你的适配器代码完成,不确定是否有帮助。好吧,这似乎以某种方式解决了问题,但问题是我确实需要更新所有行,因为我只想选择一行(选择意味着用户界面与所选行不同),我无法清楚地理解,但是,如果您觉得这有助于您对答案进行投票,请再次投票。notifyDataSetChanged()和notifyItemRangeChanged()非常相似,这会刷新数据列表。我的意思是,列表中选定的项目会以不同的颜色显示。因此,每次选择(并滚动到)新事件时,其他项目都需要刷新,以便显示为未选择。如果我照你说的做,我只会刷新从所选项目开始的一系列项目,从而使以前选择的项目保持选中状态。你听说过稀疏布尔数组吗?维护布尔数组。每当你单击某个位置时,在布尔数组中将该位置存储为true,然后用数组中的位置检查绑定持有者的位置。没关系,让它工作起来了,谢谢@Anonymous找到问题。这似乎以某种方式解决了问题,但问题是我确实需要更新所有行,因为我只想选择一行(选择意味着所选行的UI不同),我无法清楚地告诉你,但是,如果您觉得这有助于您对答案进行投票,请再次投票。notifyDataSetChanged()和notifyItemRangeChanged()非常相似,这会刷新数据列表。我的意思是,列表中选定的项目会以不同的颜色显示。因此,每次选择(并滚动到)新事件时,其他项目都需要刷新,以便显示为未选择。如果我照你说的做,我只会刷新从所选项目开始的一系列项目,从而使以前选择的项目保持选中状态。你听说过稀疏布尔数组吗?维护布尔数组。每当你单击某个位置时,在布尔数组中将该位置存储为true,然后用数组中的位置检查绑定持有者的位置。没关系,让它工作起来了,谢谢@Anonymous找到问题