源码-trigger
逛b站的时候,偶然发现一个有意思的动画效果库,展示的效果如下
于是研究了下它的源码,具体的工作流程是将视口划分成指定的块,比如使用指令tg-from:1 tg-to:10
那就是将视口划分成10份,在对应的dom上设置哪个区间(tg-filter
)去出发什么样的效果(tg-map
),就涉及到怎么去定位dom到了哪个区间,分析下dom在屏幕中的运动过程
将已经运动的距离/ 整个运动距离,就可以得出一个百分比,将这个百分比再去✖️设定的运动长度((tg-to) - (tg-from) + 1
),就可以得到dom运动到了哪个块,最后去设置你想要设置的css属性就可以了,这只是一个很粗略的过程,具体的实现比我说的复杂的多,比如要去解析不同的指令,比如tg-name tg-map tg-filter
、将指令转化成css属性等等。
// edge is 'cover' by default
let percentage = // 计算百分比
edge === 'cover'
? Math.min(
Math.max( // scrolled: clientHeight:可见区域的高度 针对整个文档 top height 针对当前的元素
// 不是实时的获取 top 的值,所以需要加上 scrolled,如果改成实时获取了?
(scrolled + clientHeight - top) / (clientHeight + height),
0
),
1
)
: Math.min(Math.max((scrolled - top) / (height - clientHeight), 0), 1);
// Calculation result value of bezier
percentage = bezier ? ease(bezier, percentage) : percentage;
let value: string | number;
const mappingValue = (
from +
Math.floor((segments + 1) * percentage) * increment * multiplier
).toFixed(decimals); // 会有存在小数的情况 (to - from) / steps 小数
// 这里实际上可以看成将视口分成 from - to 的间隔,(to - from )+ 1) * percentage, 在向下取正
value = +mappingValue;
if (filter.values.length > 0 && !filter.values.includes(value)) {
// If the mode is 'exact', remove the CSS property
// Setting the lastValue to null to ensure correct comparison below
if (filter.mode === 'exact') {
element.lastValue = null;
el.style.removeProperty(name);
}
return;
}
if (typeof mapping[value] !== 'undefined') {
value = mapping[value];
}
## 我学到的
1. 私有属性的写法: –selfProperty
2. 以前想到是不是可以在css里面去使用动态变量,在这个库里面看到使用 var
实现,动态改变私有属性,将私有属性的值赋予对应的 css属性