大屏页面需要实现内容超出时列表滚动,没有超出则不滚动,通过一下写法实现,页面滚动在多次加载或者移入移出时抖动明显且内容闪烁
ul.style.transform = `translateY(${offsetY}px)`
所以使用vue-seamless-scroll实现
第一步安装
npm install vue-seamless-scroll --save
第二步页面使用如下
<vue-seamless-scroll
:data="liList"
class="seamless-warp"
:class-option="classOption"
>
<ul style="overflow: hidden" ref="origin_chongzhuang">
<li
v-for="(item, index) in liList"
:key="index"
:title="item.pointName + item.pointValue"
>
<p>{{ item.pointName }}</p>
<p>{{ item.pointValue }}</p>
</li>
</ul>
</vue-seamless-scroll>
import VueSeamlessScroll from "vue-seamless-scroll";
export default {
components: { VueSeamlessScroll },
computed: {
classOption() {
return {
step: 0.4, // 数值越大速度滚动越快
limitMoveNum: 5, // 当数据量小于这个值时,不滚动
hoverStop: true, // 是否开启鼠标悬停stop
direction: 1, // 0向下 1向上 2向左 3向右
openWatch: true, // 开启数据实时监控刷新dom
singleHeight: 0, // 单步运动停止的高度(默认值0是无缝不停止的滚动) direction => 0/1
singleWidth: 0, // 单步运动停止的宽度(默认值0是无缝不停止的滚动) direction => 2/3
waitTime: 1000, // 单步运动停止的时间(默认值1000ms)
};
},
},
}
vue2 element的table组件实现表格自滚动,鼠标移入停止滚动、移出继续滚动、滚动到底部时触发加载更多功能
父组件:
<template>
<!-- 告警信息 -->
<div style="height: 100%">
<generalTables
ref="generalTables"
v-if="loading"
:tableList="tableList"
:columnList="columnList"
@handleScroll="handleScroll"
height="38vh"
></generalTables>
<dv-loading v-else>加载中...</dv-loading>
</div>
</template>
<script>
import { warningInfo } from "@/api/mes/screen";
import generalTables from "../generalTables.vue";
export default {
components: {
generalTables,
},
data() {
return {
loading: false,
tableList: [],
columnList: [
{
label: "名称",
prop: "Name",
},
{
label: "种类",
prop: "Species",
},
{
label: "内容",
prop: "Content",
type: "waring",
},
{
label: "时间",
prop: "Time",
type: "time",
},
],
total: 0,
query: {
pageNum: 1,
pageSize: 10,
},
};
},
created() {
this.loading = false;
this.getWarningInfo();
},
methods: {
getWarningInfo() {
warningInfo(this.query).then((res) => {
this.loading = true;
this.total = res.total;
this.tableList = [...this.tableList, ...res.rows];
});
},
handleScroll() {
if (this.tableList.length < this.total) {
this.query.pageNum++;
this.getWarningInfo();
} else {
this.$refs.generalTables.resetScroll();
}
},
},
};
</script>
<style lang="scss" scoped></style>
子组件:
<template>
<div
class="stripeTable"
@mouseenter="stopAutoScroll"
@mouseleave="startAutoScroll"
>
<el-table
ref="table"
:data="tableList"
:show-header="showHeader"
:height="height"
@scroll.passive="handleScroll"
>
<el-table-column
align="center"
label="序号"
:width="String(innerWidth * 0.03)"
>
<template slot-scope="scope">
<span>{{ scope.$index + 1 }}</span>
</template>
</el-table-column>
<el-table-column
v-for="(item, index) in columnList"
show-overflow-tooltip
align="center"
:key="index"
:prop="item.prop"
:width="item.width ? String(innerWidth * item.width) : item.width"
:label="item.label"
>
<template slot-scope="scope">
<span v-if="item.type == 'time'">{{
scope.row[item.prop]
? parseTime(scope.row[item.prop], "{y}-{m}-{d}")
: "-"
}}</span>
<span v-else-if="item.type == 'dict'">
<dict-tag
:options="dict.type.production_status"
:value="scope.row[item.prop]"
:isTag="true"
/>
</span>
<span
v-else-if="item.type == 'percentage'"
:style="{ color: scope.row[item.prop] ? '#0bffb2' : '#fff' }"
>
{{ scope.row[item.prop] ? scope.row[item.prop] + "%" : "-" }}
</span>
<span
v-else-if="item.type == 'hours'"
:style="{ color: scope.row[item.prop] ? '#0bffb2' : '#fff' }"
>
{{ scope.row[item.prop] || "-" }}
</span>
<span
v-else-if="item.type == 'error'"
:style="{
color: scope.row[item.prop]
? scope.row[item.prop] >= 60
? '#FF7124'
: '#FFAE4A'
: '#fff',
}"
>
{{ scope.row[item.prop] ? scope.row[item.prop] + "%" : "-" }}
</span>
<span v-else>{{ scope.row[item.prop] || "-" }}</span>
</template>
</el-table-column>
</el-table>
</div>
</template>
<script>
import { debounce } from "@/utils";
export default {
dicts: ["production_status"],
props: {
tableList: {
type: Array,
default: () => [],
},
showIndex: {
type: Boolean,
default: true,
},
columnList: {
type: Array,
default: () => [],
},
showHeader: {
type: Boolean,
default: true,
},
height: {
type: String,
default: "18vh",
},
},
data() {
return {
innerWidth: 1920,
scrollInterval: null,
scrollStep: 1, // 滚动步长
scrollSpeed: 100, // 滚动速度(毫秒)
};
},
mounted() {
this.innerWidth = window.innerWidth;
addEventListener("resize", debounce(this.widthScroll, 200));
const scrollBody = this.$refs.table.$el.querySelector(
".el-table__body-wrapper"
);
scrollBody?.addEventListener("scroll", this.handleScroll);
this.startAutoScroll();
},
beforeDestroy() {
this.stopAutoScroll()
const scrollBody = this.$refs.table.$el.querySelector(
".el-table__body-wrapper"
);
scrollBody?.removeEventListener("scroll", this.handleScroll);
window.removeEventListener("resize", this.debouncedWidthScroll); // 移除 resize 事件监听器
},
methods: {
widthScroll() {
this.innerWidth = window.innerWidth;
},
handleScroll(event) {
const { scrollTop, scrollHeight, clientHeight } = event.target;
if (scrollHeight - scrollTop - clientHeight <= 10) {
this.loadMoreData();
}
},
loadMoreData() {
this.$emit("handleScroll");
},
autoScroll() {
const scrollBody = this.$refs.table.$el.querySelector(
".el-table__body-wrapper"
);
if (scrollBody) {
scrollBody.scrollTop += this.scrollStep;
}
},
startAutoScroll() {
if (this.scrollInterval) return;
this.scrollInterval = setInterval(this.autoScroll, this.scrollSpeed);
},
stopAutoScroll() {
if (this.scrollInterval) {
clearInterval(this.scrollInterval);
this.scrollInterval = null;
}
},
resetScroll() {
const scrollBody = this.$refs.table.$el.querySelector(
".el-table__body-wrapper"
);
if (scrollBody) {
scrollBody.scrollTop = 0; // 重置滚动位置
}
this.startAutoScroll(); // 重新开始自动滚动
},
},
};
</script>
<style lang="scss">
.stripeTable {
.el-table {
background: none;
color: #fff;
}
.el-table::before {
height: 0px;
}
.el-table thead {
background: #003360;
}
.el-table tr {
background: none;
td {
border-bottom: none;
}
}
.el-table .el-table__row {
font-size: 0.7vw;
}
.cell .el-tooltip {
height: 100px;
}
.el-table td.el-table__cell {
padding: 0.8vh 0;
}
.el-table th.el-table__cell {
padding: 0.8vh 0;
font-size: 0.7vw;
}
.has-gutter {
background: #003360 !important;
}
.el-table th {
color: #fff;
}
.el-table--enable-row-hover .el-table__body tr:hover > td.el-table__cell {
color: #5f8fe7;
background: none !important;
}
.el-table th.el-table__cell.is-leaf {
border-bottom: none;
}
.el-table th.el-table__cell {
background: none !important;
}
.el-table__header-wrapper,
.el-table__body-wrapper {
margin-bottom: 0 !important;
}
// 设置滚动条的宽度
.el-table__body-wrapper::-webkit-scrollbar {
width: 0px;
height: 0;
}
// 设置滚动条的背景色和圆角
.el-table__body-wrapper::-webkit-scrollbar-thumb {
background-color: #5f8fe7;
-webkit-box-shadow: inset 0 0 5px rgba(0, 0, 0, 0.2);
border-radius: 10px;
}
.el-table .cell {
line-height: inherit;
}
.el-table th.gutter {
display: none;
width: 0;
height: 0;
}
.el-table colgroup col[name="gutter"] {
display: none;
width: 0;
height: 0;
}
.el-table__body {
width: 100% !important;
}
.el-table__row:nth-child(2n) {
background: #003360;
}
}
</style>
3750

被折叠的 条评论
为什么被折叠?



