当前位置: 首页 > news >正文

信息技术网站建设百度云搜索

信息技术网站建设,百度云搜索,南京企业网站排名优化,做周边的网站效果如上图。 Main Ideas 左右两个列表左列表展示人员数据#xff0c;含有姓氏首字母的 header item右列表是一个全由姓氏首字母组成的索引列表#xff0c;点击某个item#xff0c;展示一个气泡组件(它会自动延时关闭)#xff0c; 左列表滚动并显示与点击的索引列表item … 效果如上图。 Main Ideas 左右两个列表左列表展示人员数据含有姓氏首字母的 header item右列表是一个全由姓氏首字母组成的索引列表点击某个item展示一个气泡组件(它会自动延时关闭) 左列表滚动并显示与点击的索引列表item 相同的 header搜索动作后匹配人员名称中是否包含搜索字符串或搜索字符串为单一字符时是否能匹配到某个首字母而且滚动后左右列表都能滚动至对应 Header 或索引处。 Steps S1. 汉字拼音转换 先找到了 Pinyin4J 这个库后来发现没有对多音字姓氏 的处理之后找到 TinyPinyin 它可以自建字典指明多音汉字(作为姓氏时)的指定读音。 fun initChinaNamesDictMap() {// 增加 多音字 姓氏拼音词典Pinyin.init(Pinyin.newConfig().with(object : PinyinMapDict() {override fun mapping(): MutableMapString, ArrayString {val map hashMapOfString, ArrayString()map[解] arrayOf(XIE)map[单] arrayOf(SHAN)map[仇] arrayOf(QIU)map[区] arrayOf(OU)map[查] arrayOf(ZHA)map[曾] arrayOf(ZENG)map[尉] arrayOf(YU)map[折] arrayOf(SHE)map[盖] arrayOf(GE)map[乐] arrayOf(YUE)map[种] arrayOf(CHONG)map[员] arrayOf(YUN)map[繁] arrayOf(PO)map[句] arrayOf(GOU)map[牟] arrayOf(MU) // mù、móu、mūmap[覃] arrayOf(QIN)map[翟] arrayOf(ZHAI)return map}})) }// Pinyin.toPinyin(char) 方法不使用自定义字典 而使用 Pinyin.toPinyin(nameText.first().toString(), ,).first() // 将 nameText 的首字符转为拼音并取拼音首字母 S2. 数据bean 和 item view 对原有数据bean 增加 属性 data class DriverInfo(var Name: String?, // 人名var isHeader: Boolean, // 是否是 header itemvar headerPinyinText: String? // header item view 的拼音首字母 )左列表的 item view当数据是 header时仅显示 header textView (下图红色的文字)否则仅显示 item textView (下图黑色的文字) 右列表的 item view更简单了就只含一个 TextView 。 S3. 处理数据源 这一步要做的是转拼音拼音排序设置 isHeader、headerPinyinText 属性构建新的数据源集合 … // 返回新的数据源 fun getPinyinHeaderList(list: ListDriverInfo): ListDriverInfo {list.forEachIndexed { index, driverInfo -if (driverInfo.Name.isNullOrEmpty()) returnforEachIndexed// Pinyin.toPinyin(char) 方法不使用自定义字典val header Pinyin.toPinyin(driverInfo.Name!!.first().toString(), ,).first()driverInfo.headerPinyinText header.toString()}// 以拼音首字母排序(list as MutableList).sortBy { it.headerPinyinText }val newer mutableListOfDriverInfo()list.forEachIndexed { index, driverInfo -val newHeader index 0 || driverInfo.headerPinyinText ! list[index - 1].headerPinyinTextif (newHeader) {newer.add(DriverInfo(null, true, driverInfo.headerPinyinText))}newer.add(driverInfo)}return newer }当左侧列表有了数据源之后那右侧的也就可以有了将所有 header item 的 headerPinyinText 取出并转为 新的 集合。 val indexList driverList?.filter { it.isHeader }?.map { it.headerPinyinText ?: } ?: arrayListOf() indexAdapter.updateData(indexList)S4. Adapter 的点击事件 这里省略设置 adapter 、LinearLayoutManager 等 样板代码 … 设定左侧的适配器名为 adapter 右侧字母索引名为 indexAdapter左侧 RV 名为 recyclerView右侧的名为了 rvIndex。 左侧的点击事件不会触发右侧的联动 override fun onItemClick(position: Int, data: DriverInfo) {if (data.isHeader) return// 如果是点击 item 做自己的业务 }右侧点击事件会触发左侧的滚动还可以触发气泡 view 的显示甚至自身的滚动 override fun onItemClick(position: Int, data: DriverInfo) {val item adapter.dataset.first { it.isHeader it.headerPinyinText data }val index adapter.dataset.indexOf(item) // mBind.recyclerView.scrollToPosition(index)(mBind.recyclerView.layoutManager as LinearLayoutManager).scrollToPositionWithOffset(index, 0)// mBind.rvIndex.scrollToPosition(position)val rightIndex indexAdapter.dataset.indexOf(item.headerPinyinText)(mBind.rvIndex.layoutManager as LinearLayoutManager).scrollToPositionWithOffset(rightIndex, 0)showBubbleView(position, data) }一开始用 rv#scrollToPosition()发现也能滚动。但是呢指定 position 之后还有其它内容时且该位置之前也有很多的内容点击后仅将 该位置 item 显示在页面可见项的最后一个位置。 改成 LinearLayoutManager#scrollToPositionWithOffset()后更符合预期。 S5. 气泡 view widget.BubbleViewandroid:idid/bubbleViewandroid:layout_width100dpandroid:layout_height100dpandroid:visibilityinvisibleapp:layout_constraintStart_toStartOfparentapp:layout_constraintTop_toTopOfid/rv_index /设置 文本获取点击的 item view根据 item view 的位置 进行显示设置延迟1秒 隐藏气泡 private fun showBubbleView(position: Int, data: String) {lifecycleScope.launch {mBind.bubbleView.setText(data)val itemView mBind.rvIndex.findViewHolderForAdapterPosition(position)?.itemView ?: returnlaunchmBind.bubbleView.showAtLocation(itemView)delay(1000)mBind.bubbleView.visibility View.GONE} }自定义 气泡 view /*** desc: 指定view左侧显示的气泡view* author: stone* email: aa86799163.com* time: 2024/9/27 18:22*/ class BubbleView(context: Context, attrs: AttributeSet? null) : View(context, attrs) { private val paint Paint(Paint.ANTI_ALIAS_FLAG).apply { color resources.getColor(R.color.syscolor)style Paint.Style.FILL } private val textPaint Paint(Paint.ANTI_ALIAS_FLAG).apply { color Color.WHITE textSize TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 50f, resources.displayMetrics)textAlign Paint.Align.CENTER } private val path Path() private var text: String fun setText(text: String) { this.text text invalidate() } override fun onDraw(canvas: Canvas) { super.onDraw(canvas) // 绘制贝塞尔曲线气泡 path.reset() path.moveTo(width / 2f, height.toFloat()) path.quadTo(width.toFloat(), height.toFloat(), width.toFloat(), height / 2f) path.quadTo(width.toFloat(), 0f, width / 2f, 0f) path.quadTo(0f, 0f, 0f, height / 2f) path.quadTo(0f, height.toFloat(), width / 2f, height.toFloat()) path.close() canvas.drawPath(path, paint) // 绘制文本 canvas.drawText(text, width / 2f, height / 2f textPaint.textSize / 3, textPaint)}fun showAtLocation(view: View) {view.let {val location IntArray(2)it.getLocationOnScreen(location)// 设置气泡的位置x location[0] - width.toFloat() - 10y location[1] - abs(height - it.height) / 2f - getStatusBarHeight()visibility View.VISIBLE}}private fun getStatusBarHeight(): Int {var result 0val resourceId resources.getIdentifier(status_bar_height, dimen, android)if (resourceId 0) {result resources.getDimensionPixelSize(resourceId)}return result} }S6. 搜索实现 空白输入字符时左侧返回全数据源右侧列表跟随左侧变化。有输入时根据全数据源获取 匹配的子数据源右侧列表跟随左侧变化。 fun filterTextToNewHeaderList(list: ListDriverInfo?, text: String): ListDriverInfo? {// 如果item 的拼音和 查询字符 相同或者非 header 时名称包含查询字符val filterList list?.filter { it.headerPinyinText?.equals(text, true) true|| !it.isHeader it.Name?.contains(text, ignoreCase true) true }if (filterList.isNullOrEmpty()) {return null}val newer mutableListOfDriverInfo()filterList.forEachIndexed { index, driverInfo -val newHeader (index 0 || driverInfo.headerPinyinText ! filterList[index - 1].headerPinyinText) !driverInfo.isHeaderif (newHeader) {newer.add(DriverInfo(null, true, driverInfo.headerPinyinText))}newer.add(driverInfo)}return newer }// 搜索点击 mBind.tvSearch.setOnClickListener {val beanList: ListDriverInfo? adapter.filterTextToNewHeaderList(driverList, text)adapter.updateData(beanList)val indexList beanList.filter { it.isHeader }.map { it.headerPinyinText ?: }indexAdapter.updateData(indexList) }整体核心实现都贴出来了如果有什么bug欢迎回复
http://www.hkea.cn/news/14508785/

相关文章:

  • 做教程网站犯法吗优化大师下载安装app
  • 互动型网站长沙网站免费建站
  • 商城网站策划方案视频制作培训机构
  • wordpress仿站js如何导入燕莎做网站
  • 怎么做符合seo的网站免费做app的网站
  • 网站如何做参考文献西电信息化建设网站
  • 天津营销网站建设联系方式nginx 做udp网站
  • 网站开发公司的log互联网设计师前景如何
  • 宿州网站开发宁波建设网站制作
  • 最便宜买机票网站建设长沙装修网站排名
  • 电子商务网站建设收益深圳网站seo设计
  • 网站搭建视频广州优化公司推广
  • 生鲜网站建设的项目总结北京网站设计与建设
  • 长沙优化网站分析网站建设进度总结
  • 锦州网站建设预订wordpress替换谷歌字体插件
  • 做网站的一般步骤自贡企业网站
  • 公司手机网站开发没有影视许可怎么用国内空间做网站
  • 南通网站建设seo网站建设服务器都有哪些
  • 佛山营销型网站建设网站经营方案
  • 怎么建设个人网站 新手学做网站idc数据中心
  • 自助网站推广系统电子商务网站的规划与分析
  • 网站pc端和手机端分离怎么做投诉做网站的电话
  • 精品成品冈站源码免费网站设计书怎么写
  • 好看的网站建设seo权重查询
  • 威海住房和城乡建设局网站萍乡网站seo
  • 软件下载站网站源码免费有什么可以做兼职的正规网站
  • 高埗东莞微信网站建设橙色大气风格网站模板
  • 杭州品牌网站中建一局招聘网
  • 网站谁做的比较好看的优秀设计案例
  • 公司网站招聘费如何做会计分录网站建设文件夹布局