文本溢出截断是一个比较常见的场景,如新闻列表页、微博列表、商品列表等,溢出截断主要是为了保证界面的整齐。在《​​前端开发需要知道的 10 个 CSS 技巧​​》中有提到过多行文本溢出的处理,本文总结一些优雅的处理文本溢出截断的方法。

先来看一段html,如下:

<div class="block">
<div class="block-content">
<p>卡耐基对微笑有这样的描述:“它在家中产生,他不能买,不能求,不能借,不能偷,因为在人们得到它之前,对谁都是无用的东西,他给予后人之后,会使你得到别人的好感,它是疲倦者的休息,希望的阳光,悲哀者的力量,又是大自然免费赋予人们的一种解除苦难的良药。” </p>
</div>
</div>

基础样式如下:

.block {
width: 400px;
background-color: #fff;
border: 3px solid #646464;
}
.block-content {
text-align: justify;
}

优雅的处理文本溢出截断_CSS

希望把内容限制在三行以内,多余的部分已省略号 ​​…​​ 替换,下面就围绕这个需求来展开。

line-clamp

之前有介绍过,使用line-clamp,下面修改样式 ​​.block-content​​ ,如下:

.block-content {
display: -webkit-box;
-webkit-line-clamp: 3;
-webkit-box-orient: vertical;
text-align: justify;
overflow: hidden;
}

现在效果如下:

优雅的处理文本溢出截断_html_02

从效果上来看,是达到了需求,CSS完美的解决了。个人觉得前端开发还需要一点审美,上面的效果看着很难受,文字内容和边框之间没有距离产生压抑感。

接下来尝试增加一些边距,修改样式,如下:

.block-content {
display: -webkit-box;
-webkit-line-clamp: 3;
-webkit-box-orient: vertical;
text-align: justify;
overflow: hidden;
padding: 1.5em;
}

优雅的处理文本溢出截断_5e_03

一行代码,产生了边距,但不符合需求了,是的,填充让 ​​line-clamp​​ 效果显得不那么完美,需要改成下面这样:

.block-content {
display: -webkit-box;
-webkit-line-clamp: 3;
-webkit-box-orient: horizontal;
text-align: justify;
overflow: hidden;
padding: 1.5em 1.5em 0em 1.5em;
margin-bottom: 1.5em;
}

这样都达到预期目的了,效果如下:

优雅的处理文本溢出截断_前端开发_04

在使用 ​​line-clamp​​​ 处理文本溢出截断的时候设置 ​​padding-bottom​​ 需要特别注意

增加淡出效果

这种方案只适合固定高度的文本模块,在上面实现方案的基础上,设置 ​​line-height: 1.6em;​​​,展示3行文本,那么高度就是​​ 4.8em(1.6em × 3)​​​。接下来增加一个​​fade-out​​样式,代码如下:

.fade-out {
position: relative;
height: 4.8em;
}
.fade-out:after {
position: absolute;
width: 50%;
height: 1.6em;
content: "";
text-align: right;
bottom: 0;
right: 0;
background: linear-gradient(
to right,
rgba(255, 255, 255, 0),
rgba(255, 255, 255, 0.9) 50%
);
}

将其增加到 ​​.block-content​​​ 元素上,即 ​​class="block-content fade-out"​​,看到效果如下:

优雅的处理文本溢出截断_前端开发_05

更改溢出省略符

默认的溢出省略符为​​ …​​​,参照上面方案的实现原理,可以将溢出省略符换成希望的内容,示例换成 ​​==>​​​ ,增加样式 ​​.truncation​​ ,代码如下:

.truncation {
position: relative;
max-height: 4.8em;
overflow: hidden;
padding-right: 1rem;
}
.truncation::before {
position: absolute;
content: "==>";
width: 2em;
height: 1.6em;
line-height: 1.2em;
bottom: 0;
right: 1.2em;
z-index: 2;
color: #ff0000;
text-align: center;
}
.truncation::after {
content: "";
position: absolute;
width: 2em;
height: 1.6em;
background: #ffffff;
bottom: 0;
right: 1.2em;
z-index: 1;
}

html 对应结构:

<div class="block">
<div class="block-content truncation">
<p>卡耐基对微笑有这样的描述:“它在家中产生,他不能买,不能求,不能借,不能偷,因为在人们得到它之前,对谁都是无用的东西,他给予后人之后,会使你得到别人的好感,它是疲倦者的休息,希望的阳光,悲哀者的力量,又是大自然免费赋予人们的一种解除苦难的良药。” </p>
</div>
</div>

效果如下:

优雅的处理文本溢出截断_CSS_06

JavaScript方式

使用JavaScript方式实现文本溢出截断需求有很多种方案,这里介绍一种使用 Clamp.js​ 库,兼容大部分浏览器,不足的是需要作用在包含文本的标签上,如本实例就需要传入的对象是​​ .block-content p​​,代码如下:

const blockContent = document.getElementById("block-content-p");
$clamp(blockContent, {
clamp: 3,
useNativeClamp: false,
truncationChar: " ",
truncationHTML: '&nbsp;<strong style="color:#ff0000;font-weight:bold;">==></strong>',
});

效果如下:

优雅的处理文本溢出截断_前端开发_07