1.ResizeObserver
监听element边界、尺寸变化
observer(el) {
const cd = (entries) => {
console.log('监控对象尺寸变化:', entries)
}
const observer = new ResizeObserver(cd);
observer.observe(el);
this.observeCfg = observer;
}
2.transform translateX()
更改元素位置,且不会导致reflow,性能好,优于直接设置left/right/margin
transform: translateX(42px);
3.element.getBoundingClientRect()
返回一个对象,包含元素大小和相对于视窗的位置
const elementRect = elem.getBoundingClientRect(element);
// elementRect拥有属性
elementRect.x // 元素到视窗左侧距离
elementRect.y // 元素到视窗右侧距离
elementRect.width // 元素宽度
elementRect.height // 元素高度
elementRect.top // 元素到视窗上侧距离
elementRect.right // 元素到视窗右侧距离
elementRect.bottom // 元素到视窗下侧距离
elementRect.left // 元素到视窗左侧距离
4.element.offsetWidth/element.offsetHeight等
element.offsetWidth // 元素自身可视宽度加上左右 border 的宽度
element.offsetHeight // 元素自身可视高度加上上下 border 的宽度
element.offsetLeft // 元素自己 border 左边距离父元素 border 左边或者 body 元素 border 左边的距离
element.offsetTop // 元素自己 border 顶部距离父元素顶部或者 body 元素 border 顶部的距离
element.style // 获取/设置元素的 style 属性
5.transition: all 0.2s ease
为元素的一个或多个样式的变化设置过渡效果
transition: all 0.2s ease // 所有样式变化 0.2s过渡效果,ease是先快后慢
transition: margin-left 0.2s linear // margin-left变化时0.2s过渡效果,linear是线性变化
6.background: linear-gradient()
设置背景色渐变
background: linear-gradient(to right, black, black 30%, white 30%, white 100%); // 设置背景色从左向右线性变化,black 30%代表30%的位置是黑色,根据节点渐进变化颜色
7.element.scrollIntoView
滚动元素的祖先容器,使得被调用该方法的元素对用户可见(即页面滚动到元素位置)
element.scrollIntoView({
behavior: 'smooth', // 定义滚动是立即的(instant)还是平滑的(mooth)动画
inline: 'nearest', // 定义元素在可滚动祖先容器内的水平对齐方式,start/center/end/nearest
block: 'start' // 定义元素在可滚动祖先容器内的垂直对齐方式,start/center/end/nearest
})
8.文字最多三行,超过后加展开按钮
这里使用vue写的
<template>
<div class="box-wrapper">
<div ref="textBox" class="box" :class="{ 'ellipsis-box': folded }">
<span class="folded-btn" @click="folded = !folded" v-if="isOver">
<span v-if="folded">展开<i class="el-icon-arrow-down"></i></span>
<span v-else>收起<i class="el-icon-arrow-up"></i></span>
</span>
<span ref="spanBox" class="text">{{ text }}</span>
</div>
</div>
</template>
<script>
export default {
props: {
text: {
default: '',
type: String
},
},
data() {
return {
isOver: false, // 文本是否超出三行,默认否
folded: true, // 文本是否收起状态,默认收起
}
},
mounted() {
this.isOver = this.$refs.spanBox.offsetHeight > this.$refs.textBox.offsetHeight
}
}
</script>
<style lang="scss" scoped>
.box-wrapper {
display: flex;
}
.box {
position: relative;
&::before {
content: '';
float: right;
width: 0;
height: calc(100% - 20px);
}
}
.ellipsis-box {
overflow: hidden;
text-overflow: ellipsis;
-webkit-line-clamp: 3;
display: -webkit-box;
-webkit-box-orient: vertical;
}
.text {
font-family: PingFangSC, PingFang SC;
font-weight: 400;
font-size: 12px;
color: var(--agent-text5-color);;
line-height: 20px;
text-align: left;
font-style: normal;
}
.folded-btn {
font-weight: 500;
font-size: 12px;
line-height: 20px;
color: #DC573C;
float: right;
clear: both;
}
</style>
9.随鼠标移动的tooltip
// 挂载tooltip到body
mountTooltip() {
const tooltipDiv = document.createElement('div');
tooltipDiv.id = 'progress-chapter-tooltip';
tooltipDiv.style = `
position: absolute;
top: 0;
left: 0;
opacity: 0;
min-width: 10px;
border-radius: 4px;
box-shadow: 0px 4px 20px 0px rgba(0,0,0,0.2);
transition: all 0.05s ease;
`
document.body.appendChild(tooltipDiv);
},
// 展示tooltip
showTooltip(text) {
const tooltipDiv = document.getElementById('progress-chapter-tooltip');
if (tooltipDiv) {
tooltipDiv.style.opacity = 1;
tooltipDiv.innerHTML = text
}
},
// 隐藏tooltip
hideTooltip() {
const tooltipDiv = document.getElementById('progress-chapter-tooltip');
if (tooltipDiv) {
tooltipDiv.style.opacity = 0;
}
},
// 鼠标移入展示区域时,调用展示函数showTooltip,这里用了节流控制触发频率
handleMouseMEWithTooltip: throttle(
function(type, e) {
const tooltip = document.getElementById('progress-chapter-tooltip');
const progressBar = this.$refs.progressBar.getBoundingClientRect();
const body = document.body.getBoundingClientRect();
// 微前端框架中,微应用的body到窗口的边缘有一段距离,需要减掉
// transform: translateX()仅改变元素位置不触发重排,性能好
tooltip.style.transform = `translateX(${e.pageX - tooltip.offsetWidth / 2 - body.left}px)`;
tooltip.style.top = progressBar.bottom - body.top + 7 + 'px';
tooltip.style.transitionProperty = type === 'enter' ? 'none' : 'all';
this.showTooltip('tooltip展示文字');
},
50,
{leading: true, trailing: false} // trailing设置false,延迟时间结束后不再触发,防止opacity再次设置为1导致tooltip不隐藏
),
10.js中event对象的offsetX、 clientX、pageX、screenX、 layerX、x之间的区别
developer.aliyun.com/article/637…
11.title属性:鼠标悬停后展示内容
12.vue中vm.$watch()
可以同时监听多个变量
// 键路径
vm.$watch('a.b.c', function (newVal, oldVal) {
// 做点什么
})
vm.$watch(
function () {
// 表达式 `this.a + this.b` 每次得出一个不同的结果时
// 处理函数都会被调用。
// 这就像监听一个未被定义的计算属性
return this.a + this.b
},
function (newVal, oldVal) {
// 做点什么
}
)
// vm.$watch 返回一个取消观察函数,用来停止触发回调:
var unwatch = vm.$watch('a', cb)
// 之后取消观察
unwatch()