From 7d47e9c0ec5ecc59ad6368461c21a43da54d5c77 Mon Sep 17 00:00:00 2001 From: toesbieya <1647775459@126.com> Date: Fri, 16 Oct 2020 12:02:20 +0800 Subject: [PATCH] =?UTF-8?q?=E5=88=97=E8=A1=A8=E9=A1=B5=E5=A2=9E=E5=8A=A0?= =?UTF-8?q?=E4=BA=86=E8=87=AA=E9=80=82=E5=BA=94=E9=AB=98=E5=BA=A6=E5=8A=9F?= =?UTF-8?q?=E8=83=BD=20=E6=A0=B7=E5=BC=8F=E4=BF=AE=E6=94=B9=20=E4=BB=A3?= =?UTF-8?q?=E7=A0=81=E7=AE=80=E5=8C=96?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- vue/src/asset/style/element-ui.scss | 19 +++ vue/src/asset/style/index.scss | 19 +-- vue/src/asset/style/variables.scss | 1 + vue/src/component/OrgTree/OrgTreeNode.vue | 8 +- vue/src/component/OrgTree/index.vue | 4 - vue/src/component/UploadFile/style.scss | 4 - vue/src/component/abstract/Dialog/style.scss | 11 -- vue/src/component/form/Search/index.vue | 2 +- .../component/Navbar/component/HeadMenu.vue | 10 +- vue/src/mixin/chart/resize.js | 2 +- .../common/ListPage/autoAdaptHeightMixin.js | 56 +++++++++ vue/src/view/app/common/ListPage/index.vue | 110 +++++++++--------- .../view/system/category/component/List.vue | 2 +- vue/src/view/system/department/indexPage.vue | 2 +- 14 files changed, 157 insertions(+), 93 deletions(-) create mode 100644 vue/src/view/app/common/ListPage/autoAdaptHeightMixin.js diff --git a/vue/src/asset/style/element-ui.scss b/vue/src/asset/style/element-ui.scss index c58301a..727ba3c 100644 --- a/vue/src/asset/style/element-ui.scss +++ b/vue/src/asset/style/element-ui.scss @@ -236,3 +236,22 @@ background: transparent; } } + +.el-upload { + $size: 100px; + + &-list__item-thumbnail { + object-fit: cover; + } + + &.el-upload--picture-card { + height: $size; + width: $size; + line-height: $size; + } + + &-list .el-upload-list__item { + height: $size; + width: $size; + } +} diff --git a/vue/src/asset/style/index.scss b/vue/src/asset/style/index.scss index 9404486..795875b 100644 --- a/vue/src/asset/style/index.scss +++ b/vue/src/asset/style/index.scss @@ -84,32 +84,37 @@ a:hover { /*----------路由页面的最大高度开始----------*/ $page-header-offsetHeight: $page-header-line-height + #{$page-view-margin * 2}; +.max-view-height.full { + height: 100vh; +} + .max-view-height { - height: calc(100vh - #{$page-view-margin * 2}); + overflow-y: hidden; + max-height: calc(100vh - #{$page-view-margin * 2}); } .has-nav .max-view-height { - height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height}); + max-height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height}); } .has-tags-view .max-view-height { - height: calc(100vh - #{$page-view-margin * 2} - #{$tags-view-height}); + max-height: calc(100vh - #{$page-view-margin * 2} - #{$tags-view-height}); } .has-page-header .max-view-height { - height: calc(100vh - #{$page-view-margin * 2} - #{$page-header-offsetHeight}); + max-height: calc(100vh - #{$page-view-margin * 2} - #{$page-header-offsetHeight}); } .has-nav.has-tags-view .max-view-height { - height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height} - #{$tags-view-height}); + max-height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height} - #{$tags-view-height}); } .has-nav .has-page-header .max-view-height { - height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height} - #{$page-header-offsetHeight}); + max-height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height} - #{$page-header-offsetHeight}); } .has-nav.has-tags-view .has-page-header .max-view-height { - height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height} - #{$tags-view-height} - #{$page-header-offsetHeight}); + max-height: calc(100vh - #{$page-view-margin * 2} - #{$nav-height} - #{$tags-view-height} - #{$page-header-offsetHeight}); } /*----------路由页面的最大高度结束----------*/ diff --git a/vue/src/asset/style/variables.scss b/vue/src/asset/style/variables.scss index fc3cefc..5e3122d 100644 --- a/vue/src/asset/style/variables.scss +++ b/vue/src/asset/style/variables.scss @@ -91,5 +91,6 @@ $dialog-top: 100px; success: $--color-success; danger: $--color-danger; warning: $--color-warning; + pageViewMargin: $page-view-margin; dialogTop: $dialog-top; } diff --git a/vue/src/component/OrgTree/OrgTreeNode.vue b/vue/src/component/OrgTree/OrgTreeNode.vue index 8e58376..abd4817 100644 --- a/vue/src/component/OrgTree/OrgTreeNode.vue +++ b/vue/src/component/OrgTree/OrgTreeNode.vue @@ -31,7 +31,6 @@ const renderNode = (h, data, context) => { const renderLabel = (h, data, context) => { const {props} = context const label = data[props.props.label] - const nodeRender = props.nodeRender const clickHandler = context.listeners['on-node-click'] const mousedownHandler = e => { e.stopPropagation() @@ -44,10 +43,7 @@ const renderLabel = (h, data, context) => { const touchleaveHandler = context.listeners['on-node-touchleave'] const childNodes = [] - if (typeof nodeRender === 'function') { - childNodes.push(nodeRender(h, data)) - } - else if (context.parent.$scopedSlots.default) { + if (context.parent.$scopedSlots.default) { childNodes.push(context.parent.$scopedSlots.default(data)) } else childNodes.push(label) @@ -97,7 +93,7 @@ const renderBtn = (h, data, context) => { return ( - {props.buttonRender ? props.buttonRender(h, data) : } + ) } diff --git a/vue/src/component/OrgTree/index.vue b/vue/src/component/OrgTree/index.vue index b9dc3d8..f02333f 100644 --- a/vue/src/component/OrgTree/index.vue +++ b/vue/src/component/OrgTree/index.vue @@ -8,8 +8,6 @@ :label-width="labelWidth" :collapsable="collapsable" :label-class-name="labelClassName" - :node-render="nodeRender" - :button-render="buttonRender" @on-expand="handleExpand" @on-node-click="handleNodeClick" /> @@ -38,8 +36,6 @@ export default { }, horizontal: Boolean, collapsable: Boolean, - nodeRender: Function, - buttonRender: Function, labelWidth: [String, Number], labelClassName: [Function, String], expandAll: Boolean diff --git a/vue/src/component/UploadFile/style.scss b/vue/src/component/UploadFile/style.scss index d14fc61..613fa6a 100644 --- a/vue/src/component/UploadFile/style.scss +++ b/vue/src/component/UploadFile/style.scss @@ -29,10 +29,6 @@ } } -.el-upload-list__item-thumbnail { - object-fit: cover; -} - .upload-tooltip { max-width: 146px; } diff --git a/vue/src/component/abstract/Dialog/style.scss b/vue/src/component/abstract/Dialog/style.scss index f254a21..6789556 100644 --- a/vue/src/component/abstract/Dialog/style.scss +++ b/vue/src/component/abstract/Dialog/style.scss @@ -14,16 +14,5 @@ .el-form { padding: 0; } - - .el-upload.el-upload--picture-card { - height: 100px; - width: 100px; - line-height: 105px; - } - - .el-upload-list .el-upload-list__item { - height: 100px; - width: 100px; - } } } diff --git a/vue/src/component/form/Search/index.vue b/vue/src/component/form/Search/index.vue index 87f5bc1..67acd5c 100644 --- a/vue/src/component/form/Search/index.vue +++ b/vue/src/component/form/Search/index.vue @@ -102,7 +102,7 @@ export default { this.initialModel = deepClone(this.model) this.resize() - this.resizeObserver = new ResizeObserver(() => this.resize()) + this.resizeObserver = new ResizeObserver(this.resize) this.resizeObserver.observe(this.$el.parentNode) this.$once('hook:beforeDestroy', () => { diff --git a/vue/src/layout/component/Header/component/Navbar/component/HeadMenu.vue b/vue/src/layout/component/Header/component/Navbar/component/HeadMenu.vue index 3b2312e..bc05745 100644 --- a/vue/src/layout/component/Header/component/Navbar/component/HeadMenu.vue +++ b/vue/src/layout/component/Header/component/Navbar/component/HeadMenu.vue @@ -138,8 +138,12 @@ export default { //如果已创建observer,则返回 if (this.resizeObserver) return - this.resizeObserver = new ResizeObserver(() => this.resize()) + this.resizeObserver = new ResizeObserver(this.resize) this.resizeObserver.observe(this.getMenuEl()) + + this.$once('hook:beforeDestroy', () => { + this.resizeObserver && this.resizeObserver.disconnect() + }) }, renderVisibleMenus(h, visibleMenus) { @@ -162,10 +166,6 @@ export default { mounted() { this.setChildrenWidth() this.createResizeObserver() - - this.$once('hook:beforeDestroy', () => { - this.resizeObserver && this.resizeObserver.disconnect() - }) }, render(h) { diff --git a/vue/src/mixin/chart/resize.js b/vue/src/mixin/chart/resize.js index 59cde3e..33d8081 100644 --- a/vue/src/mixin/chart/resize.js +++ b/vue/src/mixin/chart/resize.js @@ -3,7 +3,7 @@ import {debounce} from '@/util' export default { methods: { $_initResizeEvent() { - this.resizeObserver = new ResizeObserver(() => this.$_resizeHandler()) + this.resizeObserver = new ResizeObserver(this.$_resizeHandler) this.resizeObserver.observe(this.$el) }, $_destroyResizeEvent() { diff --git a/vue/src/view/app/common/ListPage/autoAdaptHeightMixin.js b/vue/src/view/app/common/ListPage/autoAdaptHeightMixin.js new file mode 100644 index 0000000..3b8dff6 --- /dev/null +++ b/vue/src/view/app/common/ListPage/autoAdaptHeightMixin.js @@ -0,0 +1,56 @@ +/** + * 列表页自适应混入 + * 监听el-table,动态设置max-height属性 + */ + +import cssVariables from "@/asset/style/variables.scss" +import {debounce} from "@/util" + +export default { + data() { + return { + tableMaxHeight: undefined + } + }, + + methods: { + resize() { + const clientHeight = window.innerHeight + const pageViewMargin = parseFloat(cssVariables['pageViewMargin']) + + //计算表格底部距离视窗底部的距离 + const tableRect = this.$refs.table.$el.getBoundingClientRect() + const bottomDistanceBetweenWindowAndTable = clientHeight - tableRect.top - tableRect.height + + //判断有无分页组件,分页组件总高度为70px(本身50px高度,margin-top 20px) + const paginationHeight = this.$el.querySelector('.table-container > .el-pagination') ? 70 : 0 + + //表格距离视窗底部的理想距离(分页高度 + el-card的1px边距 + el-card padding + 页面margin) + const bottomDistanceBetweenWindowAndTableShouldBe = + paginationHeight + + 1 + + 20 + + pageViewMargin + + const overHeight = bottomDistanceBetweenWindowAndTableShouldBe - bottomDistanceBetweenWindowAndTable + if (overHeight > 0) { + this.tableMaxHeight = tableRect.height - overHeight + } + }, + createResizeObserver() { + if (this.resizeObserver) return + + this.resizeObserver = new ResizeObserver(this.resize) + this.resizeObserver.observe(this.$refs.table.$el) + + this.$once('hook:beforeDestroy', () => { + this.resizeObserver && this.resizeObserver.disconnect() + }) + }, + }, + + mounted() { + this.resize = debounce(this.resize, 300) + this.createResizeObserver() + } +} diff --git a/vue/src/view/app/common/ListPage/index.vue b/vue/src/view/app/common/ListPage/index.vue index 9225339..5cd3b63 100644 --- a/vue/src/view/app/common/ListPage/index.vue +++ b/vue/src/view/app/common/ListPage/index.vue @@ -2,69 +2,75 @@ import AbstractTable from "@/component/abstract/Table" import AbstractPagination from "@/component/abstract/Pagination" import SearchForm from "@/component/form/Search" +import autoAdaptHeightMixin from "./autoAdaptHeightMixin" import {isEmpty} from "@/util" -const renderSearchForm = (h, config, slot) => { - return slot && {slot()} -} +export default { + name: "ListPage", -const renderButtons = (h, buttons) => { - if (buttons.length > 0 && isEmpty(buttons[0].type)) { - buttons[0].type = 'primary' - } - return ( - - {buttons.map(button => { - if (!button) return - const {icon, type, content, e} = button - return ( - - {content} - - ) - })} - - ) -} + mixins: [autoAdaptHeightMixin], -const renderList = (h, {loading, tableConfig, tableColumn, paginationConfig}) => { - return ( - - {tableColumn()} - - - ) -} + components: {AbstractTable, AbstractPagination, SearchForm}, -export default { - name: "ListPage", + props: {data: Object}, - functional: true, + methods: { + renderSearchForm(config, slot) { + return slot && {slot()} + }, + renderButtons(buttons) { + if (buttons.length > 0 && isEmpty(buttons[0].type)) { + buttons[0].type = 'primary' + } + return ( + + {buttons.map(button => { + if (!button) return + const {icon, type, content, e} = button + return ( + + {content} + + ) + })} + + ) + }, + renderTableAndPagination({loading, table, pagination}) { + //为了配合autoAdaptHeightMixin + if (!table.props || !table.props.maxHeight) { + table.props.maxHeight = this.tableMaxHeight + } - props: { - data: Object + return ( + + + + + ) + } }, - render(h, context) { - const {props: {data: {pageLoading, buttons, dataLoading, search, table, pagination}}, scopedSlots} = context + render() { + const {data: {pageLoading, buttons, dataLoading, search, table, pagination}, $scopedSlots} = this + + if (!table.scopedSlots) { + table.scopedSlots = {} + } + table.scopedSlots.default = $scopedSlots.tableColumn return ( - - {renderSearchForm(h, search, scopedSlots.searchForm)} - {renderButtons(h, buttons)} - {renderList(h, { - loading: dataLoading, - tableConfig: table, - tableColumn: scopedSlots.tableColumn, - paginationConfig: pagination - })} - {scopedSlots.default && scopedSlots.default()} + + {this.renderSearchForm(search, $scopedSlots.searchForm)} + {this.renderButtons(buttons)} + {this.renderTableAndPagination({loading: dataLoading, table, pagination})} + {$scopedSlots.default && $scopedSlots.default()} ) } diff --git a/vue/src/view/system/category/component/List.vue b/vue/src/view/system/category/component/List.vue index b84b51a..d41de55 100644 --- a/vue/src/view/system/category/component/List.vue +++ b/vue/src/view/system/category/component/List.vue @@ -1,5 +1,5 @@