提交 03b6025d 作者: nebv

refactor(style): remove tailwind css

上级 66b56169
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
VITE_PORT = 3100 VITE_PORT = 3100
# spa-title # spa-title
VITE_GLOB_APP_TITLE = vben admin 2.0 VITE_GLOB_APP_TITLE = Vben Admin 2.0
# spa shortname # spa shortname
VITE_GLOB_APP_SHORT_NAME = vue_vben_admin_2x VITE_GLOB_APP_SHORT_NAME = vue_vben_admin_2x
...@@ -47,6 +47,8 @@ ...@@ -47,6 +47,8 @@
[2.0 在线预览](https://vvbin.cn/next/) [2.0 在线预览](https://vvbin.cn/next/)
测试账号: vben/123456
<p align="center"> <p align="center">
<img alt="VbenAdmin Logo" width="100%" src="./.github/res/imgs/preview1.png"> <img alt="VbenAdmin Logo" width="100%" src="./.github/res/imgs/preview1.png">
<img alt="VbenAdmin Logo" width="100%" src="./.github/res/imgs/preview2.png"> <img alt="VbenAdmin Logo" width="100%" src="./.github/res/imgs/preview2.png">
......
...@@ -82,7 +82,6 @@ ...@@ -82,7 +82,6 @@
"stylelint-config-prettier": "^8.0.2", "stylelint-config-prettier": "^8.0.2",
"stylelint-config-standard": "^20.0.0", "stylelint-config-standard": "^20.0.0",
"stylelint-order": "^4.1.0", "stylelint-order": "^4.1.0",
"tailwindcss": "^1.8.13",
"tasksfile": "^5.1.1", "tasksfile": "^5.1.1",
"ts-node": "^9.0.0", "ts-node": "^9.0.0",
"typescript": "^4.0.3", "typescript": "^4.0.3",
......
const path = require('path'); const path = require('path');
module.exports = { module.exports = {
plugins: [require('tailwindcss'), require('autoprefixer'), require('postcss-import')], plugins: [require('autoprefixer'), require('postcss-import')],
}; };
...@@ -37,7 +37,7 @@ ...@@ -37,7 +37,7 @@
</script> </script>
<style lang="less" scoped> <style lang="less" scoped>
.base-arrow { .base-arrow {
transform: rotate(-90deg) !important; transform: rotate(-90deg);
transition: all 0.3s ease 0.1s; transition: all 0.3s ease 0.1s;
transform-origin: center center; transform-origin: center center;
...@@ -50,9 +50,10 @@ ...@@ -50,9 +50,10 @@
} }
&__active { &__active {
> span { transform: rotate(90deg);
transform: rotate(90deg) !important; // > span {
} // transform: rotate(90deg);
// }
} }
} }
</style> </style>
<template> <template>
<div class="collapse-container p-2 bg:white rounded-sm"> <div class="collapse-container p-2">
<CollapseHeader v-bind="$props" :show="show" @expand="handleExpand" /> <CollapseHeader v-bind="$props" :show="show" @expand="handleExpand" />
<CollapseTransition :enable="canExpan"> <CollapseTransition :enable="canExpan">
<Skeleton v-if="loading" /> <Skeleton v-if="loading" />
...@@ -92,7 +92,6 @@ ...@@ -92,7 +92,6 @@
</script> </script>
<style lang="less"> <style lang="less">
.collapse-container { .collapse-container {
padding: 10px;
background: #fff; background: #fff;
border-radius: 8px; border-radius: 8px;
transition: all 0.3s ease-in-out; transition: all 0.3s ease-in-out;
......
...@@ -73,7 +73,9 @@ export default defineComponent({ ...@@ -73,7 +73,9 @@ export default defineComponent({
return ( return (
<li class={`${prefixCls}__item ${disabled ? 'disabled' : ''}`} key={label}> <li class={`${prefixCls}__item ${disabled ? 'disabled' : ''}`} key={label}>
<a onClick={handleAction.bind(null, item)}>{renderContent(item)}</a> <a onClick={handleAction.bind(null, item)} style="color:#333;">
{renderContent(item)}
</a>
</li> </li>
); );
}); });
......
...@@ -64,6 +64,7 @@ export default defineComponent({ ...@@ -64,6 +64,7 @@ export default defineComponent({
return { return {
fontSize: `${fs}px`, fontSize: `${fs}px`,
color, color,
display: 'inline-flex',
}; };
}); });
......
<template> <template>
<section class="flex justify-center items-center flex-col"> <section class="basic-loading">
<img <img
src="/@/assets/images/loading.svg" src="/@/assets/images/loading.svg"
alt="" alt=""
...@@ -47,3 +47,11 @@ ...@@ -47,3 +47,11 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.basic-loading {
display: flex;
justify-content: center;
align-items: center;
flex-direction: column;
}
</style>
<template> <template>
<section <section class="full-loading" :style="getStyle">
class="full-loading flex justify-center bg-mask-light items-center h-full w-full"
:style="getStyle"
>
<BasicLoading :tip="tip" :size="SizeEnum.DEFAULT" /> <BasicLoading :tip="tip" :size="SizeEnum.DEFAULT" />
</section> </section>
</template> </template>
...@@ -39,3 +36,13 @@ ...@@ -39,3 +36,13 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.full-loading {
display: flex;
width: 100%;
height: 100%;
background: rgba(255, 255, 255, 0.3);
justify-content: center;
align-items: center;
}
</style>
@import './helper/distance.less';
// 生成样式
.distance();
.hidden {
display: none !important;
}
.flex {
display: flex;
}
.flex-wrap {
flex-wrap: wrap;
}
.justify-center {
justify-content: center;
}
.items-center {
align-items: center;
}
.justify-start {
justify-content: start;
}
.justify-end {
justify-content: end;
}
.justify-around {
justify-content: space-around;
}
.relative {
position: relative;
}
.absolute {
position: absolute;
}
.ellipsis {
overflow: hidden;
text-overflow: ellipsis;
word-wrap: normal;
white-space: nowrap;
}
@import 'loop.less';
// margin 步长
@margin-size-base: 4;
// 最大生成
@margin-size-max: 10;
// padding步长
@padding-size-base: 4;
// 最大生成
@padding-size-max: 10;
.distance() {
// 生成margin
.loop (m, margin, 1, @margin-size-base, @margin-size-max);
.loop (mt, margin-top, 1, @margin-size-base, @margin-size-max);
.loop (mr, margin-right, 1, @margin-size-base, @margin-size-max);
.loop (mb, margin-bottom, 1, @margin-size-base, @margin-size-max);
.loop (ml, margin-left, 1, @margin-size-base, @margin-size-max);
.loop (my, margin, 1, @margin-size-base, @margin-size-max, y);
.loop (mx, margin, 1, @margin-size-base, @margin-size-max, x);
.loop (mx-auto, margin, 1, @padding-size-base, @padding-size-max, autoX);
.loop (my-auto, margin, 1, @padding-size-base, @padding-size-max, autoY);
.loop (m-auto, margin, 1, @padding-size-base, @padding-size-max, auto);
// 生成padding
.loop (p, padding, 1, @padding-size-base, @padding-size-max);
.loop (pt, padding-top, 1, @padding-size-base, @padding-size-max);
.loop (pr, padding-right, 1, @padding-size-base, @padding-size-max);
.loop (pb, padding-bottom, 1, @padding-size-base, @padding-size-max);
.loop (pl, padding-left, 1, @padding-size-base, @padding-size-max);
.loop (py, padding, 1, @padding-size-base, @padding-size-max, y);
.loop (px, padding, 1, @padding-size-base, @padding-size-max, x);
.loop (px-auto, padding, 1, @padding-size-base, @padding-size-max, autoX);
.loop (py-auto, padding, 1, @padding-size-base, @padding-size-max, autoY);
.loop (p-auto, padding, 1, @padding-size-base, @padding-size-max, auto);
}
.loop (@style-name, @tag-name, @i,@base-size, @max:10,@xy:none) when (@i <= @max) {
@next: @i+1;
.fn() when (@xy =none) {
@size: @base-size * @i;
.@{style-name}-@{i} {
@{tag-name}: ~'@{size}px ';
}
.loop(@style-name, @tag-name, @next, @base-size, @max, @xy);
}
.fn() when (@xy =x) {
@size: @base-size * @i;
@tnl: ~'@{tag-name}-left';
@tnr: ~'@{tag-name}-right';
.@{style-name}-@{i} {
@{tnl}: ~'@{size}px';
@{tnr}: ~'@{size}px';
}
.loop(@style-name, @tag-name, @next, @base-size, @max, @xy);
}
.fn() when (@xy =y) {
@size: @base-size * @i;
@tnt: ~'@{tag-name}-top';
@tnb: ~'@{tag-name}-bottom';
.@{style-name}-@{i} {
@{tnt}: ~'@{size}px';
@{tnb}: ~'@{size}px';
}
.loop(@style-name, @tag-name, @next, @base-size, @max, @xy);
}
.fn() when (@xy =auto) {
@tnt: ~'@{tag-name}-top';
@tnb: ~'@{tag-name}-bottom';
@tnl: ~'@{tag-name}-left';
@tnr: ~'@{tag-name}-right';
.@{style-name} {
@{tnl}: ~'auto';
@{tnr}: ~'auto';
@{tnt}: ~'auto';
@{tnb}: ~'auto';
}
}
.fn() when (@xy =autoX) {
@tnl: ~'@{tag-name}-left';
@tnr: ~'@{tag-name}-right';
.@{style-name} {
@{tnl}: ~'auto';
@{tnr}: ~'auto';
}
}
.fn() when (@xy =autoY) {
@tnt: ~'@{tag-name}-top';
@tnb: ~'@{tag-name}-bottom';
.@{style-name} {
@{tnt}: ~'auto';
@{tnb}: ~'auto';
}
}
.fn();
}
...@@ -3,6 +3,7 @@ ...@@ -3,6 +3,7 @@
@import 'public.less'; @import 'public.less';
@import 'mixins.less'; @import 'mixins.less';
@import 'ant/index.less'; @import 'ant/index.less';
@import './global.less';
*, *,
*::before, *::before,
......
@import 'tailwindcss/base';
@import 'tailwindcss/components';
@import 'tailwindcss/utilities';
...@@ -42,13 +42,6 @@ ...@@ -42,13 +42,6 @@
user-select: none; user-select: none;
} }
.ellipsis {
overflow: hidden;
text-overflow: ellipsis;
word-wrap: normal;
white-space: nowrap;
}
/* 适用于webkit内核和移动端 */ /* 适用于webkit内核和移动端 */
.ellipsis-multiple(@num: 1) { .ellipsis-multiple(@num: 1) {
display: -webkit-box; display: -webkit-box;
...@@ -56,3 +49,54 @@ ...@@ -56,3 +49,54 @@
-webkit-box-orient: vertical; -webkit-box-orient: vertical;
-webkit-line-clamp: @num; -webkit-line-clamp: @num;
} }
.respond-to (small, @content) {
@media only screen and (min-width: @screen-sm-min) {
@content();
}
}
.respond-to (medium, @content) {
@media only screen and (min-width: @screen-md-min) {
@content();
}
}
.respond-to (large, @content) {
@media only screen and (min-width: @screen-lg-min) {
@content();
}
}
.respond-to (xlarge, @content) {
@media only screen and (min-width: @screen-xl-min) {
@content();
}
}
.respond-to (xsmall-only, @content) {
@media only screen and (max-width: @screen-xs-max) {
@content();
}
}
.respond-to (small-only, @content) {
@media only screen and (min-width: @screen-sm-min) and (max-width: @screen-sm-max) {
@content();
}
}
.respond-to (medium-only, @content) {
@media only screen and (min-width: @screen-md-min) and (max-width: @screen-md-max) {
@content();
}
}
.respond-to (large-only, @content) {
@media only screen and (min-width: @screen-lg-min) and (max-width: @screen-lg-max) {
@content();
}
}
.respond-to (xsmall-and-small, @content) {
@media only screen and (max-width: @screen-sm-max) {
@content();
}
}
.respond-to (small-and-medium, @content) {
@media only screen and (min-width: @screen-sm-min) and (max-width: @screen-md-max) {
@content();
}
}
<template> <template>
<div class="flex justify-items-center items-center cursor-pointer" @click="handleGoHome"> <div class="app-logo" @click="handleGoHome">
<img :src="logo" /> <img :src="logo" />
<div v-if="show" class="logo-title ml-2 text-xl hidden md:block font-logo ellipsis">{{ <div v-if="show" class="logo-title ml-2 ellipsis">{{ globSetting.title }}</div>
globSetting.title
}}</div>
</div> </div>
</template> </template>
<script lang="ts"> <script lang="ts">
...@@ -52,3 +50,22 @@ ...@@ -52,3 +50,22 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
@import (reference) '../design/index.less';
.app-logo {
display: flex;
justify-content: center;
align-items: center;
cursor: pointer;
.logo-title {
display: none;
font-family: Georgia, serif;
font-size: 18px;
.respond-to(medium,{
display: block;
});
}
}
</style>
...@@ -65,7 +65,7 @@ export default defineComponent({ ...@@ -65,7 +65,7 @@ export default defineComponent({
return () => ( return () => (
<> <>
<Breadcrumb class="layout-breadcrumb flex-grow"> <Breadcrumb class="layout-breadcrumb ">
{() => ( {() => (
<> <>
<TransitionGroup name="breadcrumb"> <TransitionGroup name="breadcrumb">
......
...@@ -55,23 +55,17 @@ export default defineComponent({ ...@@ -55,23 +55,17 @@ export default defineComponent({
const isSidebarType = menuType === MenuTypeEnum.SIDEBAR; const isSidebarType = menuType === MenuTypeEnum.SIDEBAR;
return ( return (
<Layout.Header <Layout.Header class={['layout-header', 'flex p-0 px-4 ', unref(headerClass)]}>
class={[
'layout-header',
'bg-white flex p-0 px-4 justify-items-center',
unref(headerClass),
]}
>
{() => ( {() => (
<> <>
<div class="flex-grow flex justify-center items-center"> <div class="layout-header__content ">
{showLogo && !isSidebarType && <Logo class={`layout-header__logo`} />} {showLogo && !isSidebarType && <Logo class={`layout-header__logo`} />}
{mode !== MenuModeEnum.HORIZONTAL && showBreadCrumb && !splitMenu && ( {mode !== MenuModeEnum.HORIZONTAL && showBreadCrumb && !splitMenu && (
<LayoutBreadcrumb /> <LayoutBreadcrumb />
)} )}
{(mode === MenuModeEnum.HORIZONTAL || splitMenu) && ( {(mode === MenuModeEnum.HORIZONTAL || splitMenu) && (
<div class={[`layout-header__menu flex-grow `, `justify-${topMenuAlign}`]}> <div class={[`layout-header__menu `, `justify-${topMenuAlign}`]}>
<LayoutMenu <LayoutMenu
theme={headerTheme} theme={headerTheme}
splitType={splitMenu ? MenuSplitTyeEnum.TOP : MenuSplitTyeEnum.NONE} splitType={splitMenu ? MenuSplitTyeEnum.TOP : MenuSplitTyeEnum.NONE}
......
...@@ -191,9 +191,17 @@ ...@@ -191,9 +191,17 @@
height: @header-height; height: @header-height;
padding: 0 20px 0 0; padding: 0 20px 0 0;
color: @white; color: @white;
background: @white;
align-items: center; align-items: center;
justify-content: space-between; justify-content: space-between;
&__content {
flex-grow: 1;
display: flex;
justify-content: center;
align-items: center;
}
&__header--light { &__header--light {
background: @white; background: @white;
border-bottom: 1px solid @header-light-bottom-border-color; border-bottom: 1px solid @header-light-bottom-border-color;
...@@ -334,6 +342,7 @@ ...@@ -334,6 +342,7 @@
margin-left: 20px; margin-left: 20px;
overflow: hidden; overflow: hidden;
align-items: center; align-items: center;
flex-grow: 1;
} }
&__user-dropdown { &__user-dropdown {
...@@ -398,4 +407,5 @@ ...@@ -398,4 +407,5 @@
.layout-breadcrumb { .layout-breadcrumb {
padding: 0 16px; padding: 0 16px;
flex-grow: 1;
} }
<template> <template>
<div <div @click="openDrawer" class="setting-button">
@click="openDrawer"
class="setting-button bg-primary flex justify-center items-center text-white p-4 absolute z-10 cursor-pointer"
>
<SettingOutlined :spin="true" /> <SettingOutlined :spin="true" />
<SettingDrawer @register="register" /> <SettingDrawer @register="register" />
</div> </div>
...@@ -26,3 +23,18 @@ ...@@ -26,3 +23,18 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
@import (reference) '../../../design/index.less';
.setting-button {
position: absolute;
z-index: 10;
display: flex;
padding: 10px;
color: @white;
cursor: pointer;
background: @primary-color;
justify-content: center;
align-items: center;
}
</style>
...@@ -6,12 +6,13 @@ import { appStore } from '/@/store/modules/app'; ...@@ -6,12 +6,13 @@ import { appStore } from '/@/store/modules/app';
import { AppRouteRecordRaw } from '/@/router/types'; import { AppRouteRecordRaw } from '/@/router/types';
import { useRouter } from 'vue-router'; import { useRouter } from 'vue-router';
import router from '/@/router'; import router from '/@/router';
import { unique } from '/@/utils';
export function useFrameKeepAlive() { export function useFrameKeepAlive() {
const { currentRoute } = useRouter(); const { currentRoute } = useRouter();
function getAllFramePages(routes: AppRouteRecordRaw[]): AppRouteRecordRaw[] { function getAllFramePages(routes: AppRouteRecordRaw[]): AppRouteRecordRaw[] {
const res: AppRouteRecordRaw[] = []; let res: AppRouteRecordRaw[] = [];
for (const route of routes) { for (const route of routes) {
const { meta: { frameSrc } = {}, children } = route; const { meta: { frameSrc } = {}, children } = route;
if (frameSrc) { if (frameSrc) {
...@@ -21,6 +22,7 @@ export function useFrameKeepAlive() { ...@@ -21,6 +22,7 @@ export function useFrameKeepAlive() {
res.push(...getAllFramePages(children)); res.push(...getAllFramePages(children));
} }
} }
res = unique(res, 'name');
return res; return res;
} }
...@@ -30,6 +32,9 @@ export function useFrameKeepAlive() { ...@@ -30,6 +32,9 @@ export function useFrameKeepAlive() {
const getFramePages = computed(() => { const getFramePages = computed(() => {
const ret = const ret =
getAllFramePages((toRaw(router.getRoutes()) as unknown) as AppRouteRecordRaw[]) || []; getAllFramePages((toRaw(router.getRoutes()) as unknown) as AppRouteRecordRaw[]) || [];
console.log('======================');
console.log(ret);
console.log('======================');
return ret; return ret;
}); });
......
...@@ -10,7 +10,6 @@ import { isDevMode, isProdMode, isUseMock } from '/@/utils/env'; ...@@ -10,7 +10,6 @@ import { isDevMode, isProdMode, isUseMock } from '/@/utils/env';
import { setupProdMockServer } from '../mock/_createProductionServer'; import { setupProdMockServer } from '../mock/_createProductionServer';
import '/@/design/index.less'; import '/@/design/index.less';
import '/@/design/main.postcss';
const app = createApp(App); const app = createApp(App);
......
...@@ -59,7 +59,7 @@ const menu: MenuModule = { ...@@ -59,7 +59,7 @@ const menu: MenuModule = {
}, },
{ {
path: '/mergeHeader', path: '/mergeHeader',
name: '合并表头', name: '合并单元格',
}, },
{ {
path: '/expandTable', path: '/expandTable',
......
...@@ -183,7 +183,7 @@ export default { ...@@ -183,7 +183,7 @@ export default {
name: 'MergeHeaderDemo', name: 'MergeHeaderDemo',
component: () => import('/@/views/demo/table/MergeHeader.vue'), component: () => import('/@/views/demo/table/MergeHeader.vue'),
meta: { meta: {
title: '合并表头', title: '合并单元格',
}, },
}, },
{ {
......
...@@ -8,7 +8,7 @@ export default { ...@@ -8,7 +8,7 @@ export default {
path: '/permission', path: '/permission',
name: 'Permission', name: 'Permission',
component: PAGE_LAYOUT_COMPONENT, component: PAGE_LAYOUT_COMPONENT,
redirect: '/permission/front', redirect: '/permission/front/page',
meta: { meta: {
icon: 'carbon:user-role', icon: 'carbon:user-role',
title: '权限管理', title: '权限管理',
......
// import { FullLoading } from '/@/components/Loading/index';
// import { LoadTimeOut } from '/@/views/sys/exception/';
// /**
// * @description: Load page displayed by page switching
// */
// export const LOADING_PAGE = FullLoading;
// /**
// * @description: Switch to switch timeout page
// */
// export const TIMEOUT_PAGE = LoadTimeOut;
// /**
// * @description: If there is no response for the specified time, the loading page will be displayed
// * 400 m
// */
// export const DELAY = 400;
// /**
// * @description: Switch page if there is no response for more than the specified time, the timeout page will be displayed
// * 10秒
// */
// export const TIMEOUT = 60 * 1000;
<template> <template>
<div class="h-full w-full flex justify-center items-center"> <div class="welcome">
<House /> <House />
</div> </div>
</template> </template>
...@@ -14,3 +14,12 @@ ...@@ -14,3 +14,12 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.welcome {
display: flex;
width: 100%;
height: 100%;
justify-content: center;
align-items: center;
}
</style>
<template> <template>
<div class="px-64"> <div class="px-10">
<Alert message="点内外部触发事件" show-icon class="mt-4"></Alert> <Alert message="点内外部触发事件" show-icon class="mt-4"></Alert>
<ClickOutSide @clickOutside="handleClickOutside" class="flex justify-center mt-10"> <ClickOutSide @clickOutside="handleClickOutside" class="flex justify-center mt-10">
<div <div @click="innerClick" class="demo-box">
@click="innerClick"
class="bg-primary w-full h-64 flex justify-center items-center text-2xl text-white rounded-lg shadow-lg"
>
{{ text }} {{ text }}
</div> </div>
</ClickOutSide> </ClickOutSide>
...@@ -30,3 +27,17 @@ ...@@ -30,3 +27,17 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.demo-box {
display: flex;
width: 100%;
height: 300px;
font-size: 24px;
color: #fff;
background: #408ede;
border-radius: 10px;
justify-content: center;
align-items: center;
}
</style>
...@@ -8,11 +8,11 @@ ...@@ -8,11 +8,11 @@
<a-button @click="scrollTo(0)" class="mr-2">滚动到顶部</a-button> <a-button @click="scrollTo(0)" class="mr-2">滚动到顶部</a-button>
<a-button @click="scrollBottom()" class="mr-2">滚动到底部</a-button> <a-button @click="scrollBottom()" class="mr-2">滚动到底部</a-button>
</div> </div>
<div class="w-1/2 h-64 bg-white"> <div class="scroll-wrap">
<ScrollContainer class="mt-4" ref="scrollRef"> <ScrollContainer class="mt-4" ref="scrollRef">
<ul class="p-3"> <ul class="p-3">
<template v-for="index in 100" :key="index"> <template v-for="index in 100" :key="index">
<li class="leading-8 px-2" :style="{ border: '1px solid #eee' }">{{ index }}</li> <li class="p-2" :style="{ border: '1px solid #eee' }">{{ index }}</li>
</template> </template>
</ul> </ul>
</ScrollContainer> </ScrollContainer>
...@@ -50,3 +50,10 @@ ...@@ -50,3 +50,10 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.scroll-wrap {
width: 50%;
height: 300px;
background: #fff;
}
</style>
...@@ -9,9 +9,9 @@ ...@@ -9,9 +9,9 @@
</VirtualScroll> </VirtualScroll>
</div> </div>
<Divider>即使不可见,也预先加载30条数据,防止空白</Divider> <Divider>即使不可见,也预先加载50条数据,防止空白</Divider>
<div class="virtual-scroll-demo-wrap"> <div class="virtual-scroll-demo-wrap">
<VirtualScroll :itemHeight="41" :items="data" :height="300" :width="300" :bench="30"> <VirtualScroll :itemHeight="41" :items="data" :height="300" :width="300" :bench="50">
<template v-slot="{ item }"> <template v-slot="{ item }">
<div class="virtual-scroll-demo__item">{{ item.title }}</div> <div class="virtual-scroll-demo__item">{{ item.title }}</div>
</template> </template>
......
<template> <template>
<div class="p-4"> <div class="p-4">
<Alert message="抽取el-scrollbar,并对其进行扩展,滚动条美化,适用于各个浏览器" type="info" /> <Alert message="抽取el-scrollbar,并对其进行扩展,滚动条美化,适用于各个浏览器" type="info" />
<div class="w-1/2 h-64 bg-white"> <div class="scroll-wrap">
<ScrollContainer class="mt-4"> <ScrollContainer class="mt-4">
<ul class="p-3"> <ul class="p-3">
<template v-for="index in 100" :key="index"> <template v-for="index in 100" :key="index">
<li class="leading-8 px-2" :style="{ border: '1px solid #eee' }">{{ index }}</li> <li class="p-2" :style="{ border: '1px solid #eee' }">{{ index }}</li>
</template> </template>
</ul> </ul>
</ScrollContainer> </ScrollContainer>
...@@ -24,3 +24,10 @@ ...@@ -24,3 +24,10 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.scroll-wrap {
width: 50%;
height: 300px;
background: #fff;
}
</style>
<template> <template>
<div class="p-4 flex justify-center"> <div class="p-4 flex justify-center">
<div class="w-1/2 bg-white p-10 rounded-md"> <div class="demo-wrap p-10">
<StrengthMeter placeholder="默认" /> <StrengthMeter placeholder="默认" />
<StrengthMeter placeholder="禁用" disabled /> <StrengthMeter placeholder="禁用" disabled />
<br /> <br />
...@@ -21,3 +21,10 @@ ...@@ -21,3 +21,10 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.demo-wrap {
width: 50%;
background: #fff;
border-radius: 10px;
}
</style>
...@@ -21,3 +21,8 @@ ...@@ -21,3 +21,8 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.bg-gray-700 {
background: #4a5568;
}
</style>
...@@ -88,3 +88,8 @@ ...@@ -88,3 +88,8 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.bg-gray-700 {
background: #4a5568;
}
</style>
<template> <template>
<div class="p-4"> <div class="p-4">
<CollapseContainer <CollapseContainer title="在下面输入框输入文本,切换后回来内容会保存">
class="px-20 bg-white w-full h-32 rounded-md"
title="在下面输入框输入文本,切换后回来内容会保存"
>
<a-input placeholder="请输入" /> <a-input placeholder="请输入" />
</CollapseContainer> </CollapseContainer>
<CollapseContainer class="px-20 mt-10 bg-white w-full h-32 rounded-md" title="标签页操作"> <CollapseContainer class="mt-4 px-4" title="标签页操作">
<a-button class="mr-2" @click="closeAll">关闭所有</a-button> <a-button class="mr-2" @click="closeAll">关闭所有</a-button>
<a-button class="mr-2" @click="closeLeft">关闭左侧</a-button> <a-button class="mr-2" @click="closeLeft">关闭左侧</a-button>
<a-button class="mr-2" @click="closeRight">关闭右侧</a-button> <a-button class="mr-2" @click="closeRight">关闭右侧</a-button>
......
<template> <template>
<div class="p-10 m-4 rounded-md bg-white"> <div class="p-4 m-4 demo">
<Alert message="刷新后会还原" show-icon /> <Alert message="刷新后会还原" show-icon />
<CurrentPermissionMode /> <CurrentPermissionMode />
...@@ -83,3 +83,8 @@ ...@@ -83,3 +83,8 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.demo {
background: #fff;
}
</style>
<template> <template>
<div class="p-10 m-4 rounded-md bg-white"> <div class="p-4 m-4 demo">
<Alert <Alert
message="目前mock了两组数据, id为1 和 2 具体返回的菜单可以在mock/sys/menu.ts内查看" message="目前mock了两组数据, id为1 和 2 具体返回的菜单可以在mock/sys/menu.ts内查看"
show-icon show-icon
...@@ -35,3 +35,8 @@ ...@@ -35,3 +35,8 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.demo {
background: #fff;
}
</style>
<template> <template>
<div class="m-10 bg-primary text-2xl h-64 rounded-lg flex justify-center items-center text-white"> <div class="m-10 auth-page"> Super 角色可见 </div>
Super 角色可见
</div>
</template> </template>
<script lang="ts"> <script lang="ts">
import { defineComponent } from 'vue'; import { defineComponent } from 'vue';
export default defineComponent({}); export default defineComponent({});
</script> </script>
<style lang="less" scoped>
.auth-page {
display: flex;
height: 300px;
font-size: 24px;
color: #fff;
background: #409efe;
border-radius: 12px;
justify-content: center;
align-items: center;
}
</style>
<template> <template>
<div class="m-10 bg-primary text-2xl h-64 rounded-lg flex justify-center items-center text-white"> <div class="m-10 auth-page"> Test 角色可见 </div>
Test 角色可见
</div>
</template> </template>
<script lang="ts"> <script lang="ts">
import { defineComponent } from 'vue'; import { defineComponent } from 'vue';
export default defineComponent({}); export default defineComponent({});
</script> </script>
<style lang="less" scoped>
.auth-page {
display: flex;
height: 300px;
font-size: 24px;
color: #fff;
background: #409efe;
border-radius: 12px;
justify-content: center;
align-items: center;
}
</style>
<template> <template>
<div class="p-10 m-4 rounded-md bg-white"> <div class="demo p-4 m-4">
<Alert <Alert
message="由于刷新的时候会请求用户信息接口,会根据接口重置角色信息,所以刷新后界面会恢复原样,如果不需要,可以注释 src/layout/default/index内的获取用户信息接口" message="由于刷新的时候会请求用户信息接口,会根据接口重置角色信息,所以刷新后界面会恢复原样,如果不需要,可以注释 src/layout/default/index内的获取用户信息接口"
show-icon show-icon
...@@ -82,3 +82,8 @@ ...@@ -82,3 +82,8 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.demo {
background: #fff;
}
</style>
<template> <template>
<div class="p-10 m-4 rounded-md bg-white"> <div class="p-4 m-4 demo">
<Alert <Alert
message="由于刷新的时候会请求用户信息接口,会根据接口重置角色信息,所以刷新后界面会恢复原样,如果不需要,可以注释 src/layout/default/index内的获取用户信息接口" message="由于刷新的时候会请求用户信息接口,会根据接口重置角色信息,所以刷新后界面会恢复原样,如果不需要,可以注释 src/layout/default/index内的获取用户信息接口"
show-icon show-icon
...@@ -46,3 +46,8 @@ ...@@ -46,3 +46,8 @@
}, },
}); });
</script> </script>
<style lang="less" scoped>
.demo {
background: #fff;
}
</style>
...@@ -17,7 +17,7 @@ ...@@ -17,7 +17,7 @@
<a-button @click="deleteNodeByKey('2-2')" class="mr-2">删除parent3节点</a-button> <a-button @click="deleteNodeByKey('2-2')" class="mr-2">删除parent3节点</a-button>
<a-button @click="updateNodeByKey('1-1')" class="mr-2">更新parent2节点</a-button> <a-button @click="updateNodeByKey('1-1')" class="mr-2">更新parent2节点</a-button>
</div> </div>
<CollapseContainer title="函数操作" class="w-1/3 mr-4" :canExpan="false"> <CollapseContainer title="函数操作" class="mr-4" :canExpan="false" :style="{ width: '33%' }">
<BasicTree :treeData="treeData" ref="treeRef" :checkable="true" /> <BasicTree :treeData="treeData" ref="treeRef" :checkable="true" />
</CollapseContainer> </CollapseContainer>
</div> </div>
......
<template> <template>
<div class="flex p-4"> <div class="flex p-4">
<CollapseContainer title="右侧操作按钮" class="w-1/3 mr-4"> <CollapseContainer title="右侧操作按钮" class="mr-4" :style="{ width: '33%' }">
<BasicTree :treeData="treeData" :actionList="actionList" /> <BasicTree :treeData="treeData" :actionList="actionList" />
</CollapseContainer> </CollapseContainer>
<CollapseContainer title="右键菜单" class="w-1/3 mr-4"> <CollapseContainer title="右键菜单" class="mr-4" :style="{ width: '33%' }">
<BasicTree :treeData="treeData" :beforeRightClick="getRightMenuList" /> <BasicTree :treeData="treeData" :beforeRightClick="getRightMenuList" />
</CollapseContainer> </CollapseContainer>
</div> </div>
......
<template> <template>
<div class="flex p-4"> <div class="flex p-4">
<CollapseContainer title="基础示例" class="w-1/3 mr-4"> <CollapseContainer title="基础示例" :style="{ width: '33%' }" class="mr-4">
<BasicTree :treeData="treeData" /> <BasicTree :treeData="treeData" />
</CollapseContainer> </CollapseContainer>
<CollapseContainer title="可勾选" class="w-1/3 mr-4"> <CollapseContainer title="可勾选" class="mr-4" :style="{ width: '33%' }">
<BasicTree :treeData="treeData" :checkable="true" /> <BasicTree :treeData="treeData" :checkable="true" />
</CollapseContainer> </CollapseContainer>
<CollapseContainer title="默认展开/勾选示例" class="w-1/3"> <CollapseContainer title="默认展开/勾选示例" :style="{ width: '33%' }">
<BasicTree <BasicTree
:treeData="treeData" :treeData="treeData"
:checkable="true" :checkable="true"
......
<template>
<h1>{{ msg }}</h1>
<a-button @click="test">change </a-button>
<div class="sw">
<Scrollbar ref="a">
<div class="ss">13123</div>
</Scrollbar>
</div>
<a-button @click="test1" type="primary">change</a-button>
<ScrollYTransition>
<div class="box" v-show="show"> 1 </div>
</ScrollYTransition>
<!-- <BasicModal /> -->
</template>
<script lang="ts">
import { defineComponent, ref } from 'vue';
import { Scrollbar } from '/@/components/Scrollbar/index';
import { ScrollContainer } from '/@/components/Container/index';
import { defHttp } from '/@/utils/http/axios';
import { useThemeMode } from '/@/useApp';
import { useMessage } from '/@/hooks/web/useMessage';
import {
CollapseTransition,
ExpandXTransition,
ScaleTransition,
ScaleRotateTransition,
ScrollYTransition,
} from '/@/components/Transition';
import { ThemeModeEnum } from '../enums/appEnum';
// import { BasicModal } from '/@/components/modal';
export default defineComponent({
name: 'Home',
components: {
Scrollbar,
CollapseTransition,
ExpandXTransition,
ScaleTransition,
ScaleRotateTransition,
ScrollYTransition,
ScrollContainer,
// BasicModal
},
setup() {
const { createMessage } = useMessage();
createMessage.success({
content: '123',
duration: 999999,
});
// createMessage.error('123');
// createMessage.info('123');
// createMessage.warning('123');
// createConfirm({
// iconType: 'success',
// title: '123',
// content: '123',
// });
const { runChangeThemeMode } = useThemeMode(ThemeModeEnum.DARK);
let msg = ref('hello Home');
const show = ref(true);
function test() {
msg.value = 'hello Home1';
}
defHttp.request({
method: 'post',
url: '/login',
params: {
username: 'vben',
password: '123456',
},
});
const a = ref(null);
function test1() {
runChangeThemeMode();
// show.value = !show.value;
// a.value.scrollTo(200);
}
return {
a,
msg,
test,
show,
test1,
};
},
});
</script>
<style lang="less" scoped>
.sw {
width: 300px;
height: 300px;
border: 1px solid red;
.scrollbar {
height: 100%;
}
.ss {
height: 500px;
}
}
.box {
width: 200px;
height: 200px;
background: #000;
}
</style>
...@@ -15,6 +15,7 @@ import { useRoute } from 'vue-router'; ...@@ -15,6 +15,7 @@ import { useRoute } from 'vue-router';
import { useGo, useRedo } from '/@/hooks/web/usePage'; import { useGo, useRedo } from '/@/hooks/web/usePage';
import { PageEnum } from '/@/enums/pageEnum'; import { PageEnum } from '/@/enums/pageEnum';
import './exception.less';
interface MapValue { interface MapValue {
title: string; title: string;
subTitle: string; subTitle: string;
...@@ -105,7 +106,7 @@ export default defineComponent({ ...@@ -105,7 +106,7 @@ export default defineComponent({
const { title, subTitle, btnText, icon, handler } = unref(getMapValue) || {}; const { title, subTitle, btnText, icon, handler } = unref(getMapValue) || {};
return ( return (
<Result <Result
class="flex items-center flex-col" class="exception "
title={props.title || title} title={props.title || title}
sub-title={props.subTitle || subTitle} sub-title={props.subTitle || subTitle}
> >
......
.exception {
display: flex;
align-items: center;
flex-direction: column;
}
<template> <template>
<div class="login h-screen relative"> <div class="login">
<div class="login-mask h-full hidden lg:block" /> <div class="login-mask" />
<div <div class="login-form-wrap">
class="h-full absolute right-0 top-0 w-full lg:w-2/5 xl:w-1/3 flex justify-center items-center" <div class="login-form mx-6">
> <div class="login-form__content px-2 py-10">
<div class="login-form bg-white w-full rounded-sm border-solid bg-clip-padding mx-6 xl:mx-14"> <header>
<div class="w-full h-full border border-gray-600 px-2 py-10 rounded-sm"> <img src="/@/assets/images/logo.png" class="mr-4" />
<header class="flex justify-center items-center"> <h1>{{ title }}</h1>
<img src="/@/assets/images/logo.png" class="w-12 mr-4 inline-block" />
<h1 class="text-2xl text-center text-primary tracking-wide">Vben Admin 2.0</h1>
</header> </header>
<a-form class="w-4/5 mx-auto mt-10" :model="formData" :rules="formRules" ref="formRef"> <a-form class="mx-auto mt-10" :model="formData" :rules="formRules" ref="formRef">
<a-form-item name="account"> <a-form-item name="account">
<a-input size="large" v-model:value="formData.account" placeholder="vben" /> <a-input size="large" v-model:value="formData.account" placeholder="vben" />
</a-form-item> </a-form-item>
...@@ -50,9 +48,11 @@ ...@@ -50,9 +48,11 @@
import { userStore } from '/@/store/modules/user'; import { userStore } from '/@/store/modules/user';
import { appStore } from '/@/store/modules/app'; import { appStore } from '/@/store/modules/app';
import { useMessage } from '/@/hooks/web/useMessage'; import { useMessage } from '/@/hooks/web/useMessage';
import { useSetting } from '/@/hooks/core/useSetting';
export default defineComponent({ export default defineComponent({
components: { BasicDragVerify }, components: { BasicDragVerify },
setup() { setup() {
const { globSetting } = useSetting();
const { notification } = useMessage(); const { notification } = useMessage();
const formRef = ref<any>(null); const formRef = ref<any>(null);
const verifyRef = ref<RefInstanceType<DragVerifyActionType>>(null); const verifyRef = ref<RefInstanceType<DragVerifyActionType>>(null);
...@@ -115,23 +115,79 @@ ...@@ -115,23 +115,79 @@
formRules, formRules,
login: handleLogin, login: handleLogin,
openLoginVerify: openLoginVerifyRef, openLoginVerify: openLoginVerifyRef,
title: globSetting && globSetting.title,
}; };
}, },
}); });
</script> </script>
<style lang="less" scoped> <style lang="less" scoped>
@import (reference) '../../../design/index.less';
.login { .login {
position: relative;
height: 100vh;
background: url(../../../assets/images/login/login-bg.png) no-repeat; background: url(../../../assets/images/login/login-bg.png) no-repeat;
background-size: 100% 100%; background-size: 100% 100%;
&-mask { &-mask {
display: none;
height: 100%;
background: url(../../../assets/images/login/login-in.png) no-repeat; background: url(../../../assets/images/login/login-in.png) no-repeat;
background-size: 100% 100%; background-size: 100% 100%;
.respond-to(large, { display: block;});
} }
&-form { &-form {
border-color: rgba(255, 255, 255, 0.5); width: 100%;
background: @white;
border: 10px solid rgba(255, 255, 255, 0.5);
border-width: 10px; border-width: 10px;
border-radius: 4px;
background-clip: padding-box;
.respond-to(xlarge, { margin: 0 56px});
&-wrap {
position: absolute;
top: 0;
right: 0;
display: flex;
width: 100%;
height: 100%;
justify-content: center;
align-items: center;
.respond-to(large, { width: 40%;});
.respond-to(xlarge, { width: 33.3%;});
}
&__content {
width: 100%;
height: 100%;
border: 1px solid #999;
border-radius: 2px;
header {
display: flex;
justify-content: center;
align-items: center;
img {
display: inline-block;
width: 48px;
}
h1 {
margin-bottom: 0;
font-size: 24px;
color: @primary-color;
text-align: center;
}
}
form {
width: 80%;
}
}
} }
} }
</style> </style>
// #4c5eb8
const { colors, inset } = require('tailwindcss/defaultTheme');
const themeColors = {
mask: {
light: 'rgba(255,255,255,0.3)',
},
primary: '#018ffb',
success: '#55d187',
warning: '#ffd164',
danger: '#ed6f6f',
};
module.exports = {
purge: {
enabled: process.env.NODE_ENV === 'production',
content: [
'./index.html',
'./src/**/*.vue',
'./src/**/*.js',
'./src/**/*.jsx',
'./src/**/*.ts',
'./src/**/*.tsx',
],
},
theme: {
colors: {
...colors,
...themeColors,
},
inset: {
...inset,
'1/2': '50%',
},
screens: {
xs: '480px',
sm: '576px',
md: '768px',
lg: '992px',
xl: '1200px',
xxl: '1600px',
},
fontSize: {
xs: '.75rem', // 12px
sm: '.875rem', // 14px
base: '1rem', // 16px
lg: '1.125rem', // 18px
xl: '1.25rem', // 20px
'2xl': '1.5rem', // 24px
'3xl': '1.875rem', // 30px
'4xl': '2.25rem', // 36px
'5xl': '3rem', // 48px
'6xl': '4rem', // 64px
logo: '9rem', // 134px
},
fontWeight: {
light: 300,
normal: 400,
medium: 500,
semibold: 600,
bold: 700,
extrabold: 800,
black: 900,
},
fontFamily: {
logo: [' Georgia', 'serif'],
},
},
future: {
// 2.0 remove col-gap-{n}
removeDeprecatedGapUtilities: true,
purgeLayersByDefault: true,
},
};
...@@ -23,9 +23,6 @@ ...@@ -23,9 +23,6 @@
"paths": { "paths": {
"/@/*": [ "/@/*": [
"src/*" "src/*"
],
"/@design/": [
"src/design/index.less"
] ]
} }
}, },
......
Markdown 格式
0%
您添加了 0 到此讨论。请谨慎行事。
请先完成此评论的编辑!
注册 或者 后发表评论