Android RecyclerView实现吸顶动态效果,附详细效果图

文章目录

    • 一、ItemDecoration
    • 二、实现RecyclerView吸顶效果
      • 1、实现一个简单的RecyclerView
      • 2、通过ItemDecoration画分割线
      • 3、画出每个分组的组名
      • 4、实现吸顶效果
    • 完整demo

链接:https://download.csdn.net/download/JasonXu94/87786702
202212220944467

一、ItemDecoration

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yinKVw8W-1684338638199)(null)]ItemDecoration 允许应用给具体的
View 添加具体的图画或者 layout 的偏移,对于绘制 View之间的分割线,视觉分组边界等等是非常有用的。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-9tV6bsdW-1684338638181)(null)]当我们调用 addItemDecoration()
方法添加 decoration 的时候,RecyclerView 就会调用该类的 onDraw 方法去绘制分割线,也就是说:分割线是绘制出来的。

RecyclerView.addItemDecoration()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-QbCX4qeB-1684338638228)(null)]RecyclerView.ItemDecoration,该类为抽象类,官方目前只提供了一个实现类
DividerItemDecoration。

public abstract static class ItemDecoration

public class DividerItemDecoration extends RecyclerView.ItemDecoration

里面有3个方法:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-PF6v7Oky-1684338638211)(null)]onDraw():
在提供给RecyclerView的画布上绘制任何适当的装饰。通过此方法绘制的任何内容都将在绘制项目视图之前被绘制,因此将出现在视图的下方。

public void onDraw(Canvas c, RecyclerView parent, State state) {
            onDraw(c, parent);
        }

绘制效果

image-20230516164805173

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-oI7eqZd6-1684338638249)(null)]onDrawOver():在提供给RecyclerView的画布上绘制任何适当的装饰。通过这种方法绘制的任何内容都将在项目视图被绘制之后被绘制,因此将出现在视图上方。

public void onDrawOver(Canvas c, RecyclerView parent, State state) {
            onDrawOver(c, parent);
        }

绘制效果

image-20230516164822315

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-sDcBvRbp-1684338638239)(null)]getItemOffsets():检索给定项的任何偏移量。outRect的每个字段指定项目视图应该插入的像素数,类似于padding或margin。默认实现将outRect的界限设置为0,并返回。

public void getItemOffsets(Rect outRect, View view, RecyclerView parent, State state) {
            getItemOffsets(outRect, ((LayoutParams)view.getLayoutParams()).getViewLayoutPosition(),
                    parent);
        }

二、实现RecyclerView吸顶效果

1、实现一个简单的RecyclerView

下面这个RecyclerView的实现细节略。

image-20230516164844439

2、通过ItemDecoration画分割线

自定义ItemDecoration。

创建 fruitDecotion 类 继承 ItemDecoration,并实现onDraw、onDrawover、getItemOffsets三个方法。

RecyclerView调用自定义的fruitDecoration

RecyclerView.addItemDecoration(new fruitDecoration(this))

在getItemOffsets画分割线,当是组名时,预留更大的空间(即分割线的height比普通分割线大)。

@Override
    public void getItemOffsets(@NonNull Rect outRect, @NonNull View view, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) {
        super.getItemOffsets(outRect, view, parent, state);
        if (parent.getAdapter() instanceof fruitAdapter){
            // parent.getAdapter()获取到当前RecyclerView的Adapter
            fruitAdapter adapter = (fruitAdapter) parent.getAdapter();
            // 获取当前view的位置
            int position = parent.getChildLayoutPosition(view);
            if (adapter.isGroupHeader(position)) {
                // 如果是头部,则预留更大的地方
                outRect.set(0, groupHeaderHeight, 0, 0);
            }else {
                outRect.set(0, 4, 0, 0);
            }
        }

实现效果

2022122209445211

3、画出每个分组的组名

当是组名时,在较大分割线哪里画出组名。在onDraw()方法里实现

@Override
    public void onDraw(@NonNull Canvas c, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) {
        super.onDraw(c, parent, state);
        if (parent.getAdapter() instanceof fruitAdapter) {
            fruitAdapter adapter = (fruitAdapter) parent.getAdapter();
            //当前屏幕中item的个数
            int count = parent.getChildCount();
            // 获取当前RecyclerView距离屏幕左边的padding
            int left = parent.getPaddingLeft();
            // right == RecyclerView的宽度 - RecyclerView的右padding
            int right = parent.getWidth() - parent.getPaddingRight();
            for (int i = 0; i < count; i++) {
                //获取对应 i 的 view
                View view = parent.getChildAt(i);
                // 获取 i 的 view 的布局位置
                int position = parent.getChildLayoutPosition(view);
                // 判断是否是头部
                boolean isGroupHeader = adapter.isGroupHeader(position);
                // i 的 view 是头部并且 当前view的top位置距离屏幕的顶部还有距离
                if(isGroupHeader && view.getTop() - groupHeaderHeight - parent.getPaddingTop() >=0) {
                    c.drawRect(left, view.getTop() - groupHeaderHeight, right, view.getTop(), headPaint);
                    String groupName = adapter.getGroupName(position);
                    textPaint.getTextBounds(groupName, 0, groupName.length(), textRect);
                    c.drawText(groupName, left + 20, view.getTop() - groupHeaderHeight / 2f + textRect.height() / 2f, textPaint);
                }else if(view.getTop() - groupHeaderHeight - parent.getPaddingTop() >=0){
                    //分割线
                    c.drawRect(left, view.getTop() - 4, right, view.getTop(), headPaint);
                }
            }
       }
    }

实现效果

image-20230516164935046

4、实现吸顶效果

因为onDrawOver方法是在itemView画了之后才画,所以组名的吸顶是写在onDrawOver方法里。需要注意的时,当我们的第二个组名到顶部的时候,要把当前顶部的组名给替换掉。

 @Override
    public void onDrawOver(@NonNull Canvas c, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) {
        super.onDrawOver(c, parent, state);
        if (parent.getAdapter() instanceof fruitAdapter) {
            fruitAdapter adapter = (fruitAdapter) parent.getAdapter();
            //TODO 返回可见区域内的第一个item的position
            int position =((LinearLayoutManager) parent.getLayoutManager()).findFirstVisibleItemPosition();
            // 获取第一个item的view
            View itemView = parent.findViewHolderForAdapterPosition(position).itemView;
            int left = parent.getPaddingLeft();
            int right = parent.getWidth() - parent.getPaddingRight();
            int top = parent.getPaddingTop();
            //TODO 当第二个是头部时,
            boolean isGroupHeader = adapter.isGroupHeader(position + 1);
            if (isGroupHeader) {
                int bottom = Math.min(groupHeaderHeight, itemView.getBottom() - parent.getPaddingTop());
                c.drawRect(left, top, right, top + bottom, headPaint);
                String groupName = adapter.getGroupName(position);
                textPaint.getTextBounds(groupName, 0, groupName.length(), textRect);
                c.drawText(groupName, left + 20, top + bottom - groupHeaderHeight / 2f
                        + textRect.height() / 2f, textPaint);
            }else { // 如果不是头部, 即普通的itemView,则当前的头部一直固定在顶部
                c.drawRect(left, top, right, top + groupHeaderHeight, headPaint);;
                String groupName = adapter.getGroupName(position);
                textPaint.getTextBounds(groupName, 0, groupName.length(), textRect);
                c.drawText(groupName, left + 20, top + groupHeaderHeight / 2f
                        + textRect.height() / 2f, textPaint);
            }
        }
    }

实现效果

image-20230516164951564

完整demo

链接:https://download.csdn.net/download/JasonXu94/87786702

到此这篇关于Android RecyclerView实现吸顶动态效果流程分析的文章就介绍到这了

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/21478.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

猜谜游戏、彩云词典爬虫、SOCKS5代理的 Go(Golang) 小实践,附带全代码解释

猜谜游戏在编程语言实践都已经和 HelloWord 程序成为必不可少的新手实践环节&#xff0c;毕竟&#xff0c;它能够让我们基本熟悉 for 循环、变量定义、打印、if else 语句等等的使用&#xff0c;当我们基本熟悉该语言基础之后&#xff0c;就要学会其优势方面的程序实践&#xf…

软考算法-算法篇

软考算法 一&#xff1a;故事背景二&#xff1a;分治法2.1 概念2.2 题目描述2.3 代码实现2.4 总结提升 三&#xff1a;回溯法3.1 概念3.2 题目描述3.3 代码实现3.3.1 TreeNode 类3.3.2 将数组处理成二叉树结构并且返回根节点3.3.3 进行搜索 3.4 总结提升 四&#xff1a;回溯法-…

头歌计算机组成原理实验—运算器设计(7) 第7关:6位有符号补码阵列乘法器

第7关&#xff1a;6位有符号补码阵列乘法器 实验目的 帮助学生掌握补码阵列乘法器的实现原理。 视频讲解 实验内容 在 Logisim 中打开 alu.circ 文件&#xff0c;在6位补码阵列乘法器中利用5位阵列乘法器以及求补器等部件实现补码阵列乘法器&#xff0c;实验框架如图所示&a…

【Linux】进程信号

目录 一、信号概念 二、信号捕捉预备知识 三、产生信号 1、通过终端按键 Core Dump 概念 Core Dump 用法 2、系统调用 2.1、kill 2.2、raise 2.3、abort 3、软件条件 4、硬件异常 4.1、除0 4.2、野指针 四、保存信号 1、信号其他相关概念 2、内核中的表示 3、…

【全网首测】5G随身Wi-Fi —— 中兴U50 Pro

说到随身Wi-Fi&#xff0c;大家应该都不陌生。 它是一个专门将移动信号转换成Wi-Fi信号的设备&#xff0c;经常被用于旅行和出差场景&#xff0c;也被人们亲切地称为“上网宝”。 现在&#xff0c;我们已经全面进入了5G时代&#xff0c;随身Wi-Fi也升级迭代&#xff0c;出现了支…

一个有趣的avs编码器(注意,是avs,而不是avs2噢)

本章附件是一个清华大学写的关于avs编解码器: https://download.csdn.net/download/weixin_43360707/87793302 该编码器遵循了stuffing bit: 打开文件夹后&#xff0c;如下&#xff1a; 可以看出这个是个跨平台的工程&#xff0c;提供了windows vs2015的工程文件sln&#x…

【最新可用】chatGPT镜像网站国内使用,免费稳定!

新建了一个网站 https://ai.weoknow.com/ 每天给大家更新可用的国内可用chatGPT 2023.5.8新增一个 ChatGPT 国内免翻版 【网站名称】&#xff1a;Chat GPT Ai 【使用环境】&#xff1a;移动端/电脑网页端 ChatGPT是一款功能强大的免费在线聊天机器人&#xff0c;具有人工智能…

网络编程(TCP与UDP协议)

文章目录 1. 网络编程1.1 软件架构1.2 网络基础 2. 网络通信要素2.1 如何实现网络中的主机互相通信2.2 通信要素一&#xff1a;IP地址和域名2.2.1 IP地址2.2.2 域名 2.3 通信要素二&#xff1a;端口号2.4 通信要素三&#xff1a;网络通信协议 3. 传输层协议&#xff1a;TCP与UD…

机器人工程学习和研究的结构性失衡

结论&#xff1a;无解&#xff0c;谁是那屈指可数的幸运者/(ㄒoㄒ)/~~ 供给&#xff1a;培养的机器人工程专业人才 需求&#xff1a;市场企业主体招聘的相关人才 不匹配&#xff0c;错配&#xff0c;导致供给无效。 机器人工程学习和研究的结构性失衡可能是由多种原因导致的…

Qt6之万能数据类型QVariant详解

QVariant&#xff0c;被称为万能数据类型&#xff0c;实际上它是类似C的联合union类型。简单的说自定义性能强就像一个盒子几乎可以让你放任意的qt类型&#xff0c;同时可以轻松构造任意类型的任意复杂数据结构&#xff0c;但请注意复杂类型意味着性能和效率的让步。 qt6在文档…

自然语言处理与其Mix-up数据增强方法报告

自然语言处理与其Mix-up数据增强方法 1绪论1.课题背景与意义1.2国内外研究现状 2 自然语言经典知识简介2.1 贝叶斯算法2.2 最大熵模型2.3神经网络模型 3 Data Augmentation for Neural Machine Translation with Mix-up3.1 数据增强3.2 对于神经机器翻译的软上下文的数据增强3.…

2023年市场规模将超147亿美元,中国人工智能产业的“风口”来了吗?

2023年IDC中国ICT市场趋势论坛于5月10日召开&#xff0c;会议重点探讨了人工智能、工业互联网、网络安全、大数据、云计算等领域&#xff0c;并强调了智能终端、智慧城市和半导体等行业的前景。 IDC预计&#xff0c;中国人工智能市场规模在2023年将超过147亿美元&#xff0c;到…

springboot+jsp高校社交校友交流平台的设计与实现

在学校里我们结识了很多朋友。当我们毕业离校走上各自的人生道路&#xff0c;这份友谊将成为宝贵的人生精神财富。但世事变迁&#xff0c;或许我们原本留下的联系方式已经不能再用&#xff0c;使得朋友之间失去联系&#xff0c;更别提相聚&#xff0c;这份精神财富也将丢失。这…

python字典

和列表相同&#xff0c;字典也是许多数据的集合&#xff0c;属于可变序列类型。不同之处在于&#xff0c;它是无序的可变序列&#xff0c;其保存的内容是以“键值对”的形式存放的。 字典类型是Python中唯一的映射类型。“映射”是数学中的术语&#xff0c;简单理解&#xff0…

点亮未来明灯,引领绿色革命

随着全球气候变化日趋严重&#xff0c;能源转型成为解决气候问题和提高全球能源安全合理性的必要措施之一。可持续能源技术因其对环境的友好性和可再生性而成为了当前热点话题。可持续能源技术已经成为人们日益关注的焦点。这项技术可以帮助我们减少对化石燃料的依赖&#xff0…

机械大专生能学会云计算吗,完全零基础的

机械大专生能学会云计算吗&#xff0c;完全零基础的 正常来说&#xff0c;大专及以上学历都能学会云计算&#xff0c;但是会和满足就业需求是两回事哈。如果你想通过学习就业&#xff0c;就需要根据当下相关岗位的普遍技术需求以及其他方面的要求&#xff0c;来针对性的学习和提…

chatgpt赋能Python-pythondoc

PythonDoc&#xff1a;了解Python的文档工具 什么是PythonDoc&#xff1f; PythonDoc是Python官方文档。它是Python编程语言的权威指南和参考资料&#xff0c;提供丰富而全面的信息&#xff0c;从基础语法到高级主题&#xff0c;都有许多实用和详细的文档说明。 PythonDoc的…

【重新定义matlab强大系列七】利用matlab函数ischange查找数据变化点

&#x1f517; 运行环境&#xff1a;matlab &#x1f6a9; 撰写作者&#xff1a;左手の明天 &#x1f947; 精选专栏&#xff1a;《python》 &#x1f525; 推荐专栏&#xff1a;《算法研究》 #### 防伪水印——左手の明天 #### &#x1f497; 大家好&#x1f917;&#x1f91…

水电站泄洪监测预警系统解决方案

一、方案背景 每到汛期水库或电站泄洪时&#xff0c;下游各责任单位接到泄洪通知后&#xff0c;组织人员对下游河道进行巡查&#xff0c;耗费大量的人力物力&#xff0c;且信息传递效果不明显。巡查办法老套单一&#xff0c;信息传递速度慢、覆盖范围小&#xff0c; 无法让沿途…

oa是什么意思?oa系统哪个好用?

一、oa是什么意思 oa&#xff08;Office Automation办公自动化&#xff09;是一种将智能化科技应用于企业管理中的应用系统。它可以通过电脑网络、互联网等技术手段&#xff0c;将企业的各种业务流程、各种业务数据进行集成和处理&#xff0c;将各种业务流程和各种业务数据统一…