同步修改精简版

master
toesbieya 6 years ago
parent c44753a0ce
commit b449fbfa7b
  1. 250
      vue/full/src/asset/style/element-ui.scss
  2. 2
      vue/template/element-ui-personal/style/message.scss
  3. 9
      vue/template/package-lock.json
  4. 3
      vue/template/package.json
  5. 93
      vue/template/src/asset/style/cover/element-ui.scss
  6. 7
      vue/template/src/asset/style/cover/var.scss
  7. 2
      vue/template/src/asset/style/display.scss
  8. 19
      vue/template/src/asset/style/index.scss
  9. 32
      vue/template/src/asset/style/mixin.scss
  10. 2
      vue/template/src/asset/style/nprogress.scss
  11. 222
      vue/template/src/asset/style/transition.scss
  12. 59
      vue/template/src/asset/style/var.scss
  13. 11
      vue/template/src/component/checkbox/ImgCheckbox.vue
  14. 4
      vue/template/src/component/menu/ContextMenu/index.vue
  15. 4
      vue/template/src/component/menu/NavMenu/index.vue
  16. 2
      vue/template/src/component/menu/NavMenu/style.scss
  17. 2
      vue/template/src/component/menu/NavMenu/theme-dark.scss
  18. 2
      vue/template/src/component/menu/NavMenu/theme-light.scss
  19. 12
      vue/template/src/config/index.js
  20. 82
      vue/template/src/directive/dragDialog.js
  21. 5
      vue/template/src/directive/index.js
  22. 4
      vue/template/src/layout/component/Aside/component/MenuSearch.vue
  23. 3
      vue/template/src/layout/component/Aside/style.scss
  24. 6
      vue/template/src/layout/component/Aside/theme-dark.scss
  25. 6
      vue/template/src/layout/component/Aside/theme-light.scss
  26. 2
      vue/template/src/layout/component/Logo.vue
  27. 2
      vue/template/src/layout/component/Navbar/style.scss
  28. 2
      vue/template/src/layout/component/Navbar/theme-dark.scss
  29. 4
      vue/template/src/layout/component/Navbar/theme-light.scss
  30. 2
      vue/template/src/layout/component/Page/component/BackToTop.vue
  31. 5
      vue/template/src/layout/component/Page/component/PageFooter.vue
  32. 8
      vue/template/src/layout/component/Page/component/PageHeader.vue
  33. 8
      vue/template/src/layout/component/Page/component/TagsView/style.scss
  34. 50
      vue/template/src/layout/component/Page/index.vue
  35. 23
      vue/template/src/layout/component/Page/style.scss
  36. 34
      vue/template/src/layout/component/SettingDrawer.vue
  37. 13
      vue/template/src/layout/mixin/decideRouterTransition.js
  38. 2
      vue/template/src/layout/store/app.js
  39. 17
      vue/template/src/layout/store/page.js
  40. 10
      vue/template/src/layout/store/tagsView.js
  41. 1
      vue/template/src/main.js
  42. 5
      vue/template/src/router/guardian/accessControl.js
  43. 11
      vue/template/src/router/module/example/child/directive.js
  44. 37
      vue/template/src/store/module/resource.js
  45. 20
      vue/template/src/store/module/user.js
  46. 17
      vue/template/src/util/auth.js
  47. 4
      vue/template/src/util/browser.js
  48. 2
      vue/template/src/view/_app/login/index.vue
  49. 44
      vue/template/src/view/_app/login/style.scss
  50. 7
      vue/template/src/view/_common/ExceptionPage/style.scss
  51. 2
      vue/template/src/view/_common/SkeletonPage/style.scss
  52. 4
      vue/template/src/view/example/component/skeletonPage.vue
  53. 25
      vue/template/src/view/example/directive/dragDialogPage.vue
  54. 12
      vue/template/vue.config.js

@ -1,250 +0,0 @@
// cover some element-ui styles
.el-alert {
&--info.is-light {
color: #606266;
background-color: #f0faff;
border: 1px solid #abdcff;
.el-icon-info {
color: $--color-primary;
}
}
}
.el-button {
[class*="el-icon-"] + span {
margin-left: 7px;
}
//按钮新增类型type=dashed
&.el-button--dashed {
border-style: dashed;
}
&.el-button--small {
font-size: 14px;
padding: 8px 15px;
&.is-circle {
padding: 8px;
}
}
}
.el-card {
overflow: visible;
.el-card__body {
height: 100%;
@include clearfix;
}
.el-card__header + .el-card__body {
height: calc(100% - 55px);
}
}
.el-date-editor.el-input,
.el-date-editor--daterange {
width: 100% !important;
}
.el-dialog {
@include deep-shadow;
margin-bottom: 0;
min-width: 384px;
.el-dialog__header {
border-bottom: 1px solid #EBEEF5;
padding: 17px;
.el-dialog__title {
line-height: inherit;
color: inherit;
font-size: inherit;
}
.el-dialog__headerbtn {
top: 18px;
}
}
.el-dialog__footer {
border-top: 1px solid #EBEEF5;
padding: 10px 16px;
}
.el-scrollbar__wrap {
//53 for dialog header,53 for dialog footer
max-height: calc(100vh - 53px - 53px - #{$dialog-top * 2});
}
}
.el-drawer {
&__body {
overflow-y: overlay;
}
}
.el-loading-mask {
background: #ffffff;
color: $--color-primary;
}
.el-menu {
width: 100%;
border: none !important;
overflow: hidden;
&::-webkit-scrollbar {
display: none;
}
//子级菜单激活时父级同样高亮
.el-menu-item.is-active,
.is-active > .el-submenu__title {
color: $--color-primary !important;
}
//箭头图标与字体同色
.el-submenu__title i {
color: inherit;
}
//原先垂直时右侧展开箭头偏上
.el-submenu__icon-arrow {
margin-top: -4px;
}
//弹出菜单
&.el-menu--popup {
max-height: 88vh;
min-width: 160px;
padding: 0;
margin-bottom: 0.5vh;
overflow-y: auto;
.el-menu-item,
.el-submenu__title {
padding: 0 $menu-padding;
}
}
&--horizontal > .el-menu-item:not(.is-disabled):hover,
&--horizontal > .el-menu-item:not(.is-disabled):focus,
&--horizontal > .el-submenu .el-submenu__title:hover,
&--horizontal .el-menu .el-menu-item,
&--horizontal .el-menu .el-submenu__title {
background-color: inherit;
}
}
.el-message {
@include deep-shadow;
@include max-width-on-mobile;
border-width: 0;
.el-message__icon, .el-message__content {
color: #ffffff !important;
}
&.el-message--success {
background: $--color-success;
}
&.el-message--info {
background: $--color-primary;
}
&.el-message--warning {
background: $--color-warning;
}
&.el-message--error {
background: $--color-danger;
}
}
.el-message-box {
position: relative;
@include deep-shadow;
@include max-width-on-mobile;
}
.el-notification {
@include deep-shadow;
.el-notification__icon.el-icon-info {
color: $--color-primary;
}
}
.el-pagination {
text-align: right;
.el-pagination__editor.el-input {
margin: 0 5px;
}
.el-table + & {
padding-top: 20px;
}
}
.el-scrollbar {
height: 100%;
.el-scrollbar__wrap {
-webkit-overflow-scrolling: touch;
}
}
.el-select {
width: 100%;
}
.el-steps {
&.el-steps--horizontal {
.el-step__line {
left: 57%;
right: -43%;
}
}
}
.el-table {
thead {
color: #303133
}
thead > tr > th {
background: #fbfbfb;
}
}
.el-textarea {
.el-input__count {
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;
}
}

@ -23,7 +23,7 @@
left: 10px; left: 10px;
right: 10px; right: 10px;
animation: el-message-progress linear; animation: el-message-progress linear;
background: currentColor; background-color: currentColor;
opacity: .3; opacity: .3;
transform-origin: 0 50%; transform-origin: 0 50%;
transform: scaleX(0); transform: scaleX(0);

@ -11560,15 +11560,6 @@
} }
} }
}, },
"webpack-theme-color-replacer": {
"version": "1.3.14",
"resolved": "https://registry.npm.taobao.org/webpack-theme-color-replacer/download/webpack-theme-color-replacer-1.3.14.tgz",
"integrity": "sha1-K9ybKecIqpDKVq/OZJVWksUFC4s=",
"dev": true,
"requires": {
"webpack-sources": "*"
}
},
"websocket-driver": { "websocket-driver": {
"version": "0.6.5", "version": "0.6.5",
"resolved": "https://registry.npm.taobao.org/websocket-driver/download/websocket-driver-0.6.5.tgz", "resolved": "https://registry.npm.taobao.org/websocket-driver/download/websocket-driver-0.6.5.tgz",

@ -24,8 +24,7 @@
"sass-loader": "^8.0.2", "sass-loader": "^8.0.2",
"svg-sprite-loader": "^4.3.0", "svg-sprite-loader": "^4.3.0",
"svgo": "^1.3.2", "svgo": "^1.3.2",
"vue-template-compiler": "^2.6.11", "vue-template-compiler": "^2.6.11"
"webpack-theme-color-replacer": "^1.3.14"
}, },
"postcss": { "postcss": {
"plugins": { "plugins": {

@ -0,0 +1,93 @@
// cover some element-ui styles
.el-backtop {
border-radius: 0;
}
.el-drawer {
&__body {
overflow-y: overlay;
}
}
.el-menu {
width: 100%;
border: none !important;
overflow: hidden;
&::-webkit-scrollbar {
display: none;
}
//子级菜单激活时父级同样高亮
.el-menu-item.is-active,
.is-active > .el-submenu__title {
color: $--color-primary !important;
}
//箭头图标与字体同色
.el-submenu__title i {
color: inherit;
}
//原先垂直时右侧展开箭头偏上
.el-submenu__icon-arrow {
margin-top: -4px;
}
//弹出菜单
&.el-menu--popup {
max-height: 88vh;
min-width: 160px;
padding: 0;
margin-bottom: 0.5vh;
overflow-y: auto;
.el-menu-item,
.el-submenu__title {
padding: 0 $menu-padding;
}
}
&--horizontal > .el-menu-item:not(.is-disabled):hover,
&--horizontal > .el-menu-item:not(.is-disabled):focus,
&--horizontal > .el-submenu .el-submenu__title:hover,
&--horizontal .el-menu .el-menu-item,
&--horizontal .el-menu .el-submenu__title {
background-color: inherit;
}
}
.el-message {
@include deep-shadow;
@include max-width-on-mobile;
border-width: 0;
.el-message__icon,
.el-message__content {
color: $--color-white !important;
}
&.el-message--success {
background-color: $--color-success;
}
&.el-message--info {
background-color: $--color-primary;
}
&.el-message--warning {
background-color: $--color-warning;
}
&.el-message--error {
background-color: $--color-danger;
}
}
.el-scrollbar {
height: 100%;
.el-scrollbar__wrap {
-webkit-overflow-scrolling: touch;
}
}

@ -0,0 +1,7 @@
/*仅覆盖element-ui中的预设变量,不会被使用*/
//el-menu的hover背景颜色
$--menu-item-hover-fill: none;
//引入element的scss时需要覆盖字体路径
$--font-path: '~element-ui/lib/theme-chalk/fonts';

@ -1,4 +1,4 @@
@media only screen and (max-width: 768px) { @media only screen and (max-width: $--sm) {
.hidden-xs { .hidden-xs {
display: none !important display: none !important
} }

@ -1,11 +1,13 @@
@import "~normalize.css/normalize.css"; @import "~normalize.css/normalize.css";
@import "./variables"; @import "./var.scss";
@import "~element-ui/packages/theme-chalk/src/index"; @import "./cover/var.scss";
@import "./mixin.scss";
@import "~element-ui/packages/theme-chalk/src/index.scss";
@import "~@ele/style/index.scss"; @import "~@ele/style/index.scss";
@import "./element-ui"; @import "./cover/element-ui.scss";
@import './display'; @import './display.scss';
@import "./transition"; @import "./transition.scss";
@import "./nprogress"; @import "./nprogress.scss";
body { body {
height: 100%; height: 100%;
@ -59,7 +61,7 @@ a:hover {
background-color: rgba($--color-primary, 0.8); background-color: rgba($--color-primary, 0.8);
&:hover { &:hover {
background-color: rgba($--color-primary, 1); background-color: $--color-primary;
} }
} }
} }
@ -72,10 +74,11 @@ a:hover {
align-content: space-between; align-content: space-between;
} }
//仅用于演示用例
.tip-row { .tip-row {
position: relative; position: relative;
z-index: 1; z-index: 1;
background: #fafafa; background-color: #fafafa;
padding: 8px 24px; padding: 8px 24px;
margin-bottom: 20px; margin-bottom: 20px;
border-radius: 2px; border-radius: 2px;

@ -0,0 +1,32 @@
@mixin clearfix {
&::after {
visibility: hidden;
display: block;
font-size: 0;
content: " ";
clear: both;
height: 0;
}
}
@mixin deep-shadow {
box-shadow: 0 3px 5px -1px rgba(0, 0, 0, 0.2), 0 6px 10px 0 rgba(0, 0, 0, 0.14), 0 1px 18px 0 rgba(0, 0, 0, 0.12);
}
@mixin mobile {
@media (max-width: $max-mobile-width) {
@content
}
}
@mixin pc {
@media (min-width: $max-mobile-width) {
@content
}
}
@mixin max-width-on-mobile {
@include mobile {
max-width: 384px;
}
}

@ -2,7 +2,7 @@
#nprogress { #nprogress {
.bar { .bar {
background: $--color-primary; background-color: $--color-primary;
.peg { .peg {
box-shadow: 0 0 10px $--color-primary, 0 0 5px $--color-primary;; box-shadow: 0 0 10px $--color-primary, 0 0 5px $--color-primary;;

@ -1,5 +1,3 @@
$transition-easing: cubic-bezier(0.215, 0.61, 0.355, 1);
.right-out, .right-out,
.left-out { .left-out {
&-leave-active, &-leave-active,
@ -31,223 +29,3 @@ $transition-easing: cubic-bezier(0.215, 0.61, 0.355, 1);
transform: translateX(-30px); transform: translateX(-30px);
} }
} }
.slide-right,
.slide-left,
.slide-up,
.slide-down,
.jump-right,
.jump-left,
.jump-up,
.jump-down,
.fade,
.scale,
.rotate,
.flip {
&-leave-active {
position: absolute
}
}
.slide-right,
.slide-left,
.slide-up,
.slide-down {
&-enter-active,
&-leave-active {
transition: transform .3s $transition-easing
}
}
.slide-right {
&-enter {
transform: translate3d(-100%, 0, 0);
}
&-leave-to {
transform: translate3d(100%, 0, 0);
}
}
.slide-left {
&-enter {
transform: translate3d(100%, 0, 0);
}
&-leave-to {
transform: translate3d(-100%, 0, 0);
}
}
.slide-up {
&-enter {
transform: translate3d(0, 100%, 0)
}
&-leave-to {
transform: translate3d(0, -100%, 0)
}
}
.slide-down {
&-enter {
transform: translate3d(0, -100%, 0)
}
&-leave-to {
transform: translate3d(0, 100%, 0)
}
}
.jump-right,
.jump-left,
.jump-up,
.jump-down {
&-enter-active,
&-leave-active {
transition: opacity .3s, transform .3s
}
&-enter,
&-leave-to {
opacity: 0
}
}
.jump-right {
&-enter {
transform: translate3d(-15px, 0, 0)
}
&-leave-to {
transform: translate3d(15px, 0, 0)
}
}
.jump-left {
&-enter {
transform: translate3d(15px, 0, 0)
}
&-leave-to {
transform: translateX(-15px)
}
}
.jump-up {
&-enter {
transform: translate3d(0, 15px, 0)
}
&-leave-to {
transform: translate3d(0, -15px, 0)
}
}
.jump-down {
&-enter {
transform: translate3d(0, -15px, 0)
}
&-leave-to {
transform: translate3d(15px, 0, 0)
}
}
.fade {
&-enter-active,
&-leave-active {
transition: opacity .3s ease-out
}
&-enter,
&-leave,
&-leave-to {
opacity: 0
}
}
.scale {
&-enter-active,
&-leave-active {
transition: opacity .3s, transform .3s $transition-easing
}
&-enter,
&-leave,
&-leave-to {
opacity: 0;
transform: scale3d(0, 0, 1)
}
}
.rotate {
&-enter-active,
&-leave-active {
transition: opacity .3s, transform .3s $transition-easing;
transform-style: preserve-3d
}
&-enter,
&-leave,
&-leave-to {
opacity: 0;
transform: scale3d(0, 0, 1) rotate3d(0, 0, 1, 90deg)
}
}
.flip-right,
.flip-left,
.flip-up,
.flip-down {
&-enter-active,
&-leave-active {
transition: transform .3s;
backface-visibility: hidden
}
&-enter-to,
&-leave {
transform: perspective(400px) rotate3d(1, 1, 0, 0deg)
}
}
.flip-right {
&-enter {
transform: perspective(400px) rotate3d(0, 1, 0, -180deg)
}
&-leave-to {
transform: perspective(400px) rotate3d(0, 1, 0, 180deg)
}
}
.flip-left {
&-enter {
transform: perspective(400px) rotate3d(0, 1, 0, 180deg)
}
&-leave-to {
transform: perspective(400px) rotate3d(0, 1, 0, -180deg)
}
}
.flip-up {
&-enter {
transform: perspective(400px) rotate3d(1, 0, 0, -180deg)
}
&-leave-to {
transform: perspective(400px) rotate3d(1, 0, 0, 180deg)
}
}
.flip-down {
&-enter {
transform: perspective(400px) rotate3d(1, 0, 0, 180deg)
}
&-leave-to {
transform: perspective(400px) rotate3d(1, 0, 0, -180deg)
}
}

@ -1,52 +1,15 @@
@import "~element-ui/packages/theme-chalk/src/common/var";
//设定移动端的最大宽度只能是number类型 //设定移动端的最大宽度只能是number类型
$max-mobile-width: 500px; $max-mobile-width: 500px;
//覆盖element颜色 //覆盖element颜色
$--color-primary: #1890ff; //这里如果有改动需要同时修改vue.config.js中ThemeColorReplacer的配置 $--color-primary: #1890ff;
$--color-success: #21BA45; $--color-success: #21BA45;
$--color-warning: #FF5722; $--color-warning: #FF5722;
$--color-danger: #F44336; $--color-danger: #F44336;
$--color-info: #009688; $--color-info: #009688;
//覆盖el-menu的hover背景颜色
$--menu-item-hover-fill: none;
//引入element的scss时需要覆盖字体路径
$--font-path: '~element-ui/lib/theme-chalk/fonts';
@mixin clearfix {
&::after {
visibility: hidden;
display: block;
font-size: 0;
content: " ";
clear: both;
height: 0;
}
}
@mixin deep-shadow {
box-shadow: 0 3px 5px -1px rgba(0, 0, 0, 0.2), 0 6px 10px 0 rgba(0, 0, 0, 0.14), 0 1px 18px 0 rgba(0, 0, 0, 0.12);
}
@mixin mobile {
@media (max-width: $max-mobile-width) {
@content
}
}
@mixin pc {
@media (min-width: $max-mobile-width) {
@content
}
}
@mixin max-width-on-mobile {
@include mobile {
max-width: 384px;
}
}
//菜单中icon的大小 //菜单中icon的大小
$menu-icon-size: 14px; $menu-icon-size: 14px;
//菜单中icon和文字的距离 //菜单中icon和文字的距离
@ -60,7 +23,7 @@ $sub-menu-background-dark: darken($menu-background-dark, 5%);
//暗色主菜单的背景色用于双层侧边栏的主菜单和顶部导航栏 //暗色主菜单的背景色用于双层侧边栏的主菜单和顶部导航栏
$root-menu-background-dark: #1F293D; $root-menu-background-dark: #1F293D;
//亮色菜单的文字颜色 //亮色菜单的文字颜色
$menu-text-color-light: #303133; $menu-text-color-light: $--color-text-primary;
//暗色菜单的文字颜色 //暗色菜单的文字颜色
$menu-text-color-dark: rgba(255, 255, 255, .65); $menu-text-color-dark: rgba(255, 255, 255, .65);
//亮色菜单的文字hover颜色 //亮色菜单的文字hover颜色
@ -89,17 +52,19 @@ $navbar-item-hover-color-dark: lighten($root-menu-background-dark, 5%);
//多页签栏高度 //多页签栏高度
$tags-view-height: 32px; $tags-view-height: 32px;
//页头 //页头高用于max-view-height
$page-header-line-height: 26px; $page-header-height: 44px;
//页头的上下padding //页头的上下padding
$page-header-padding: 12px; $page-header-padding: 12px;
//路由页面的margin //路由页面的margin
$page-view-margin: 24px; $page-view-margin: 24px;
//亮色边框的颜色使用的element-ui原定义 //页脚高度用于max-view-height
$border-color-light: #dcdfe6; $page-footer-height: 64px;
//暗色边框的颜色
$border-color-dark: darken($root-menu-background-dark, 5%); //暗色边框的颜色用于nav-menu和侧边栏
$--border-color-dark: darken($root-menu-background-dark, 5%);
//dialog距离顶部的距离用于<el-dialog>的top属性<el-dialog>中滚动区域的最大高度 //dialog距离顶部的距离用于<el-dialog>的top属性<el-dialog>中滚动区域的最大高度
$dialog-top: 100px; $dialog-top: 100px;

@ -6,13 +6,16 @@ export default {
mixins: [common], mixins: [common],
props: ['img'], props: {
img: String,
label: String
},
render() { render() {
return ( return (
<div class="img-checkbox" on-click={this.click}> <div class="img-checkbox" title={this.label} on-click={this.click}>
<img src={this.img}/> <img src={this.img}/>
{this.checked && <i class="el-icon-check"/>} {this.checked && <i className="el-icon-check"/>}
</div> </div>
) )
} }
@ -20,7 +23,7 @@ export default {
</script> </script>
<style lang="scss"> <style lang="scss">
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.img-checkbox { .img-checkbox {
width: 55px; width: 55px;

@ -86,11 +86,11 @@ export default {
</script> </script>
<style lang="scss"> <style lang="scss">
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.context-menu { .context-menu {
margin: 0; margin: 0;
background: $menu-background-dark; background-color: $menu-background-dark;
z-index: 10; z-index: 10;
position: fixed; position: fixed;
list-style-type: none; list-style-type: none;

@ -1,9 +1,9 @@
<script type="text/jsx"> <script type="text/jsx">
import cssVariables from '@/asset/style/variables.scss' import cssVar from '@/asset/style/var.scss'
import Item from './item' import Item from './item'
import {isEmpty, deepClone, trim} from "@/util" import {isEmpty, deepClone, trim} from "@/util"
const inlineIndent = parseFloat(cssVariables.menuPadding) const inlineIndent = parseFloat(cssVar.menuPadding)
export default { export default {
name: 'NavMenu', name: 'NavMenu',

@ -1,4 +1,4 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.el-menu { .el-menu {
//图标的大小 //图标的大小

@ -28,7 +28,7 @@
//设置了显示弹出菜单的父级 //设置了显示弹出菜单的父级
&.el-menu--popup .popover-menu__title { &.el-menu--popup .popover-menu__title {
color: $menu-text-hover-color-dark; color: $menu-text-hover-color-dark;
border-bottom-color: $border-color-dark; border-bottom-color: $--border-color-dark;
} }
} }
} }

@ -16,7 +16,7 @@
//弹出菜单的父级 //弹出菜单的父级
&.el-menu--popup .popover-menu__title { &.el-menu--popup .popover-menu__title {
color: $menu-text-hover-color-light; color: $menu-text-hover-color-light;
border-bottom-color: $border-color-light; border-bottom-color: $--border-color-light;
} }
} }
} }

@ -12,17 +12,7 @@ module.exports = {
//路由配置 //路由配置
route: { route: {
//路由模式,['hash','history'] //路由模式,['hash','history']
mode: 'history', mode: 'history'
//路由过渡动画设置,关联transition.css
animate: {
//当未启用多页签时的路由动画
default: 'el-fade-in-linear',
//要访问的tab顺序高于上一个访问的tab时的路由动画
next: 'left-out',
//要访问的tab顺序不高于上一个访问的tab时的路由动画
prev: 'right-out',
}
}, },
//本地存储配置 //本地存储配置

@ -1,82 +0,0 @@
export default {
bind(el, bind, vnode) {
const dialogHeaderEl = el.querySelector('.el-dialog__header')
const dragDom = el.querySelector('.el-dialog')
dialogHeaderEl.style.setProperty('cursor', 'move')
dialogHeaderEl.addEventListener('mousedown', e => {
// 鼠标按下,计算当前元素距离可视区的距离
const disX = e.clientX - dialogHeaderEl.offsetLeft
const disY = e.clientY - dialogHeaderEl.offsetTop
const dragDomWidth = dragDom.offsetWidth
const dragDomHeight = dragDom.offsetHeight
const screenWidth = document.body.clientWidth
const screenHeight = document.body.clientHeight
const minDragDomLeft = dragDom.offsetLeft
const maxDragDomLeft = screenWidth - minDragDomLeft - dragDomWidth
const minDragDomTop = dragDom.offsetTop
const maxDragDomTop = screenHeight - minDragDomTop - dragDomHeight
// 获取到的值带px 正则匹配替换
let {left: styL, top: styT} = window.getComputedStyle(dragDom)
if (styL.includes('%')) {
styL = +document.body.clientWidth * (+styL.replace(/%/g, '') / 100)
styT = +document.body.clientHeight * (+styT.replace(/%/g, '') / 100)
}
else {
styL = +styL.replace(/px/g, '')
styT = +styT.replace(/px/g, '')
}
function onMousemove(e) {
// 通过事件委托,计算移动的距离
let left = e.clientX - disX
let top = e.clientY - disY
// 边界处理
if (-(left) > minDragDomLeft) {
left = -minDragDomLeft
}
else if (left > maxDragDomLeft) {
left = maxDragDomLeft
}
if (-(top) > minDragDomTop) {
top = -minDragDomTop
}
else if (top > maxDragDomTop) {
top = maxDragDomTop
}
// 移动当前元素
dragDom.style.setProperty('left', `${left + styL}px`)
dragDom.style.setProperty('top', `${top + styT}px`)
}
function onMouseup() {
window.removeEventListener('mousemove', onMousemove)
window.removeEventListener('mouseup', onMouseup)
}
window.addEventListener('mousemove', onMousemove)
window.addEventListener('mouseup', onMouseup)
})
function resetStyle() {
dragDom.style.removeProperty('left')
dragDom.style.removeProperty('top')
}
//当dialog关闭时恢复原位
vnode.componentInstance.$on('closed', resetStyle)
vnode.componentInstance.$once('hook:beforeDestroy', () => {
vnode.componentInstance.$off('closed', resetStyle)
})
}
}

@ -1,5 +0,0 @@
import Vue from 'vue'
import dragDialog from './dragDialog'
Vue.directive('drag-dialog', dragDialog)

@ -36,7 +36,7 @@ export default {
</script> </script>
<style lang="scss"> <style lang="scss">
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
// //
.collapse .aside-search { .collapse .aside-search {
@ -50,7 +50,7 @@ export default {
// //
.dark .aside-search .el-input__inner { .dark .aside-search .el-input__inner {
border: none; border: none;
color: #ffffff; color: $--color-white;
background-color: lighten($menu-background-dark, 5%); background-color: lighten($menu-background-dark, 5%);
} }
</style> </style>

@ -1,4 +1,5 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
@import "~@/asset/style/mixin.scss";
.aside { .aside {
display: flex; display: flex;

@ -10,15 +10,15 @@
} }
.root-sidebar { .root-sidebar {
border-right-color: $border-color-dark; border-right-color: $--border-color-dark;
} }
.sub-sidebar-title { .sub-sidebar-title {
color: #ffffff; color: $--color-white;
} }
.hamburger { .hamburger {
border-top-color: $border-color-dark; border-top-color: $--border-color-dark;
i { i {
color: $menu-text-color-dark; color: $menu-text-color-dark;

@ -1,11 +1,11 @@
.aside.light { .aside.light {
.root-sidebar { .root-sidebar {
background-color: #ffffff; background-color: $--color-white;
border-right-color: $border-color-light; border-right-color: $--border-color-light;
} }
.hamburger { .hamburger {
border-top-color: $border-color-light; border-top-color: $--border-color-light;
i { i {
color: $menu-text-color-light; color: $menu-text-color-light;

@ -26,7 +26,7 @@ export default {
</script> </script>
<style lang="scss"> <style lang="scss">
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
$logoSize: 30px; $logoSize: 30px;

@ -1,4 +1,4 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.navbar { .navbar {
display: flex; display: flex;

@ -5,7 +5,7 @@
color: $navbar-item-color-dark; color: $navbar-item-color-dark;
&:hover { &:hover {
background: $navbar-item-hover-color-dark; background-color: $navbar-item-hover-color-dark;
} }
} }
} }

@ -1,11 +1,11 @@
.navbar.light { .navbar.light {
background-color: #ffffff; background-color: $--color-white;
.navbar-item { .navbar-item {
color: $navbar-item-color-light; color: $navbar-item-color-light;
&:hover { &:hover {
background: $navbar-item-hover-color-light; background-color: $navbar-item-hover-color-light;
} }
} }
} }

@ -5,9 +5,7 @@ export default {
render() { render() {
return ( return (
<el-backtop target=".page-main .scroll-container" visibility-height={400} bottom={66}> <el-backtop target=".page-main .scroll-container" visibility-height={400} bottom={66}>
<div class="back-to-top">
<v-icon icon="el-icon-top"/> <v-icon icon="el-icon-top"/>
</div>
</el-backtop> </el-backtop>
) )
} }

@ -13,10 +13,11 @@ export default {
</script> </script>
<style lang="scss"> <style lang="scss">
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.page-footer { .page-footer {
padding: 48px $page-view-margin $page-view-margin $page-view-margin; height: $page-footer-height;
padding: $page-view-margin;
text-align: center; text-align: center;
.copyright { .copyright {

@ -32,7 +32,7 @@ export default {
</script> </script>
<style lang="scss"> <style lang="scss">
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.page-header { .page-header {
display: flex; display: flex;
@ -40,16 +40,16 @@ export default {
align-items: center; align-items: center;
flex-wrap: nowrap; flex-wrap: nowrap;
font-size: 14px; font-size: 14px;
line-height: $page-header-line-height; height: $page-header-height;
padding: $page-header-padding $page-view-margin $page-header-padding $page-view-margin; padding: $page-header-padding $page-view-margin $page-header-padding $page-view-margin;
> .el-breadcrumb .no-redirect { > .el-breadcrumb .no-redirect {
color: #909399; color: $--color-text-secondary;
cursor: text; cursor: text;
} }
&-title { &-title {
color: #303133; color: $--color-text-primary;
font-weight: 600; font-weight: 600;
font-size: 18px; font-size: 18px;
overflow: hidden; overflow: hidden;

@ -1,4 +1,4 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.tags-view-container { .tags-view-container {
height: $tags-view-height; height: $tags-view-height;
@ -21,10 +21,10 @@
cursor: pointer; cursor: pointer;
height: #{$tags-view-height - $margin * 2}; height: #{$tags-view-height - $margin * 2};
line-height: #{$tags-view-height - $margin * 2 - $border-width * 2}; line-height: #{$tags-view-height - $margin * 2 - $border-width * 2};
color: #909399; color: $--color-text-secondary;
background-color: #ffffff; background-color: #ffffff;
border-radius: 3px; border-radius: 3px;
border: $border-width solid $border-color-light; border: $border-width solid $--border-color-base;
padding: 0 12px; padding: 0 12px;
font-size: 12px; font-size: 12px;
margin: $margin; margin: $margin;
@ -54,7 +54,7 @@
color: $--color-primary; color: $--color-primary;
&::before { &::before {
background: $--color-primary; background-color: $--color-primary;
} }
} }

@ -17,13 +17,17 @@ export default {
return pageGetters.showPageHeader && this.$route.meta.pageHeader !== false return pageGetters.showPageHeader && this.$route.meta.pageHeader !== false
}, },
pageClass() { pageClass() {
return {'scroll-container': true, 'has-page-header': this.renderPageHeader} return {
'scroll-container': true,
'has-page-header': this.renderPageHeader,
'has-page-footer': true
}
} }
}, },
render() { render() {
const {showIframe, iframeList, currentIframe} = pageGetters const {transition, showIframe, iframeList, currentIframe} = pageGetters
const {cachedViews, transitionName, enabled} = tagsViewGetters const {cachedViews, enabled} = tagsViewGetters
return ( return (
<main class="page-main"> <main class="page-main">
@ -34,7 +38,7 @@ export default {
<page-view <page-view
include={cachedViews} include={cachedViews}
transition-name={transitionName} transition-name={transition.curr}
cacheable={enabled} cacheable={enabled}
/> />
@ -47,7 +51,7 @@ export default {
id={src} id={src}
key={src} key={src}
src={src} src={src}
frameborder="0" frameBorder="0"
height="100%" height="100%"
width="100%" width="100%"
/> />
@ -60,38 +64,4 @@ export default {
} }
</script> </script>
<style lang="scss"> <style lang="scss" src="./style.scss"></style>
@import "~@/asset/style/variables.scss";
.page-main {
display: flex;
flex-direction: column;
flex: 1;
position: relative;
overflow: hidden;
background-color: #f0f2f5;
> .scroll-container {
display: flex;
flex: 1;
flex-direction: column;
overflow-y: overlay;
overflow-x: inherit;
> .page-view {
margin: $page-view-margin;
flex: 1;
}
}
.back-to-top {
height: 100%;
width: 100%;
background-color: #f2f5f6;
box-shadow: 0 0 6px rgba(0, 0, 0, .12);
text-align: center;
line-height: 40px;
color: #1989fa;
}
}
</style>

@ -0,0 +1,23 @@
@import "~@/asset/style/var";
.page-main {
display: flex;
flex-direction: column;
flex: 1;
position: relative;
overflow: hidden;
background-color: #f0f2f5;
> .scroll-container {
display: flex;
flex: 1;
flex-direction: column;
overflow-y: overlay;
overflow-x: inherit;
> .page-view {
margin: $page-view-margin;
flex: 1;
}
}
}

@ -7,20 +7,13 @@
@close="$emit('input', false)" @close="$emit('input', false)"
> >
<div class="drawer-container"> <div class="drawer-container">
<el-divider>主题色</el-divider>
<div class="drawer-item">
<checkbox-group :value="appGetters.color" @input="changeThemeColor">
<color-checkbox v-for="i in colors" :key="i" :value="i"/>
</checkbox-group>
</div>
<el-divider>导航模式</el-divider> <el-divider>导航模式</el-divider>
<div class="drawer-item"> <div class="drawer-item">
<checkbox-group :value="appGetters.navMode" @input="changeNavMode"> <checkbox-group :value="appGetters.navMode" @input="changeNavMode">
<img-checkbox <img-checkbox
v-for="{title, value, img} in navModes" v-for="{label, value, img} in navModes"
:key="value" :key="value"
:title="title" :label="label"
:value="value" :value="value"
:img="img" :img="img"
/> />
@ -131,8 +124,6 @@
</template> </template>
<script> <script>
import client from 'webpack-theme-color-replacer/client'
import forElementUI from 'webpack-theme-color-replacer/forElementUI'
import CheckboxGroup from "@/component/checkbox/Group" import CheckboxGroup from "@/component/checkbox/Group"
import ColorCheckbox from "@/component/checkbox/ColorCheckbox" import ColorCheckbox from "@/component/checkbox/ColorCheckbox"
import ImgCheckbox from "@/component/checkbox/ImgCheckbox" import ImgCheckbox from "@/component/checkbox/ImgCheckbox"
@ -155,25 +146,24 @@ export default {
return { return {
appGetters, asideGetters, navbarGetters, pageGetters, tagsViewGetters, appGetters, asideGetters, navbarGetters, pageGetters, tagsViewGetters,
colors: ['#f5222d', '#fa541c', '#fadb14', '#3eaf7c', '#13c2c2', '#1890ff', '#722ed1', '#eb2f96'],
navModes: [ navModes: [
{ {
title: '侧边栏导航', label: '侧边栏导航',
value: 'aside', value: 'aside',
img: 'https://gw.alipayobjects.com/zos/antfincdn/XwFOFbLkSM/LCkqqYNmvBEbokSDscrm.svg' img: 'https://gw.alipayobjects.com/zos/antfincdn/XwFOFbLkSM/LCkqqYNmvBEbokSDscrm.svg'
}, },
{ {
title: '顶部导航', label: '顶部导航',
value: 'head', value: 'head',
img: 'https://gw.alipayobjects.com/zos/antfincdn/URETY8%24STp/KDNDBbriJhLwuqMoxcAr.svg' img: 'https://gw.alipayobjects.com/zos/antfincdn/URETY8%24STp/KDNDBbriJhLwuqMoxcAr.svg'
}, },
{ {
title: '混合导航', label: '混合导航',
value: 'mix', value: 'mix',
img: 'https://gw.alipayobjects.com/zos/antfincdn/x8Ob%26B8cy8/LCkqqYNmvBEbokSDscrm.svg' img: 'https://gw.alipayobjects.com/zos/antfincdn/x8Ob%26B8cy8/LCkqqYNmvBEbokSDscrm.svg'
}, },
{ {
title: '双层侧边栏导航', label: '双层侧边栏导航',
value: 'aside-two-part', value: 'aside-two-part',
img: 'https://gw.alipayobjects.com/zos/antfincdn/XwFOFbLkSM/LCkqqYNmvBEbokSDscrm.svg' img: 'https://gw.alipayobjects.com/zos/antfincdn/XwFOFbLkSM/LCkqqYNmvBEbokSDscrm.svg'
} }
@ -181,7 +171,6 @@ export default {
setting: { setting: {
app: { app: {
color: '#1890ff',
navMode: 'mix' navMode: 'mix'
}, },
page: { page: {
@ -238,10 +227,6 @@ export default {
setLocalPersonalSettings(this.setting) setLocalPersonalSettings(this.setting)
}, },
changeThemeColor(v) {
client.changer.changeColor({newColors: forElementUI.getElementUISeries(v)})
appMutations.color(v)
},
changeNavMode(v) { changeNavMode(v) {
appMutations.navMode(v) appMutations.navMode(v)
}, },
@ -315,14 +300,13 @@ export default {
setLocalPersonalSettings(this.setting) setLocalPersonalSettings(this.setting)
this.syncLayoutStore() this.syncLayoutStore()
//
this.changeThemeColor(this.setting.app.color)
} }
} }
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>
@import "~@/asset/style/var";
.drawer-container { .drawer-container {
padding: 24px; padding: 24px;
font-size: 14px; font-size: 14px;
@ -332,7 +316,7 @@ export default {
.drawer-item { .drawer-item {
display: flex; display: flex;
justify-content: space-between; justify-content: space-between;
color: #606266; color: $--color-text-regular;
font-size: 14px; font-size: 14px;
padding: 12px 0; padding: 12px 0;
} }

@ -1,7 +1,4 @@
import {route as routeConfig} from '@/config' import {getters as pageGetters, mutations as pageViewMutations} from "@/layout/store/page"
import {mutations as tagsViewMutations} from "@/layout/store/tagsView"
const {animate} = routeConfig
export default { export default {
watch: { watch: {
@ -13,7 +10,9 @@ export default {
methods: { methods: {
//根据访问的tab页的左右顺序来确定路由动画 //根据访问的tab页的左右顺序来确定路由动画
decideRouteTransition(to, from) { decideRouteTransition(to, from) {
let transitionName = animate.prev const {next, prev} = pageGetters.transition
let transitionName = prev
//这里认为页签数量不会太多,所以为了可读性使用两次循环查找 //这里认为页签数量不会太多,所以为了可读性使用两次循环查找
const fromIndex = this.visitedViews.findIndex(i => i.path === from.path) const fromIndex = this.visitedViews.findIndex(i => i.path === from.path)
@ -21,10 +20,10 @@ export default {
//新开tab也认为顺序高于上一个tab //新开tab也认为顺序高于上一个tab
if (toIndex === -1 || fromIndex < toIndex) { if (toIndex === -1 || fromIndex < toIndex) {
transitionName = animate.next transitionName = next
} }
tagsViewMutations.transitionName(transitionName) pageViewMutations.transition({curr: transitionName})
}, },
} }
} }

@ -17,8 +17,6 @@ const state = {
//所有的树形菜单,每个元素为顶部菜单,顶部菜单的子级(如果有)为侧边栏菜单 //所有的树形菜单,每个元素为顶部菜单,顶部菜单的子级(如果有)为侧边栏菜单
menus: [], menus: [],
//主题色
color: '#1890ff',
//导航模式,'aside'、'aside-two-part'、'head'、'mix' //导航模式,'aside'、'aside-two-part'、'head'、'mix'
navMode: 'mix' navMode: 'mix'
} }

@ -6,6 +6,18 @@ import {bindThis} from "@/util"
import {createGetters, createMutations} from "@/util/observable" import {createGetters, createMutations} from "@/util/observable"
const state = { const state = {
//路由过渡动画
transition: {
//当未启用多页签时的路由动画
default: 'el-fade-in-linear',
//要访问的tab顺序高于上一个访问的tab时的路由动画
next: 'left-out',
//要访问的tab顺序不高于上一个访问的tab时的路由动画
prev: 'right-out',
//当前使用的路由动画
curr: 'el-fade-in-linear'
},
/*iframe的控制*/ /*iframe的控制*/
showIframe: false, showIframe: false,
currentIframe: '', currentIframe: '',
@ -28,6 +40,11 @@ export const getters = createGetters(store)
export const mutations = bindThis({ export const mutations = bindThis({
...createMutations(store), ...createMutations(store),
//修改transition时使用Object.assign
transition(obj) {
Object.assign(store.transition, obj)
},
addIframe(src) { addIframe(src) {
!store.iframeList.includes(src) && store.iframeList.push(src) !store.iframeList.includes(src) && store.iframeList.push(src)
}, },

@ -2,8 +2,7 @@
* 多页签的响应式数据 * 多页签的响应式数据
*/ */
import Vue from 'vue' import Vue from 'vue'
import {route as routeConfig} from "@/config" import {getters as pageGetters, mutations as pageMutations} from "@/layout/store/page"
import {mutations as pageMutations} from "@/layout/store/page"
import {getRouterViewCacheKey} from "@/layout/util" import {getRouterViewCacheKey} from "@/layout/util"
import {bindThis} from "@/util" import {bindThis} from "@/util"
import {createGetters, createMutations} from "@/util/observable" import {createGetters, createMutations} from "@/util/observable"
@ -20,10 +19,7 @@ const state = {
visitedViews: [], visitedViews: [],
//缓存的页签,用于<keep-router-view-alive/>:include //缓存的页签,用于<keep-router-view-alive/>:include
cachedViews: [], cachedViews: []
//路由过渡动画名称
transitionName: routeConfig.animate.default
} }
const store = Vue.observable(state) const store = Vue.observable(state)
@ -42,7 +38,7 @@ export const mutations = bindThis({
store.enabled = v store.enabled = v
if (!v) { if (!v) {
this.transitionName(routeConfig.animate.default) pageMutations.transition({curr: pageGetters.transition.default})
this.delAllTagAndCache() this.delAllTagAndCache()
} }
}, },

@ -6,7 +6,6 @@ import App from '@/App'
import store from '@/store' import store from '@/store'
import router from '@/router' import router from '@/router'
import '@/asset/icon' import '@/asset/icon'
import '@/directive'
import filters from './filter' import filters from './filter'
Vue.use(Element) Vue.use(Element)

@ -1,6 +1,5 @@
import store from "@/store" import store from "@/store"
import {isEmpty} from "@/util" import {isLogin, auth, needAuth} from "@/util/auth"
import {auth, needAuth} from "@/util/auth"
const noLoginList = ['/login', '/register', '/403', '/404', '/500'] const noLoginList = ['/login', '/register', '/403', '/404', '/500']
@ -11,7 +10,7 @@ const beforeEach = async (to, from, next) => {
} }
//未登录时返回登录页 //未登录时返回登录页
if (isEmpty(store.state.user.id, store.state.user.token)) { if (!isLogin()) {
return next({path: '/login', query: {redirect: to.fullPath}}) return next({path: '/login', query: {redirect: to.fullPath}})
} }

@ -1,11 +0,0 @@
export default {
path: 'directive',
meta: {title: '全局指令', icon: 'el-icon-s-grid', alwaysShow: true},
children: [
{
path: 'dragDialog',
component: 'example/directive/dragDialog',
meta: {title: '可拖拽dialog'}
}
]
}

@ -9,35 +9,28 @@ import {shakeTree} from "@/util/tree"
import {isExternal} from "@/util/validate" import {isExternal} from "@/util/validate"
const state = { const state = {
//权限映射表:<权限路径,权限id>,用于util.auth
resourceMap: {},
//判断权限是否已经初始化 //判断权限是否已经初始化
init: false init: false
} }
const mutations = { const mutations = {
resource(state, {data, admin}) {
state.resourceMap = {}
},
init(state, sign) { init(state, sign) {
state.init = sign state.init = sign
} }
} }
const actions = { const actions = {
init({state, commit}, {admin}) { init({state, commit}) {
return new Promise(resolve => { return new Promise(resolve => {
commit('resource', {data: [], admin})
const routes = getDynamicRoutes() const routes = getDynamicRoutes()
metaExtend(routes) metaExtend(routes)
//动态添加路由,这里不需要进行权限过滤 //动态添加路由,这里不需要进行权限过滤
//可能存在多次调用的情况,所以仅在第一次调用时添加进vue-router //可能存在多次调用的情况,所以仅在第一次调用时添加进vue-router
!state.init && addDynamicRoutes(routes) !state.init && addDynamicRoutes(routes)
//生成经过权限过滤后的菜单 //生成经过权限过滤后的菜单,并传递给layout的store
appMutations.menus(getAuthorizedMenus(routes)) appMutations.menus(getAuthorizedMenus(routes))
//设置初始化完成的标志 //设置初始化完成的标志
@ -51,17 +44,6 @@ const actions = {
//获取经过权限控制后的菜单 //获取经过权限控制后的菜单
function getAuthorizedMenus(menus) { function getAuthorizedMenus(menus) {
menus = deepClone(menus) menus = deepClone(menus)
clean(menus)
addFullPath(menus)
return shakeTree(menus, i => {
//非叶子节点时,当定义了children属性却没有子节点时移除
if (i.children && i.children.length === 0) {
return false
}
return !needAuth(i) || auth(i.fullPath)
})
}
//删除不显示的菜单(没有children且没有meta.title) //删除不显示的菜单(没有children且没有meta.title)
function clean(menus) { function clean(menus) {
@ -102,6 +84,19 @@ function addFullPath(routes, basePath = '/') {
}) })
} }
clean(menus)
addFullPath(menus)
return shakeTree(menus, i => {
//非叶子节点时,当定义了children属性却没有子节点时移除
if (i.children && i.children.length === 0) {
return false
}
return !needAuth(i) || auth(i.fullPath)
})
}
export default { export default {
namespaced: true, namespaced: true,
state, state,

@ -25,33 +25,29 @@ const mutations = createMutations(state, true)
const actions = { const actions = {
login({commit, dispatch}, userInfo) { login({commit, dispatch}, userInfo) {
const {username, password} = userInfo const {username, password} = userInfo
if (username !== 'admin') {
elError('登录时请用admin作为用户名!')
return Promise.reject()
}
const user = {id: 1, admin: true, name: username, avatar: null, token: 'token'} const user = {id: 1, admin: true, name: username, avatar: null, token: 'token'}
commit('$all', user) commit('$all', user)
setUser(user) setUser(user)
return Promise.resolve() return Promise.resolve()
}, },
logout({commit, state, dispatch}) { logout({commit, state, dispatch}) {
return new Promise((resolve, reject) => {
if (state.prepareLogout) return Promise.reject() if (state.prepareLogout) return Promise.reject()
commit('prepareLogout', true) commit('prepareLogout', true)
commit('resource/init', false, {root: true})
Promise.all([ return Promise.all([
dispatch('removeUser'), dispatch('removeUser'),
tagsViewMutations.delAllTagAndCache() tagsViewMutations.delAllTagAndCache()
]) ])
.then(() => { .then(() => window.location.reload())
resolve()
window.location.reload()
})
.finally(() => commit('prepareLogout', false)) .finally(() => commit('prepareLogout', false))
})
}, },
//刷新本地存储中保存的用户数据
refresh({state}) { refresh({state}) {
setUser(state) setUser(state)
}, },

@ -27,13 +27,7 @@ export function needAuth(route) {
* @return {boolean} * @return {boolean}
*/ */
export function auth(path) { export function auth(path) {
if (store.state.user.admin === true) return true return true
const resourceMap = store.state.resource.resourceMap
if (!(path in resourceMap)) return true
const resources = store.state.user.resources
return resources && path in resources
} }
/** /**
@ -53,3 +47,12 @@ export function wic(apiMap) {
return attrs return attrs
} }
/**
* 判断是否已登录已登录则返回true
*
* @return {boolean}
*/
export function isLogin() {
return !isEmpty(store.state.user.token)
}

@ -1,6 +1,6 @@
import cssVariables from '@/asset/style/variables.scss' import cssVar from '@/asset/style/var.scss'
const maxMobileWidth = parseFloat(cssVariables.maxMobileWidth) const maxMobileWidth = parseFloat(cssVar.maxMobileWidth)
/** /**
* 根据body宽度判断是否为移动端是则返回true * 根据body宽度判断是否为移动端是则返回true

@ -1,5 +1,7 @@
<template> <template>
<div class="login-page"> <div class="login-page">
<canvas id="login-background"/>
<div class="login-container" @click.stop> <div class="login-container" @click.stop>
<div class="title"> <div class="title">
{{ title }} {{ title }}

@ -1,16 +1,20 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
$bg: #283443;
$light_gray: #ffffff;
$dark_gray: #889aa4;
$cursor: #ffffff;
.login-page { .login-page {
$background-color: #2d3a4b;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
height: 100%; height: 100%;
overflow: auto; overflow: auto;
background: #2d3a4b;
canvas {
position: absolute;
height: 100%;
width: 100%;
z-index: -1;
background-color: $background-color;
}
.login-container { .login-container {
flex: 1; flex: 1;
@ -25,14 +29,22 @@ $cursor: #ffffff;
margin-bottom: 40px; margin-bottom: 40px;
cursor: pointer; cursor: pointer;
font-size: 26px; font-size: 26px;
color: #eee; color: #ffffff;
font-weight: bold; font-weight: bold;
position: relative; position: relative;
.set-animation {
position: absolute;
top: 115px;
font-size: 18px;
right: 10px;
cursor: pointer;
}
} }
.svg-container { .svg-container {
padding: 6px 5px 6px 0; padding: 6px 5px 6px 0;
color: $dark_gray; color: $--color-text-secondary;
vertical-align: middle; vertical-align: middle;
display: inline-block; display: inline-block;
} }
@ -42,7 +54,7 @@ $cursor: #ffffff;
right: 10px; right: 10px;
top: 7px; top: 7px;
font-size: 16px; font-size: 16px;
color: $dark_gray; color: $--color-text-secondary;
cursor: pointer; cursor: pointer;
user-select: none; user-select: none;
} }
@ -53,26 +65,20 @@ $cursor: #ffffff;
width: 85%; width: 85%;
input { input {
background: transparent; background-color: transparent;
border: 0; border: 0;
-webkit-appearance: none; -webkit-appearance: none;
border-radius: 0; border-radius: 0;
padding: 12px 5px 12px 15px; padding: 12px 5px 12px 15px;
color: $light_gray; color: #ffffff;
height: 47px; height: 47px;
caret-color: $cursor;
&:-webkit-autofill {
box-shadow: 0 0 0 1000px $bg inset !important;
-webkit-text-fill-color: $cursor !important;
}
} }
} }
.el-form-item { .el-form-item {
border: 1px solid rgba(255, 255, 255, 0.1); border: 1px solid rgba(255, 255, 255, 0.1);
border-radius: 5px; border-radius: 5px;
background: rgba(0, 0, 0, 0.1); background-color: rgba(0, 0, 0, 0.1);
margin-bottom: 22px; margin-bottom: 22px;
} }

@ -1,4 +1,5 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
@import "~@/asset/style/mixin.scss";
.exception { .exception {
width: 100%; width: 100%;
@ -16,7 +17,7 @@
.content { .content {
h1 { h1 {
color: #434e59; color: $--color-text-primary;
font-size: 72px; font-size: 72px;
font-weight: 600; font-weight: 600;
line-height: 72px; line-height: 72px;
@ -24,7 +25,7 @@
} }
.desc { .desc {
color: rgba(0, 0, 0, .45); color: $--color-text-secondary;
font-size: 20px; font-size: 20px;
line-height: 28px; line-height: 28px;
margin-bottom: 16px; margin-bottom: 16px;

@ -1,4 +1,4 @@
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.skeleton-page-wrapper { .skeleton-page-wrapper {
margin: $page-view-margin; margin: $page-view-margin;

@ -40,14 +40,14 @@ export default {
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>
@import "~@/asset/style/variables.scss"; @import "~@/asset/style/var";
.q-skeleton + .q-skeleton { .q-skeleton + .q-skeleton {
margin-top: 20px; margin-top: 20px;
} }
.bg-primary { .bg-primary {
background: $--color-primary; background-color: $--color-primary;
} }
.bg-info { .bg-info {

@ -1,25 +0,0 @@
<template>
<div>
<div class="tip-row">
可拖拽的dialog
</div>
<el-button @click="value = true">打开dialog</el-button>
<el-dialog v-drag-dialog :visible.sync="value" title="我可以拖动">
<div>蛤蛤</div>
</el-dialog>
</div>
</template>
<script>
export default {
name: "dragDialogPage",
data() {
return {
value: false
}
}
}
</script>

@ -1,8 +1,6 @@
'use strict' 'use strict'
const path = require('path') const path = require('path')
const settings = require('./src/config') const settings = require('./src/config')
const ThemeColorReplacer = require('webpack-theme-color-replacer')
const forElementUI = require('webpack-theme-color-replacer/forElementUI')
function resolve(dir) { function resolve(dir) {
return path.join(__dirname, dir) return path.join(__dirname, dir)
@ -33,15 +31,7 @@ module.exports = {
'@': resolve('src'), '@': resolve('src'),
'@ele': resolve('element-ui-personal') '@ele': resolve('element-ui-personal')
} }
}, }
plugins: [
new ThemeColorReplacer({
fileName: 'css/theme-colors.[contenthash:8].css',
matchColors: forElementUI.getElementUISeries('#1890ff'),
changeSelector: forElementUI.changeSelector,
injectCss: true
})
]
}, },
chainWebpack(config) { chainWebpack(config) {
config.plugins.delete('preload') config.plugins.delete('preload')

Loading…
Cancel
Save