浅谈移动端过长文本溢出显示省略号的实现方案

简介: 本文通过图文并茂的方式,由浅入深地讲述了多种文本过长场景下显示省略号的背景和解决方案。

本文首发于 vivo互联网技术 微信公众号 
链接: https://mp.weixin.qq.com/s/39NCyZvm8EYiJ-pEEtjxGw
作者:何彦军

目前在移动端开发的展示界面中,如果一段文本的数量过长,受限于屏幕的宽高等因素,有可能不能完全显示,这个时候就会把溢出的文本显示成省略号。

最近就亲身经历了一系列类似的需求,于是这里做个总结和记录。

首先一个最基本的需求就是当文本超过一行最大宽度时,超出的部分变为省略号,如下图所示。

这个功能比较基础,只用css就可以实现,如下图所示代码块。

可是有时候产品同学希望显示的文本可以再多一点,于是就有了多行文本溢出显示省略号的需求,如下图所示。

这个功能也可以通过css实现,如下图代码块所示。

这里用到了webkit的css扩展属性,因此适用于webkit浏览器及移动端,并且在兼容性方面也有些影响,但是只要不是特别老旧的机器,还是完全能够支持的。

在支持了多行文本溢出显示省略号的功能之后,产品同学又发现了体验不友好的点,如下图所示。文本在第二行开头处就结束了,这就导致第二行大部分是空白的,影响了美观度。

因此,产品同学提出了一个新需求:

  • 当文本没有超过第x行的一半时,则按第x-1行溢出显示省略号的方式展示;(第1行除外)

  • 当文本超过第x行的一半但没有超过第x行时,则正常展示;

  • 当文本超过第x行时,则按第x行溢出显示省略号的方式展示。

这就需要计算出文本实际占用的宽度才能选择采用哪种展示方式。

查找资料得知,canvas提供了一个measureText的方法,该方法的返回包含一个对象,这个对象里包含了以像素计的指定字体宽度。

如果需要在文本显示之前,就了解文本的宽度,那么可以使用该方法。

上面的代码显示效果如下:

于是可以基于canvas能力来实现这个功能,大概的流程图如下图所示。

这里最关键的是要计算出每一行可以显示多少文本,利用canvas的measureText方法,可以达到这个效果,伪代码如下所示。

虽然canvas可以计算出文本显示的宽度,并且兼容性和性能都还不错,但是当某一行末尾出现特殊符号或者是英文单词时,就会出现预期外的情况。

浏览器实际渲染出来的时候,如果末尾有特殊符号时会连同前面的字符一起换行,而如果末尾有英文单词时也会将这个英文单词换行展示。

但通过canvas计算出来的结果,会导致每一行的文本增多了,从而跟预期的展示效果有出入。

因此,这种方案只能适用于文本中不包含特殊符号和英文单词的场景。

一段时间后,产品同学感觉展示那么一段文本有点儿单调,于是又提出了一个进阶版的需求:

  • 文本的首行开头需要缩进或者可以配置一个图标;

  • 文本的末尾可以配置按钮或者图标,并且如果文本超过了范围需要显示省略号,但是省略号需要在按钮或图标的前面。

顺带给出了一个参考示例,如下图所示。

由于之前没有遇到过类似的需求,于是开始google这个问题,经过海量的检索,终于发现了该问题实现的方案。

原来网上也有很多朋友遇到了这样的需求,并专门写了单独的组件来使用,比如:

HeyUI:https://www.heyui.top/component/other/textellipsis

vue-text-ellipsis:https://github.com/Luobata/vue-text-ellipsis

它们的思路都是通过最终展示的实际高度是否超过预期的容器高度来判断是否需要删减文本。其流程图大概如下图所示。

就这样,通过现成的组件就解决了一个难题。

然鹅,本以为需求已经告一段落了,哪知产品同学又开始了体验上的深度挖掘。

她们认为,展示的文本样式不应该都是一样的。

有些文本表达的意思可能比较重要,这就需要重点引起用户的注意。

而有些文本表达的意思可能重要程度一般,这就不需要用户注意。

于是乎她们又提出了一个通过高亮文本来提升用户体验的需求:

  • 能够根据文本的标记进行高亮展示

比方说,获取到下面一段文本,它要显示出入下图所示的那样高亮效果。

由于文本高亮需要通过标签将文本包裹起来并添加高亮样式才能实现,而之前的组件是通过v-text的方式实现的,因此这里不能直接使用,需要将组件改造成v-html的方式插入才可以。

假如通过v-html插入文本,并且设置了em标签的样式,那么就会有一个问题,组件是通过循环剔除最后一个字符直到实际高度小于容器高度来实现展示功能的,这就有可能截掉标签字符,导致最后的展示有异常。

所以,在截取文本的时候还需要做一些处理,流程图如下图所示。

到这里,已经实现文本的一种高亮形式了,但是假如有好几个部分的文本需要高亮且高亮的样式还各不相同,这又要怎么解决呢?

一种思路是,通过几种不同名称的标签分别包裹需要高亮的文本,每一种标签会对应一种高亮样式,这样的话,在获得源文本后,首先通过词法分析将源文本中的标签解析出来,后面的流程就跟上图步骤1后面的流程类似了。

目录
相关文章
|
应用服务中间件 Linux nginx
【Linux环境】centOS 7安装nginx详细步骤及nginx配置
【Linux环境】centOS 7安装nginx详细步骤及nginx配置
3055 0
|
应用服务中间件 Linux 网络安全
Linux 安装 Nginx 并配置为系统服务(超详细)
Linux 安装 Nginx 并配置为系统服务(超详细)
|
5月前
Multisim14.0中文下载安装步骤教程
Multisim14.0是由美国NI公司开发的EDA工具,适用于电路设计与仿真。本文提供详细中文安装步骤:下载安装包后解压,运行安装程序并设置路径,填写用户信息,选择安装位置,接受协议完成安装。随后安装NILicense激活器及中文语言包,最终实现软件汉化与正常运行。附带网盘下载链接,方便国内用户获取资源。
1918 15
Vue3分页(Pagination)
这是一个高度可定制的分页组件,支持通过属性设置当前页数、每页条数、数据总数等,并提供了禁用分页、隐藏单页分页、快速跳转等功能。此外,还可以自定义分页的位置、显示的数据条数选项及数据总数的显示格式。组件内置了对多种场景的支持,如禁用状态下的分页操作、不同位置的分页显示等,适用于多种应用界面需求。在线预览展示了各种配置项的效果。
354 1
Vue3分页(Pagination)
|
11月前
Uniapp矩阵评分组件
Uniapp矩阵评分组件
142 2
|
JavaScript 前端开发
我为展开收起功能做了动画,被老板称赞!
【8月更文挑战第23天】我为展开收起功能做了动画,被老板称赞!
397 1
我为展开收起功能做了动画,被老板称赞!
|
图形学 开发者
U3D开发进阶:精细调整Collider与优化碰撞检测性能
【7月更文第11天】在Unity 3D(简称U3D)开发过程中,精确控制Collider(碰撞器)的设置与合理利用Layer Collision Matrix(层级碰撞矩阵)对于提升游戏性能、优化物理模拟至关重要。本文将深入探讨这两项技术的应用,通过实际案例和代码示例,帮助开发者构建更加高效、流畅的游戏体验。
1704 2
UE虚幻引擎 UTextBlock UMG文本控件超过边界区域以后显示省略号
UE虚幻引擎 UTextBlock UMG文本控件超过边界区域以后显示省略号
394 0
echarts 热力图(中国地图版)
echarts 热力图(中国地图版)
891 0
|
SQL 存储 分布式计算
DataWorks产品使用合集之在DataWorks中调用存储过程(PROCEDURE)如何解决
DataWorks作为一站式的数据开发与治理平台,提供了从数据采集、清洗、开发、调度、服务化、质量监控到安全管理的全套解决方案,帮助企业构建高效、规范、安全的大数据处理体系。以下是对DataWorks产品使用合集的概述,涵盖数据处理的各个环节。
395 0