开箱即用的文本折叠
写追剧感想的时候顺手捣鼓出来的长文折叠,代码很简单,基本上直接复制就能用。外加我的脑子还是处在不停 storm 的状态中,所以还是更新一些不太需要动脑子组织语言的内容……
ʚ ⸸ ɞ
先来看效果:
Mercy is hybris, charity is sacrilege.
慈悲即傲慢,救济乃渎神。⸺五十五 孁(我说的)
虽然只测试了纯文本,不过理论上任意元素都是能正常工作的,只是排版和动画上可能会出现一点小瑕疵,但是 CSS 代码没什么泛用性所以大家就各扫门前雪……【喂
文本部分
为了保持代码简洁易懂所以文本输入的方式稍微有一点复杂,格式大概如下:
<div class="hidden-post">
折叠提示:
折叠正文折叠正文折叠正文折叠正文
</div>
如果嫌 hidden-post
太长了可以自己改一个好打的,但我建议用输入法做一个快捷输入。
另外代码的设计思路是「用 div
中的第一个 <p>
子元素作为折叠提示」,所以代码里的每一个换行都不可以省略噢【为什么出现了迷之幼师语气……
JS 部分
注:本代码需依赖 jQuery 运行。
$('.hidden-post').each(function() {
// 如果之前改了 class 这里也要做相应修改
let $div = $(this);
let $hint = $div.children('p:first-child');
let $hiddenP = $div.children(':not(p:first-child)');
$hiddenP.hide();
$hint.on('click', function() {
$hiddenP.slideToggle().toggleClass("active");
// 如果不需要透明渐变的话可以去掉 `.toggleClass()`
$(this).toggleClass("active-hint");
// 如果不需要提示按钮可以直接删掉这一行
});
});
直接复制就可以开箱即用了!如果要添加提示按钮小箭头的话需要再添加一些 CSS。
CSS 部分
在 css 里额外添加的东西:折叠正文的透明度渐变,折叠提示的指示按钮。
这是透明度渐变的代码:
.hidden-post p {
transition: opacity 0.5s;
opacity: 0;
}
.hidden-post p.active,
.hidden-post p:first-child {
opacity: 1;
}
这是提示按钮的代码:
.hidden-post p:first-child::after {
content: '▶';
// 也可以用「展开」
cursor: pointer;
// 使鼠标经过按钮时显示为超链接样式,但其实点击整行字都能触发
background: #000a;
color: #fff;
transition: all .5s;
}
.hidden-post p:hover::after {
background: #000;
}
.hidden-post p.active-hint::after {
content: '▼'
// 也可以用「折叠」
}
所以就是这样完成了……诶居然才写了 500 字吗不管了【
小 bug 调整
昨天更新完之后突然发现展开和收起的动画会有一个小小的卡顿,像这样:
这是会卡的:
前面的那个不会卡
测试后发现是一个非常玄学的 bug……
首先 blog 的 <p>
样式是上下各 margin 1em,两个连续的 <p>
元素之间理论上会间隔 2em,但浏览器会自动把两个 margin 部分重叠,于是最终显示的间隔还是 1em。
折叠提示和后续的正常文本之间也存在这种重叠关系,但是当折叠文本播放展开动画的时候,「折叠提示」和「后续文本」之间就会出现一个新的 <p>
元素,而动画刚开始播放的时候这个 <p>
元素的高度为 0,所以看起来就会像两个文本之间突然多了 1em 的间距。
大概感觉就是这样:
【点击前】折叠提示
后续文本
【点击后】折叠提示
后续文本
解决的方法非常简单,只要把 hidden-post
后续紧跟着的 <p>
元素的 margin-top
设置为 0,浏览器就不会再自动处理重叠了。
.hidden-post + p {
margin-top: 0;
}