//el-tree结构的一些知识
//修改el-tree的整体及节点样式
.el-tree {
background: transparent !important;
color: #ffffff !important;
font-size: 16px !important;
}
.el-tree-node:focus > .el-tree-node__content {
// color: rgb(255, 248, 169) !important;
// color: #003f95;
background-color: #003f95 !important;
}
.el-tree-node__content:hover {
background-color: #66b1ff87;
}
.el-tree--highlight-current
.el-tree-node.is-current
> .el-tree-node__content {
background-color: #003f95;
}
//一颗树状图的情况
<el-tree
ref="menuTree"
show-checkbox
highlight-current
:data="getFilterTreeData"
:props="defaultProps"
:filter-node-method="filterNode"
default-expand-all
@check-change="checkChange"
:check-strictly="true"
check-on-click-node
node-key="id"
:default-expand-all="true"
:expand-on-click-node="false"
/>
//多颗树状图的情况 使用v-for循环拿动态的ref
<div v-for="(c1,index1) in findArr" :key="c1.deviceRelationName" style="padding:10px">
<el-tree
:ref="`list${index1}`"
node-key="id"
check-on-click-node
show-checkbox
highlight-current
:data="c1"
:props="defaultStyle"
:check-strictly="true"
:filter-node-method="filterNode"
default-expand-all
@check-change="(data, node, isCheck) => {checkChangeRight(data, node, isCheck, index1)}"
:expand-on-click-node="false"
/>
</div>
// 节点选中 获取子节点的所有父节点
checkChange(a, b, c) {
// 如果为取消
if (b === false) {
//如果当前节点有子集
if (a.dopTemplateDetailList) {
//循环子集将他们的选中取消
a.dopTemplateDetailList.map((item) => {
this.$refs.menuTree.setChecked(item.id, false)
})
}
} else {
//否则(为选中状态)
//判断父节点id是否为空
if (a.pid !== 0) {
//如果不为空则将其选中
this.$refs.menuTree.setChecked(a.pid, true)
}
}
let res = this.$refs.menuTree.getCheckedNodes(false, true)//res为选中子节点的所有父节点的数组
},
//获取父节点的子节点
checkChangeNewRight(data, node) {
if (node === true) {
//如果当前节点有子集
if (data.children) {
//循环子集将他们的选中
data.children.map((item) => {
this.$refs.rightTree.setChecked(item.id, true)
})
}
}
}
checkChangeRight(data, node, isCheck, index) {
if (node === true) {
//如果当前节点有子集
if (data.children) {
//循环子集将他们的选中
data.children.map((item) => {
this.$refs[`list${index}`][0].setChecked(item.id, true)
})
}
}
//找到2个树所选的节点对象
let rightCheckTree = []
this.findArr.forEach((item, index) => {
let res = this.$refs[`list${index}`][0].getCheckedNodes(false, true)
rightCheckTree.push(...res)
})
//2维中找一维没有的新的2维
this.unContextArr = this.cForm.fdsConfigDeviceRangeList.map((item) =>
item.filter((item1, index) => {
return !rightCheckTree.find((item2) => item1.id == item2.id)
})
)
},
//把数组生成树形结构
toTree(data) {
let result = []
if (!Array.isArray(data)) {
return result
}
data.forEach((item) => {
delete item.children
})
let map = {}
data.forEach((item) => {
map[item.deviceRelationId] = item
})
data.forEach((item) => {
let parent = map[item.deviceRelationPid]
if (parent) {
;(parent.children || (parent.children = [])).push(item)
} else {
result.push(item)
}
})
return result
},
//树拍平
readNodes(nodes = [], arr = []) {
for (let item of nodes) {
arr.push(item)
if (item.children && item.children.length) {
this.readNodes(item.children, arr)
}
}
return arr
},
//截取当前点击的所有父节点组成的数据(网上找的用的是递归需要传递整个树的数据及点击node-click的data.id)
getAllParentArr(list, id) {
for (let i in list) {
if (list[i].id === id) {
//查询到返回该数组对象
return [list[i]]
}
if (list[i].dopTemplateDetailList) {
let node = this.getAllParentArr(list[i].dopTemplateDetailList, id)
if (node !== undefined) {
//查询到把父节点连起来
return node.concat(list[i])
} else {
console.log('没有le')
}
}
}
},
//组合对象数组中的数组相同的
dedup(arr = []) {
const mp = {}
for (let obj of arr) {
const { deviceRelationName, deviceRelationPath, patternId, children } =
obj
if (mp[deviceRelationName]) {
mp[deviceRelationName].children.push(children)
} else {
mp[deviceRelationName] = {
deviceRelationName,
deviceRelationPath,
patternId,
children: [children],
}
}
}
return Object.values(mp)
},
//关键字搜索展开及过滤
watch: {
filterTextMenu(val) {
this.$refs.leftMenu.filter(val)
},
keyword(val) {
this.$refs.Tree.filter(val)
if (!val) {
this.$refs.Tree.setCheckedKeys([])
}
},
},
methods:{
menuFilterNode(value, data) {
if (!value) return true
return data.name.indexOf(value) !== -1
},
filterNode(value, data, node) {
if (!value) return true
return this.findSearkey(node, value)
},
findSearkey(node, key) {
if (node.label.indexOf(key) !== -1) {
return true
} else {
if (node.parent.parent == null) {
return false
} else {
return this.findSearkey(node.parent, key)
}
}
},
}
//附带一个el时间选择器的禁用
//限制时间选择到秒
nowDateByDay: string = new Date().format('YYYY-MM-DD 00:00:00');
pickerOptions: any = {
disabledDate: (time: any) => {
return new Date(time).getTime() >= new Date(this.nowDateByDay).getTime() + 1000 * 60 * 60 * 24;
},
//限制时间到日
pickerOptions: {
disabledDate(time) {
return time.getTime() > new Date().getTime();
}
},
分页器2次封装 一个全局组件
组件引入后传入pager 及 change=“getChangePage”
pager: {
currentPage: 1,
pageSize: 10,
total: null,
pageSizes: [5, 10, 50, 100],
},
getChangePage(val){
this.pager = val
调用组件中的页面方法
}
<template>
<div class="pagination">
<el-pagination
@size-change="handleSizeChange"
@current-change="handleCurrentChange"
:current-page.sync="pager.currentPage"
:page-sizes="pager.pageSize"
:page-count="5"
layout="total.sizes,prev,pager,next,jumper"
:total="pager.total"
>
</el-pagination>
</div>
</template>
<script>
export default {
name:'pagination',
data(){
return {}
},
props:{
pager:{
type:Obejct,
default(){
return{
currentPage:1,
pageSize:10,
total:null,
pageSize:[5,10,50,100]
}
}
}
},
created(){},
mounted(){},
methods:{
handleSizeChange(val){
if(this.pager.total === null){
this.pager.total === null
this.pager.pageSize = val
return
}
this.pager.pageSize = val
this.pager.currentPage = 1
this.$emit("change",this.pager)
},
handleCurrentChange(val){
if(this.pager.total === null){
this.pager.total == null
this.pager.currentPage = 1
return
}
this.pager.currentPage = val
this.$emit('change',this.pager)
}
}
</script>
看看别人的二次封装el-table
<template>
<div>
<template :table="table">
<el-table
v-loading="table.loading"
element-loading-spinner="el-icon-loading"
element-loading-background="rgba(0,0,0,0.1)"
:show-summary="table.hasShowSummary"
:summary-method="table.getSummaries"
ref="TIRITable"
:height="table.height"
:max-height="table.maxHeight"
:data="table.data"
tooltip-effect="dark"
:border="table.border"
style="width:100%"
:row-class-name="rowClassName"
:span-method="objectSpanMethod"
header-row-class-name="thClassName"
@selection-change="handleSelectionChange"
@select="selectionSelect"
@select-all="selectionSelectAll"
@row-click="rowClick"
row-class-name="singleDobuleStyle"
>
<el-table-column
v-if="table.hasSelect"
align="center"
type="selection"
:width="table.hasSelctWidth ? table.hasSelectWidth: '55px'"
>
</el-table-column>
<el-table-column
v-if="!table.hasOrder"
type="index"
align="center"
fixed
:width="table.hasOrderWidth?table.hasOrderWidth:'55px'"
label="序号"
></el-table-column>
<el-table-column type="expand" v-if="table.hasExpand" align="center">
<template slot-scope="props">
<el-form label-position="left" inline class="demo-table-expand">
<el-form-item :label="item.label" v-for="item in table.expands" :key="item.id">
<span>{{props.row[item.prop]}}</span>
</el-form-item>
</el-form>
</template>
</el-table-column>
<tempalte v-for="item in table.tr">
<el-table-column
v-if="item.show !== false && item.show === 'tempalte'"
:label="item.label"
:class-name="item.className ? item.className :''"
:key="item.id"
:width="item.width?item.width:''"
:min-width="item.minWidth?item.minWidth:''"
:fixed="item.fixed"
>
<tempalte slot-scope="scope">
<slot :name="item.prop" :obj="scope"></slot>
<tempalte>
</el-table-column>
<el-table-column
:sortable="item.sorttable"
:sort-method="item.sortMethod"
:fixed="item.fixed"
v-else-if="item.show !== false && item.show !=='tempalte'"
:label="item.label"
:prop="item.prop"
:key="item.id"
:class-name="item.className:item.className:''"
:width="item.width?item.width:''"
>
<el-table-column
v-show="item.children"
v-for="item1 in item.children"
:label="item1.label"
:prop="item1.prop"
:class-name="item1.className ? item1.className:''"
:key="item1.id"
:width="item1.width?item1.width:''"
:min-width="item1.minWidth?item1.minWidth:''"
>
<el-table-column
v-show="item1.children"
v-for="item2 in item1.children"
:label="item2.label"
:prop="item2.prop"
:key="item2.id"
:class-name="item2.className?item2.className:''"
:width="item2.width?item2.width:''"
:min-width="item2.minWidth?item2.minWith:''"
>
</el-table-column>
</el-table-column>
</el-table-column>
</tempalte>
<el-table-column
column-key="operation"
:label="table.operation.label"
:fixed="table.operation.fixed"
:width="table.operation.width?table.operation:''"
:min-width="table.operation.minWidth?table.operation.minWidth:''"
:class-name="table.operation.className"
v-if="table.hasOperation"
align="center"
>
<template slot-scope="scope">
<slot :name="table.operation.label" :obj="scope"></slot>
</template>
</el-table-column>
</el-table>
</tempalte>
</div>
</template>
<script>
export default {
name:'',
props:{
table:{
type:Object,
default(){
return{
hasMergeRowOrColumn: false, // 是否合并单元格
loading: false, // 加载中动画
hasShowSummary: false, // 是否显示表位合计行
border: false, // 是否带有纵向边框,默认为false
hasOrder: false, // 是否需要显示序列 默认fslae 显示
isRadio: false, // 是否单选
hasSelect: false, // 有无选中功能
hasOperation: false, // 有无操作功能
hasExpand: false, // 有无展开行功能
tr:[
{
id:'1',
label:'label',
prop:'prop',
className:'classname',
minWidth:'80',
show:true,// show有三种值:false隐藏当前列,true常规表格列,’template‘自定义表格列
}
],
data:[],
operation:{
label:'操作',
width:'200',
className:'',
data: [
// 如果每一行的操作列的数据都是一样的,可以把操作数据定义在data 里面。但是如果每一列的操作列根据具体情况来定义的话 需要在模板里面自定义操作类别
{
label: '编辑', // 按钮文字
Fun: 'handleSubmit', // 点击按钮后触发的父组件事件
size: 'mini', // 按钮大小
id: '1', // 按钮循环组件的key值
classname: 'show', // 按钮的类名
icon: 'el-icon-delete', // 按钮的图标
type: 'primary', //按钮的类型 primary / success / warning / danger / info / text,如果设置为text 那么一定是plain:false
plain: true, //是否朴素按钮
},
]
},
expands:[
// 展开行数据
{
id: '1',
label: 'label',
prop: 'prop',
},
],
getSummaries(param) {
// 自定义表位合计行数据
// *** 此函数传入param参数
console.log(param)
// *** 最后返回一个数组,合计行会显示数组中的内容
return []
},
}
}
},
sendmethod: {
type: Function,
required: false,
},
},
mounted() {
// 解决table 表头错位问题
setTimeout(() => {
this.$refs.TlRlTable.doLayout()
}, 1200)
},
methods:{
handleSelectionChange(val) {
this.$emit('onHandleSelectionChange', val)
},
selectionSelectAll(selection) {
if (selection.length > 1 && this.table.isRadio) {
selection.length = 1
}
},
selectionSelect(selection) {
if (selection.length > 1 && this.table.isRadio) {
let del_row = selection.shift()
this.$refs.TlRlTable.toggleRowSelection(del_row, false)
}
},
handleOperation(a, b, id) {
const data = this.table.operation.data
for (let i = 0; i < data.length; i++) {
if (id === data[i].id) {
this.$emit(data[i].Fun, a, b)
}
}
},
objectSpanMethod({ row, column, rowIndex, columnIndex }) {
if (!this.table.hasMergeRowOrColumn) {
return
} else {
//this.$emit('onMergeRowOrColumn', { row, column, rowIndex, columnIndex });
return this.sendmethod({ row, column, rowIndex, columnIndex }) //通过父组件传递方法的形式来达到单元格的合并
}
},
// 点击某一行时触发的函数
// *** 按下左键然后移动鼠标到其它列放开左键,会有报错 -- 优化:添加点击行参数,
rowClick(Row, Event, Column) {
if (
!Column ||
Column.type === 'selection' ||
Column.columnKey === 'operation' ||
Column.type === 'expand'
) {
return
}
const data = {
row: Row,
event: Event,
column: Column,
}
this.$emit('onRowClick', data)
},
// 行类名的回调函数
// 在表格数据中添加class字段即为表格行类名,配合css可对表格行中的自定义标签进行样式优化
rowClassName(rowdata) {
const data = this.table.data
// 把行索引添加到行数据中以便使用
rowdata.row.index = rowdata.rowIndex
let className = data[rowdata.rowIndex].class
? data[rowdata.rowIndex].class
: ''
if (className.length === 0) {
return
}
className = className.join(' ')
return className
},
}
}
</script>
<style scoped>
.el-table th {
text-align: center !important;
}
.el-table td,
.el-table th {
text-align: center !important;
}
.el-table th {
text-align: center;
font-size: 12px;
color: #323232;
font-weight: normal;
background: #bbb;
font-family: 'SourceHanSansCN-Normal';
}
.el-table td {
padding: 8px 0 !important;
}
.el-table th {
padding: 10px 0 !important;
}
table tr:nth-child(odd) {
background: #fff;
}
table tr:nth-child(even) {
background: #f1f1f1;
}
.el-table__header thead th {
background: #f5f7fa !important;
}
/*table, thead, tbody, tfoot, tr, th, td, caption, col, colgroup {
text-align: inherit;
line-height: inherit;
font-size: 100%;
border-bottom: 1px solid #eee !important;
}*/
/*.el-table--border td, .el-table--border th:*/
/* >>>.el-table__header thead {
border-top: 1px solid #ccc;
border-bottom: 1px solid #ccc;
border-left: 1px solid #eee !important;
box-sizing: border-box;
}*/
</style>
<style>
.el-table th,
.el-table td {
text-align: center;
}
#tableBox tbody tr:last-child td {
/*border-right: 1px solid #EBEEF5;*/
/*border-bottom: 1px solid #EBEEF5;*/
}
/* #tableBox .el-table{
border-left: 1px solid #EBEEF5;
}*/
#tableBox .thClassName th:nth-child(1) {
border-left: 1px solid #ebeef5;
}
#tableBox .el-table__row td:nth-child(1) {
border-left: 1px solid #ebeef5;
}
#tableBox .el-table__row td:nth-child(1) {
border-left: 1px solid #ebeef5;
}
</style>
el-table合并
getSpanArr(data) {
this.spanArr = [] //在data里面定义
this.position = 0 //在data里面定义
this.spanArr2 = []
this.pos2 = 0
var tableData = data
tableData.forEach((item, index) => {
if (index === 0) {
this.spanArr.push(1)
this.position = 0
this.spanArr2.push(1)
this.pos2 = 0
} else {
const sequenceFlag =
tableData[index].Id === tableData[index - 1].Id
const sequenceFlag2 =
tableData[index].secondId === tableData[index - 1].secondId
if (sequenceFlag) {
this.spanArr[this.position] += 1 //连续有几行项目名名称相同
this.spanArr.push(0) // 名称相同后往数组里面加一项0
//当项目名称相同时,设置当前序号和前一个相同
} else {
this.spanArr.push(1)
this.position = index
}
if (sequenceFlag2) {
this.spanArr2[this.pos2] += 1
this.spanArr2.push(0)
} else {
this.spanArr2.push(1)
this.pos2 = index
}
}
})
objectSpanMethod({ row, rowIndex, columnIndex }) {
if (columnIndex === 1) {
const _row = this.spanArr[rowIndex]
const _col = _row > 0 ? 1 : 0
return {
rowspan: _row,
colspan: _col,
}
}
if (columnIndex === 2) {
const _row = this.spanArr2[rowIndex]
const _col = _row > 0 ? 1 : 0
// console.log(`rowspan:${_row} colspan:${_col}`)
return {
// [0,0] 表示这一行不显示, [2,1]表示行的合并数
rowspan: _row,
colspan: _col,
}
}
},
//为template写法
<el-table
:data="tableData"
border
:span-method="objectSpanMethod"
></el-table>
el-table合计功能
tabledoLayout(){
this.$nextTick(()=>{
this.$refs.table.doLayout()
})
}
// 给个开关控制新增只点击一次 让表格重构避免表尾合计样式的问题,直接在mounted或者created中调用会报错
if (!this.addtag) {
this.tabledoLayout()
this.addtag = true
}