Compare commits
2
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ed364f6343 | ||
|
|
2b378b0343 |
No files matched your search
+92
-43
@@ -1,14 +1,20 @@
|
|||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
|
import { h, onMounted, reactive, ref, shallowRef } from 'vue'
|
||||||
import { h, onMounted, reactive, ref, shallowRef } from 'vue';
|
import { NIcon, NScrollbar, NDropdown, NQrCode } from 'naive-ui'
|
||||||
import { NIcon, NScrollbar, NDropdown, NQrCode } from 'naive-ui';
|
import {
|
||||||
import { EyeOffOutline, EyeOutline, CloseOutline, CopyOutline, EllipsisVertical, QrCodeOutline } from '@vicons/ionicons5'
|
EyeOffOutline,
|
||||||
import miaoDirectory from './views/miaoDirectory.vue';
|
EyeOutline,
|
||||||
import VirtualPage from './class/VirtualPage';
|
CloseOutline,
|
||||||
import VirtualDirectory, { VirtualFile } from './class/VirtualDirectory';
|
CopyOutline,
|
||||||
import MiaoMask from './components/miaoMask.vue';
|
EllipsisVertical,
|
||||||
import config from './config';
|
QrCodeOutline
|
||||||
import useViretualPages from './hooks/useVirtualPages';
|
} from '@vicons/ionicons5'
|
||||||
|
import miaoDirectory from './views/miaoDirectory.vue'
|
||||||
|
import VirtualPage from './class/VirtualPage'
|
||||||
|
import VirtualDirectory, { VirtualFile } from './class/VirtualDirectory'
|
||||||
|
import MiaoMask from './components/miaoMask.vue'
|
||||||
|
import config from './config'
|
||||||
|
import useVirtualPages from './hooks/useVirtualPages'
|
||||||
|
|
||||||
const { baseUrl } = config
|
const { baseUrl } = config
|
||||||
|
|
||||||
@@ -19,22 +25,32 @@ const modalData = shallowRef<{
|
|||||||
props: any
|
props: any
|
||||||
}>()
|
}>()
|
||||||
|
|
||||||
const views = useViretualPages()
|
const views = useVirtualPages()
|
||||||
|
|
||||||
const rootDirectory = reactive(new VirtualDirectory({
|
const rootDirectory = reactive(
|
||||||
|
new VirtualDirectory({
|
||||||
name: '根目录',
|
name: '根目录',
|
||||||
stats: {
|
stats: {
|
||||||
atimeMs: 0,
|
atimeMs: 0,
|
||||||
birthtimeMs: 0,
|
birthtimeMs: 0,
|
||||||
ctimeMs: 0,
|
ctimeMs: 0,
|
||||||
mtimeMs: 0,
|
mtimeMs: 0
|
||||||
}
|
}
|
||||||
}))
|
})
|
||||||
|
)
|
||||||
|
|
||||||
// component就是一个vue组件,类似于miaoDirectory
|
// component就是一个vue组件,类似于miaoDirectory
|
||||||
const createView = (component: any, currentObjects: (VirtualDirectory | VirtualFile)[], index?: number) => {
|
const createView = (
|
||||||
|
component: any,
|
||||||
|
currentObjects: (VirtualDirectory | VirtualFile)[],
|
||||||
|
index?: number
|
||||||
|
) => {
|
||||||
index ?? (index = views.length)
|
index ?? (index = views.length)
|
||||||
views.splice(index, 0, reactive<VirtualPage>(new VirtualPage(component, [...currentObjects])))
|
views.splice(
|
||||||
|
index,
|
||||||
|
0,
|
||||||
|
reactive<VirtualPage>(new VirtualPage(component, [...currentObjects]))
|
||||||
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
const deleteView = (index: number) => {
|
const deleteView = (index: number) => {
|
||||||
@@ -46,7 +62,7 @@ const deleteView = (index: number) => {
|
|||||||
|
|
||||||
// 点击标题是隐藏其他标签或显示其他标签,还挺好用的
|
// 点击标题是隐藏其他标签或显示其他标签,还挺好用的
|
||||||
const handleClickTitle = (index: number) => {
|
const handleClickTitle = (index: number) => {
|
||||||
let count = views.filter(v => v.visible).length
|
let count = views.filter((v) => v.visible).length
|
||||||
let op = !views[index].visible || count > 1 ? 'hideOthers' : 'showOthers'
|
let op = !views[index].visible || count > 1 ? 'hideOthers' : 'showOthers'
|
||||||
let _index = 0
|
let _index = 0
|
||||||
while (_index < views.length) {
|
while (_index < views.length) {
|
||||||
@@ -59,7 +75,6 @@ const handleClickTitle = (index: number) => {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// 顶部菜单相关
|
// 顶部菜单相关
|
||||||
function renderIcon(icon: any) {
|
function renderIcon(icon: any) {
|
||||||
return () => {
|
return () => {
|
||||||
@@ -102,19 +117,43 @@ onMounted(() => {
|
|||||||
<n-scrollbar x-scrollable>
|
<n-scrollbar x-scrollable>
|
||||||
<div class="tags-container">
|
<div class="tags-container">
|
||||||
<transition-group name="tab">
|
<transition-group name="tab">
|
||||||
<div class="tab" v-for="(view, index) of views" :key="view.uid">
|
<div
|
||||||
<div class="tab-title" @click="handleClickTitle(index)">{{ view.title }}</div>
|
class="tab"
|
||||||
<div class="tab-point" :style="{ backgroundColor: view.color }"></div>
|
v-for="(view, index) of views"
|
||||||
|
:key="view.uid">
|
||||||
|
<div
|
||||||
|
class="tab-title"
|
||||||
|
@click="handleClickTitle(index)">
|
||||||
|
{{ view.title }}
|
||||||
|
</div>
|
||||||
|
<div
|
||||||
|
class="tab-point"
|
||||||
|
:style="{ backgroundColor: view.color }"></div>
|
||||||
<div class="tab-control">
|
<div class="tab-control">
|
||||||
<n-icon class="tag-control-icon icon" @click="view.switchShow()">
|
<n-icon
|
||||||
<EyeOutline v-show="view.visible" class="icon-inner" />
|
class="tag-control-icon icon"
|
||||||
<EyeOffOutline v-show="!view.visible" class="icon-inner" />
|
@click="view.switchShow()">
|
||||||
|
<EyeOutline
|
||||||
|
v-show="view.visible"
|
||||||
|
class="icon-inner" />
|
||||||
|
<EyeOffOutline
|
||||||
|
v-show="!view.visible"
|
||||||
|
class="icon-inner" />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
<n-icon class="tag-control-icon icon"
|
<n-icon
|
||||||
@click="createView(view.component, view.currentObjects, index + 1)">
|
class="tag-control-icon icon"
|
||||||
|
@click="
|
||||||
|
createView(
|
||||||
|
view.component,
|
||||||
|
view.currentObjects,
|
||||||
|
index + 1
|
||||||
|
)
|
||||||
|
">
|
||||||
<CopyOutline />
|
<CopyOutline />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
<n-icon class="tag-control-icon icon" @click="deleteView(index)">
|
<n-icon
|
||||||
|
class="tag-control-icon icon"
|
||||||
|
@click="deleteView(index)">
|
||||||
<CloseOutline class="icon-inner" />
|
<CloseOutline class="icon-inner" />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
</div>
|
</div>
|
||||||
@@ -122,9 +161,12 @@ onMounted(() => {
|
|||||||
</transition-group>
|
</transition-group>
|
||||||
</div>
|
</div>
|
||||||
</n-scrollbar>
|
</n-scrollbar>
|
||||||
<div class="view-controler-menu">
|
<div class="view-controller-menu">
|
||||||
<div class="view-controler-menu-item">
|
<div class="view-controller-menu-item">
|
||||||
<n-dropdown trigger="click" :options="openMenuOption" @select="handleMenuSelect">
|
<n-dropdown
|
||||||
|
trigger="click"
|
||||||
|
:options="openMenuOption"
|
||||||
|
@select="handleMenuSelect">
|
||||||
<n-icon class="icon">
|
<n-icon class="icon">
|
||||||
<EllipsisVertical class="icon-inner" />
|
<EllipsisVertical class="icon-inner" />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
@@ -134,16 +176,26 @@ onMounted(() => {
|
|||||||
</div>
|
</div>
|
||||||
<div class="view-container">
|
<div class="view-container">
|
||||||
<transition-group name="page">
|
<transition-group name="page">
|
||||||
<div class="view-container-item" v-for="(view, index) of views" v-show="view.visible" :key="view.uid">
|
<div
|
||||||
<component :is="view.component" v-model:current-objects="view.currentObjects" :id="view.uid"
|
class="view-container-item"
|
||||||
:color="view.color" @exit="deleteView(index)"></component>
|
v-for="(view, index) of views"
|
||||||
|
v-show="view.visible"
|
||||||
|
:key="view.uid">
|
||||||
|
<component
|
||||||
|
:is="view.component"
|
||||||
|
v-model:current-objects="view.currentObjects"
|
||||||
|
:id="view.uid"
|
||||||
|
:color="view.color"
|
||||||
|
@exit="deleteView(index)"></component>
|
||||||
</div>
|
</div>
|
||||||
</transition-group>
|
</transition-group>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<!-- 模态框展示,用来显示分享二维码,设置菜单之类的东西 -->
|
<!-- 模态框展示,用来显示分享二维码,设置菜单之类的东西 -->
|
||||||
<MiaoMask v-model:show="showModal" @click="showModal = false">
|
<MiaoMask v-model:show="showModal" @click="showModal = false">
|
||||||
<component :is="modalData?.component" v-bind="modalData?.props"></component>
|
<component
|
||||||
|
:is="modalData?.component"
|
||||||
|
v-bind="modalData?.props"></component>
|
||||||
</MiaoMask>
|
</MiaoMask>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
@@ -205,7 +257,7 @@ $tag-width: 170px;
|
|||||||
|
|
||||||
&:not(:last-child)::after {
|
&:not(:last-child)::after {
|
||||||
content: '';
|
content: '';
|
||||||
height: calc($controler-height*0.6);
|
height: calc($controler-height * 0.6);
|
||||||
width: 1px;
|
width: 1px;
|
||||||
border-right: 1px solid black;
|
border-right: 1px solid black;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
@@ -214,13 +266,13 @@ $tag-width: 170px;
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.view-controler-menu {
|
.view-controller-menu {
|
||||||
position: relative;
|
position: relative;
|
||||||
display: flex;
|
display: flex;
|
||||||
align-items: center;
|
align-items: center;
|
||||||
padding: 0 5px;
|
padding: 0 5px;
|
||||||
|
|
||||||
.view-controler-menu-item {
|
.view-controller-menu-item {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
aspect-ratio: 1;
|
aspect-ratio: 1;
|
||||||
display: flex;
|
display: flex;
|
||||||
@@ -230,7 +282,7 @@ $tag-width: 170px;
|
|||||||
|
|
||||||
&::before {
|
&::before {
|
||||||
content: '';
|
content: '';
|
||||||
height: calc($controler-height*0.6);
|
height: calc($controler-height * 0.6);
|
||||||
width: 1px;
|
width: 1px;
|
||||||
border-right: 1px solid black;
|
border-right: 1px solid black;
|
||||||
position: absolute;
|
position: absolute;
|
||||||
@@ -295,7 +347,6 @@ $tag-width: 170px;
|
|||||||
.view {
|
.view {
|
||||||
.view-controler {
|
.view-controler {
|
||||||
.tags-container {
|
.tags-container {
|
||||||
|
|
||||||
.tab-move,
|
.tab-move,
|
||||||
.tab-enter-active {
|
.tab-enter-active {
|
||||||
transition: all 0.2s ease;
|
transition: all 0.2s ease;
|
||||||
@@ -321,13 +372,11 @@ $tag-width: 170px;
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.view-container {
|
// .view-container {
|
||||||
|
|
||||||
// .page-move {
|
// .page-move {
|
||||||
// transition: all 0.2s ease;
|
// transition: all 0.2s ease;
|
||||||
// }
|
// }
|
||||||
|
|
||||||
|
|
||||||
// .page-enter-active {
|
// .page-enter-active {
|
||||||
|
|
||||||
// }
|
// }
|
||||||
@@ -343,6 +392,6 @@ $tag-width: 170px;
|
|||||||
// .page-leave-active {
|
// .page-leave-active {
|
||||||
// position: absolute;
|
// position: absolute;
|
||||||
// }
|
// }
|
||||||
}
|
// }
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
File renamed without changes.
File renamed without changes.
@@ -1,7 +1,13 @@
|
|||||||
<template>
|
<template>
|
||||||
<div class="miao-item" draggable="true" ref="itemRef" @dragstart="handleDragStart">
|
<div
|
||||||
|
class="miao-item"
|
||||||
|
draggable="true"
|
||||||
|
ref="itemRef"
|
||||||
|
@dragstart="handleDragStart">
|
||||||
<div class="item-main">
|
<div class="item-main">
|
||||||
<div class="item-main-front" :style="{ backgroundColor: props.color }"></div>
|
<div
|
||||||
|
class="item-main-front"
|
||||||
|
:style="{ backgroundColor: props.color }"></div>
|
||||||
<Icon class="item-main-icon"></Icon>
|
<Icon class="item-main-icon"></Icon>
|
||||||
<div class="item-main-info">
|
<div class="item-main-info">
|
||||||
<div class="item-main-info-name">
|
<div class="item-main-info-name">
|
||||||
@@ -11,8 +17,13 @@
|
|||||||
{{ time }}
|
{{ time }}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<n-dropdown trigger="click" :options="dropDownOptions" @select="handleDropdownSelect">
|
<n-dropdown
|
||||||
<div class="item-main-option" @click="e=>e.stopPropagation()">
|
trigger="click"
|
||||||
|
:options="dropDownOptions"
|
||||||
|
@select="handleDropdownSelect">
|
||||||
|
<div
|
||||||
|
class="item-main-option"
|
||||||
|
@click="(e) => e.stopPropagation()">
|
||||||
<EllipsisVertical class="item-main-option-icon" />
|
<EllipsisVertical class="item-main-option-icon" />
|
||||||
</div>
|
</div>
|
||||||
</n-dropdown>
|
</n-dropdown>
|
||||||
@@ -21,96 +32,138 @@
|
|||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
|
import VirtualDirectory, { VirtualFile } from '@/class/VirtualDirectory'
|
||||||
|
import {
|
||||||
|
DocumentText,
|
||||||
|
FileTray,
|
||||||
|
Help,
|
||||||
|
Image,
|
||||||
|
LogoChrome,
|
||||||
|
LogoCss3,
|
||||||
|
LogoJavascript,
|
||||||
|
LogoVue,
|
||||||
|
PlayCircle,
|
||||||
|
EllipsisVertical,
|
||||||
|
Disc
|
||||||
|
} from '@vicons/ionicons5'
|
||||||
|
import { computed, ref } from 'vue'
|
||||||
|
import dateFormatter from '@/hooks/dateFormatter'
|
||||||
|
// import useDataBus from '@/hooks/useDataBus'
|
||||||
|
import { NDropdown } from 'naive-ui'
|
||||||
|
|
||||||
import VirtualDirectory, { VirtualFile } from '@/class/VirtualDirectory';
|
// const dataBus = useDataBus()
|
||||||
import { DocumentText, FileTray, Help, Image, LogoChrome, LogoCss3, LogoJavascript, LogoVue, PlayCircle, EllipsisVertical, Disc } from '@vicons/ionicons5';
|
|
||||||
import { computed, ref } from 'vue';
|
|
||||||
import dateFormatter from '@/hooks/dateFormatter';
|
|
||||||
import useDataBus from '@/hooks/useDataBus';
|
|
||||||
import { NDropdown } from 'naive-ui';
|
|
||||||
|
|
||||||
const dataBus = useDataBus()
|
|
||||||
|
|
||||||
const emit = defineEmits<{
|
|
||||||
download: []
|
|
||||||
delete: []
|
|
||||||
dragStart: []
|
|
||||||
}>()
|
|
||||||
|
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
item: VirtualDirectory | VirtualFile
|
item: VirtualDirectory | VirtualFile
|
||||||
name?: string
|
name?: string
|
||||||
color:string
|
color: string
|
||||||
|
}>()
|
||||||
|
|
||||||
|
const emit = defineEmits<{
|
||||||
|
download: []
|
||||||
|
delete: []
|
||||||
|
dragStart: [event: DragEvent, item: VirtualDirectory | VirtualFile]
|
||||||
}>()
|
}>()
|
||||||
|
|
||||||
const itemType = ref<'file' | 'directory'>(props.item.type)
|
const itemType = ref<'file' | 'directory'>(props.item.type)
|
||||||
|
|
||||||
const name = props.name ?? props.item.name
|
const name = props.name ?? props.item.name
|
||||||
|
|
||||||
const time = computed(()=>{
|
const time = computed(() => {
|
||||||
return dateFormatter(new Date(props.item.stats.mtimeMs), "yyyy-MM-dd hh:mm:ss");
|
return dateFormatter(
|
||||||
|
new Date(props.item.stats.mtimeMs),
|
||||||
|
'yyyy-MM-dd hh:mm:ss'
|
||||||
|
)
|
||||||
})
|
})
|
||||||
|
|
||||||
const dropDownOptions = computed(()=> {
|
const dropDownOptions = computed(() => {
|
||||||
const options = [{
|
const options = [
|
||||||
|
{
|
||||||
label: '删除',
|
label: '删除',
|
||||||
key: 'delete'
|
key: 'delete'
|
||||||
}]
|
}
|
||||||
if(itemType.value === 'file'){
|
]
|
||||||
options.push(...[
|
if (itemType.value === 'file') {
|
||||||
|
options.push(
|
||||||
|
...[
|
||||||
{
|
{
|
||||||
label: '下载',
|
label: '下载',
|
||||||
key: 'download',
|
key: 'download'
|
||||||
}
|
}
|
||||||
])
|
]
|
||||||
|
)
|
||||||
}
|
}
|
||||||
return options
|
return options
|
||||||
})
|
})
|
||||||
|
|
||||||
const handleDropdownSelect = (key: 'download' | 'delete') => {
|
const handleDropdownSelect = (key: 'download' | 'delete') => {
|
||||||
if(key === 'download'){
|
if (key === 'download') {
|
||||||
emit('download')
|
emit('download')
|
||||||
} else if (key === 'delete') {
|
} else if (key === 'delete') {
|
||||||
emit('delete')
|
emit('delete')
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
const Icon = computed(()=>{
|
const Icon = computed(() => {
|
||||||
try{
|
try {
|
||||||
if(props.item.type === 'directory') {
|
if (props.item.type === 'directory') {
|
||||||
return FileTray
|
return FileTray
|
||||||
} else if(props.item.type === 'file') {
|
} else if (props.item.type === 'file') {
|
||||||
const aft = props.item.name.split('.').at(-1)?.toLowerCase()
|
const aft = props.item.name.split('.').at(-1)?.toLowerCase()
|
||||||
if(!aft){
|
if (!aft) {
|
||||||
throw(1)
|
throw 1
|
||||||
}else if(['txt', 'doc', 'docs', 'docx', 'xls', 'xlsx'].includes(aft)){
|
} else if (
|
||||||
|
['txt', 'doc', 'docs', 'docx', 'xls', 'xlsx'].includes(aft)
|
||||||
|
) {
|
||||||
return DocumentText
|
return DocumentText
|
||||||
}else if(['mp3', 'wav', 'ape', 'acc', 'ogg', 'flac'].includes(aft)){
|
} else if (
|
||||||
|
['mp3', 'wav', 'ape', 'acc', 'ogg', 'flac'].includes(aft)
|
||||||
|
) {
|
||||||
return Disc
|
return Disc
|
||||||
}else if(['.xbm','.tif','pjp','.svgz','jpg','jpeg','ico','tiff','.gif','svg','.jfif','.webp','.png','.bmp','pjpeg','.avif'].includes(aft)){
|
} else if (
|
||||||
|
[
|
||||||
|
'.xbm',
|
||||||
|
'.tif',
|
||||||
|
'pjp',
|
||||||
|
'.svgz',
|
||||||
|
'jpg',
|
||||||
|
'jpeg',
|
||||||
|
'ico',
|
||||||
|
'tiff',
|
||||||
|
'.gif',
|
||||||
|
'svg',
|
||||||
|
'.jfif',
|
||||||
|
'.webp',
|
||||||
|
'.png',
|
||||||
|
'.bmp',
|
||||||
|
'pjpeg',
|
||||||
|
'.avif'
|
||||||
|
].includes(aft)
|
||||||
|
) {
|
||||||
return Image
|
return Image
|
||||||
}else if(['mp4', 'm2v', 'mkv'].includes(aft)){
|
} else if (['mp4', 'm2v', 'mkv'].includes(aft)) {
|
||||||
return PlayCircle
|
return PlayCircle
|
||||||
}else if(['js', 'jsx', 'ts', 'tsx'].includes(aft)){
|
} else if (['js', 'jsx', 'ts', 'tsx'].includes(aft)) {
|
||||||
return LogoJavascript
|
return LogoJavascript
|
||||||
}else if(['html'].includes(aft)){
|
} else if (['html'].includes(aft)) {
|
||||||
return LogoChrome
|
return LogoChrome
|
||||||
}else if(['css', 'scss', 'less'].includes(aft)){
|
} else if (['css', 'scss', 'less'].includes(aft)) {
|
||||||
return LogoCss3
|
return LogoCss3
|
||||||
}else if(['vue'].includes(aft)){
|
} else if (['vue'].includes(aft)) {
|
||||||
return LogoVue
|
return LogoVue
|
||||||
}
|
}
|
||||||
return DocumentText
|
return DocumentText
|
||||||
}
|
}
|
||||||
}catch{
|
} catch {
|
||||||
return Help
|
return Help
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
||||||
const itemRef = ref()
|
const itemRef = ref()
|
||||||
|
|
||||||
const handleDragStart = () => {
|
const handleDragStart = (event: DragEvent) => {
|
||||||
dataBus.set('dragData', [ props.item ])
|
emit('dragStart', event, props.item)
|
||||||
|
// dataBus.set('dragData', [props.item])
|
||||||
}
|
}
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@@ -138,7 +191,7 @@ const handleDragStart = () => {
|
|||||||
.item-main-front {
|
.item-main-front {
|
||||||
height: 100%;
|
height: 100%;
|
||||||
width: 10px;
|
width: 10px;
|
||||||
border-radius: 7px 0 0 7px ;
|
border-radius: 7px 0 0 7px;
|
||||||
background-color: rgb(0, 0, 0);
|
background-color: rgb(0, 0, 0);
|
||||||
}
|
}
|
||||||
.item-main-icon {
|
.item-main-icon {
|
||||||
@@ -176,17 +229,18 @@ const handleDragStart = () => {
|
|||||||
color: #000;
|
color: #000;
|
||||||
transition: color 0.15s;
|
transition: color 0.15s;
|
||||||
}
|
}
|
||||||
&:hover, &:active {
|
&:hover,
|
||||||
|
&:active {
|
||||||
background-color: #8b8b8b;
|
background-color: #8b8b8b;
|
||||||
.item-main-option-icon {
|
.item-main-option-icon {
|
||||||
color: #FFF;
|
color: #fff;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
&:hover, &:active {
|
&:hover,
|
||||||
|
&:active {
|
||||||
background-color: #d2d2d2;
|
background-color: #d2d2d2;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
</style>
|
</style>
|
||||||
@@ -0,0 +1,106 @@
|
|||||||
|
<template>
|
||||||
|
<div
|
||||||
|
class="container"
|
||||||
|
@dragover="handleDragOver"
|
||||||
|
@dragleave="handleDragLeave"
|
||||||
|
@drop="handleDrop">
|
||||||
|
<slot></slot>
|
||||||
|
<miao-mask v-model:show="showMask"></miao-mask>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
import { ref } from 'vue'
|
||||||
|
import miaoMask from './miaoMask.vue'
|
||||||
|
import VirtualDirectory, { VirtualFile } from '@/class/VirtualDirectory'
|
||||||
|
import config from '@/config'
|
||||||
|
import useDataBus from '@/hooks/useDataBus'
|
||||||
|
|
||||||
|
const dataBus = useDataBus()
|
||||||
|
|
||||||
|
const { uploadSizeLimit } = config
|
||||||
|
|
||||||
|
const emit = defineEmits<{
|
||||||
|
onFiles: [files: File[]]
|
||||||
|
onVirtualFiles: [vFiles: VirtualFile[]]
|
||||||
|
onVirtualDirectory: [vDirectory: VirtualDirectory[]]
|
||||||
|
}>()
|
||||||
|
|
||||||
|
const showMask = ref<number>(0)
|
||||||
|
|
||||||
|
// File類型的數據可能爲文件夾,通過FileReader進行判斷
|
||||||
|
const isFile = (file: File) =>
|
||||||
|
new Promise((resolve) => {
|
||||||
|
const reader = new FileReader()
|
||||||
|
reader.onload = () => {
|
||||||
|
resolve(true)
|
||||||
|
reader.abort()
|
||||||
|
}
|
||||||
|
reader.onerror = () => {
|
||||||
|
resolve(false)
|
||||||
|
reader.abort()
|
||||||
|
}
|
||||||
|
reader.readAsText(file)
|
||||||
|
})
|
||||||
|
|
||||||
|
/**
|
||||||
|
* 只保留文件,移去文件夹
|
||||||
|
* @param {File[]} files
|
||||||
|
*/
|
||||||
|
const removeDirectory = async (files: File[]) => {
|
||||||
|
let index = 0
|
||||||
|
while (index < files.length) {
|
||||||
|
const currentFile = files[index]
|
||||||
|
const _isFile = await isFile(currentFile)
|
||||||
|
if (_isFile) {
|
||||||
|
index += 1
|
||||||
|
continue
|
||||||
|
} else {
|
||||||
|
files.splice(index, 1)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleDragOver = async (event: DragEvent) => {
|
||||||
|
showMask.value += 1
|
||||||
|
event.preventDefault()
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleDragLeave = async () => {
|
||||||
|
showMask.value = 0
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleDrop = async (event: DragEvent) => {
|
||||||
|
showMask.value = 0
|
||||||
|
event.preventDefault()
|
||||||
|
event.stopPropagation()
|
||||||
|
// todo: uploadSize的限制不應該在這裏
|
||||||
|
const files = [...(event.dataTransfer?.files ?? [])].filter(
|
||||||
|
(file) => file.size < uploadSizeLimit
|
||||||
|
)
|
||||||
|
await removeDirectory(files)
|
||||||
|
const virtualFiles: VirtualFile[] = dataBus.pop('dragData_vFiles')
|
||||||
|
const virtualDirectory: VirtualDirectory[] = dataBus.pop(
|
||||||
|
'dragData_vDirectory'
|
||||||
|
)
|
||||||
|
// console.log({ virtualDirectory, virtualFiles })
|
||||||
|
if (files && files.length) {
|
||||||
|
emit('onFiles', files)
|
||||||
|
}
|
||||||
|
if (virtualFiles && virtualFiles.length) {
|
||||||
|
emit('onVirtualFiles', virtualFiles)
|
||||||
|
}
|
||||||
|
if (virtualDirectory && virtualDirectory.length) {
|
||||||
|
emit('onVirtualDirectory', virtualDirectory)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style lang="scss" scoped>
|
||||||
|
.container {
|
||||||
|
width: 100%;
|
||||||
|
height: 100%;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@@ -2,7 +2,7 @@
|
|||||||
<transition name="transition">
|
<transition name="transition">
|
||||||
<div class="mask-body" ref="maskBodyRef" v-show="showMask">
|
<div class="mask-body" ref="maskBodyRef" v-show="showMask">
|
||||||
<div @click="e=>e.stopPropagation()">
|
<div @click="e=>e.stopPropagation()">
|
||||||
<slot> {{}} </slot>
|
<slot></slot>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</transition>
|
</transition>
|
||||||
|
|||||||
+159
-129
@@ -1,10 +1,15 @@
|
|||||||
<template>
|
<template>
|
||||||
|
<miao-drop-handler @on-virtual-directory="handleDropVDirectory" @on-files="handleDropFiles">
|
||||||
<div class="miao-directory-item-container" ref="rootDomRef">
|
<div class="miao-directory-item-container" ref="rootDomRef">
|
||||||
<div
|
<div
|
||||||
class="container-top"
|
class="container-top"
|
||||||
:style="{ backgroundColor: index % 2 === 0 ? '#f8f8f8' : 'rgb(240 240 240)' }"
|
:style="{
|
||||||
>
|
backgroundColor:
|
||||||
<div class="container-top-colorbar" :style="{ backgroundColor: props.color }"></div>
|
index % 2 === 0 ? '#f8f8f8' : 'rgb(240 240 240)'
|
||||||
|
}">
|
||||||
|
<div
|
||||||
|
class="container-top-colorfulBar"
|
||||||
|
:style="{ backgroundColor: props.color }"></div>
|
||||||
<div class="container-top-breadcrumb">
|
<div class="container-top-breadcrumb">
|
||||||
<!-- <n-scrollbar x-scrollable> -->
|
<!-- <n-scrollbar x-scrollable> -->
|
||||||
<div class="container-top-breadcrumb-container">
|
<div class="container-top-breadcrumb-container">
|
||||||
@@ -17,8 +22,7 @@
|
|||||||
<n-breadcrumb-item
|
<n-breadcrumb-item
|
||||||
v-for="dir in currentDirectory?.directoryArray"
|
v-for="dir in currentDirectory?.directoryArray"
|
||||||
@click="setCurrentDirectory(dir)"
|
@click="setCurrentDirectory(dir)"
|
||||||
:clickable="true"
|
:clickable="true">
|
||||||
>
|
|
||||||
<div>{{ dir.name }}</div>
|
<div>{{ dir.name }}</div>
|
||||||
</n-breadcrumb-item>
|
</n-breadcrumb-item>
|
||||||
</n-breadcrumb>
|
</n-breadcrumb>
|
||||||
@@ -26,21 +30,33 @@
|
|||||||
<!-- </n-scrollbar> -->
|
<!-- </n-scrollbar> -->
|
||||||
</div>
|
</div>
|
||||||
<div class="container-top-tools">
|
<div class="container-top-tools">
|
||||||
<n-icon class="container-top-tools-item" size="15" @click="handleBack">
|
<n-icon
|
||||||
|
class="container-top-tools-item"
|
||||||
|
size="15"
|
||||||
|
@click="handleBack">
|
||||||
<ChevronBackOutline />
|
<ChevronBackOutline />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
<n-icon class="container-top-tools-item" size="14" @click="handleReload">
|
<n-icon
|
||||||
<ReloadOutline class="container-top-tools-item-reload" />
|
class="container-top-tools-item"
|
||||||
|
size="14"
|
||||||
|
@click="handleReload">
|
||||||
|
<ReloadOutline
|
||||||
|
class="container-top-tools-item-reload" />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
<n-icon class="container-top-tools-item" size="20" @click="emit('exit')">
|
<n-icon
|
||||||
|
class="container-top-tools-item"
|
||||||
|
size="20"
|
||||||
|
@click="emit('exit')">
|
||||||
<CloseOutline />
|
<CloseOutline />
|
||||||
</n-icon>
|
</n-icon>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="container-items"
|
class="container-items"
|
||||||
:style="{ backgroundColor: index % 2 === 0 ? '#f8f8f8' : 'rgb(240 240 240)' }"
|
:style="{
|
||||||
>
|
backgroundColor:
|
||||||
|
index % 2 === 0 ? '#f8f8f8' : 'rgb(240 240 240)'
|
||||||
|
}">
|
||||||
<n-scrollbar>
|
<n-scrollbar>
|
||||||
<transition-group name="dirItem">
|
<transition-group name="dirItem">
|
||||||
<miaoDirectoryItem
|
<miaoDirectoryItem
|
||||||
@@ -50,7 +66,7 @@
|
|||||||
:key="dir.uid"
|
:key="dir.uid"
|
||||||
:color="props.color"
|
:color="props.color"
|
||||||
@delete="handleItemDelete(dir)"
|
@delete="handleItemDelete(dir)"
|
||||||
/>
|
@drag-start="handleItemDragStart" />
|
||||||
</transition-group>
|
</transition-group>
|
||||||
<transition-group name="dirItem">
|
<transition-group name="dirItem">
|
||||||
<miaoDirectoryItem
|
<miaoDirectoryItem
|
||||||
@@ -59,182 +75,196 @@
|
|||||||
:key="file.uid"
|
:key="file.uid"
|
||||||
@click="openUrl(`${baseUrl}${api.get}${file.path}`)"
|
@click="openUrl(`${baseUrl}${api.get}${file.path}`)"
|
||||||
@download="
|
@download="
|
||||||
openUrl(`${baseUrl}${api.get}${file.path}`, { download: file.name })
|
openUrl(`${baseUrl}${api.get}${file.path}`, {
|
||||||
|
download: file.name
|
||||||
|
})
|
||||||
"
|
"
|
||||||
@delete="handleItemDelete(file)"
|
@delete="handleItemDelete(file)"
|
||||||
:color="props.color"
|
@drag-start="handleItemDragStart"
|
||||||
/>
|
:color="props.color" />
|
||||||
</transition-group>
|
</transition-group>
|
||||||
</n-scrollbar>
|
</n-scrollbar>
|
||||||
</div>
|
</div>
|
||||||
<div
|
<div
|
||||||
class="container-bottom"
|
class="container-bottom"
|
||||||
:style="{ backgroundColor: index % 2 === 1 ? 'rgb(61 61 61)' : 'rgb(162 162 162)' }"
|
:style="{
|
||||||
></div>
|
backgroundColor:
|
||||||
|
index % 2 === 1 ? 'rgb(61 61 61)' : 'rgb(162 162 162)'
|
||||||
|
}"></div>
|
||||||
<miao-mask v-model:show="showModel"></miao-mask>
|
<miao-mask v-model:show="showModel"></miao-mask>
|
||||||
<!-- <miao-popup-input ref="popupInput"></miao-popup-input> -->
|
<!-- <miao-popup-input ref="popupInput"></miao-popup-input> -->
|
||||||
</div>
|
</div>
|
||||||
|
</miao-drop-handler>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
import { NBreadcrumbItem, NBreadcrumb, NIcon, NScrollbar } from "naive-ui";
|
import { NBreadcrumbItem, NBreadcrumb, NIcon, NScrollbar } from 'naive-ui'
|
||||||
import type { file, directory } from "@/types/type.ts";
|
import type { file, directory } from '@/types/type.ts'
|
||||||
import VirtualDirectory, { VirtualFile } from "@/class/VirtualDirectory";
|
import VirtualDirectory, { VirtualFile } from '@/class/VirtualDirectory'
|
||||||
import { computed, onMounted, ref } from "vue";
|
import { computed, onMounted, ref } from 'vue'
|
||||||
import Config from "@/config";
|
import Config from '@/config'
|
||||||
import dropHandler, { dropHandlerHooks } from "@/hooks/dropHandler";
|
import miaoMask from '@/components/miaoMask.vue'
|
||||||
import miaoMask from "@/components/miaoMask.vue";
|
import miaoDirectoryItem from '@/components/miaoDirectory/miaoDirectoryItem.vue'
|
||||||
import miaoPopupInput from "@/components/miaoPopupInput.vue";
|
// import miaoPopupInput from "@/components/miaoPopupInput.vue";
|
||||||
import miaoDirectoryItem from "@/components/miaoDirectory/miaoDirectoryItem.vue";
|
import miaoDropHandler from '@/components/miaoDropHandler.vue'
|
||||||
import useMiaoFetchApi from "@/hooks/useMiaoFetchApi";
|
import useMiaoFetchApi from '@/hooks/useMiaoFetchApi'
|
||||||
import useDataBus from "@/hooks/useDataBus";
|
import useDataBus from '@/hooks/useDataBus'
|
||||||
import {
|
import {
|
||||||
CloudOutline,
|
CloudOutline,
|
||||||
ChevronBackOutline,
|
ChevronBackOutline,
|
||||||
ReloadOutline,
|
ReloadOutline,
|
||||||
CloseOutline,
|
CloseOutline
|
||||||
} from "@vicons/ionicons5";
|
} from '@vicons/ionicons5'
|
||||||
import useUploadQueue from "@/hooks/useUploadQueue";
|
import useUploadQueue from '@/hooks/useUploadQueue'
|
||||||
import useViretualPages from "@/hooks/useVirtualPages";
|
import useVirtualPages from '@/hooks/useVirtualPages'
|
||||||
|
|
||||||
const { baseUrl, api } = Config;
|
const { baseUrl, api } = Config
|
||||||
const dataBus = useDataBus();
|
const dataBus = useDataBus()
|
||||||
const views = useViretualPages();
|
const views = useVirtualPages()
|
||||||
|
|
||||||
const miaoFetchApi = useMiaoFetchApi();
|
const miaoFetchApi = useMiaoFetchApi()
|
||||||
|
|
||||||
const props = defineProps<{
|
const props = defineProps<{
|
||||||
color: string;
|
color: string
|
||||||
id: number;
|
id: number
|
||||||
}>();
|
}>()
|
||||||
|
|
||||||
const emit = defineEmits<{
|
const emit = defineEmits<{
|
||||||
exit: [];
|
exit: []
|
||||||
}>();
|
}>()
|
||||||
|
|
||||||
const popupInput = ref()
|
const popupInput = ref()
|
||||||
// 是否显示模态框
|
// 是否显示模态框
|
||||||
const showModel = ref(0);
|
const showModel = ref(0)
|
||||||
|
|
||||||
const currentObjects = defineModel<VirtualDirectory[]>("currentObjects", {
|
const currentObjects = defineModel<VirtualDirectory[]>('currentObjects', {
|
||||||
required: true,
|
required: true
|
||||||
});
|
})
|
||||||
|
|
||||||
// 目前展示的Dir
|
// 目前展示的Dir
|
||||||
const currentDirectory = computed(() => {
|
const currentDirectory = computed(() => {
|
||||||
return currentObjects.value[0];
|
return currentObjects.value[0]
|
||||||
});
|
})
|
||||||
|
|
||||||
const index = computed(() => {
|
const index = computed(() => {
|
||||||
for (let i in views) {
|
for (let i in views) {
|
||||||
if (views[i].uid === props.id) {
|
if (views[i].uid === props.id) {
|
||||||
return parseInt(i);
|
return parseInt(i)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return 0;
|
return 0
|
||||||
});
|
})
|
||||||
|
|
||||||
// 用于展示的数据,后续会增加排序等操作
|
// 用于展示的数据,后续会增加排序等操作
|
||||||
const showData_directory = computed<VirtualDirectory[]>(() => {
|
const showData_directory = computed<VirtualDirectory[]>(() => {
|
||||||
const data = currentDirectory.value?.directorys
|
const data = currentDirectory.value?.directorys
|
||||||
? [...currentDirectory.value?.directorys]
|
? [...currentDirectory.value?.directorys]
|
||||||
: [];
|
: []
|
||||||
return data;
|
return data
|
||||||
});
|
})
|
||||||
const showData_files = computed<VirtualFile[]>(() => {
|
const showData_files = computed<VirtualFile[]>(() => {
|
||||||
const data = currentDirectory.value?.files ? [...currentDirectory.value?.files] : [];
|
const data = currentDirectory.value?.files
|
||||||
return data;
|
? [...currentDirectory.value?.files]
|
||||||
});
|
: []
|
||||||
|
return data
|
||||||
|
})
|
||||||
|
|
||||||
// 用于监听拖拽文件事件
|
// 用于监听拖拽文件事件
|
||||||
const rootDomRef = ref<HTMLDivElement>();
|
const rootDomRef = ref<HTMLDivElement>()
|
||||||
|
|
||||||
const uploadQueue = useUploadQueue();
|
const uploadQueue = useUploadQueue()
|
||||||
|
|
||||||
// 设置显示的dir
|
// 设置显示的dir
|
||||||
const setCurrentDirectory = async (virtualDirectory: VirtualDirectory) => {
|
const setCurrentDirectory = async (virtualDirectory: VirtualDirectory) => {
|
||||||
// 若没有缓存数据则同步刷新,有缓存数据则异步刷新
|
// 若没有缓存数据则同步刷新,有缓存数据则异步刷新
|
||||||
if (virtualDirectory.files === undefined || virtualDirectory.directorys === undefined) {
|
if (
|
||||||
const data: (file | directory)[] = await miaoFetchApi.get(virtualDirectory);
|
virtualDirectory.files === undefined ||
|
||||||
virtualDirectory.updateContent(data);
|
virtualDirectory.directorys === undefined
|
||||||
|
) {
|
||||||
|
const data: (file | directory)[] = await miaoFetchApi.get(
|
||||||
|
virtualDirectory
|
||||||
|
)
|
||||||
|
virtualDirectory.updateContent(data)
|
||||||
} else {
|
} else {
|
||||||
(async () => {
|
;(async () => {
|
||||||
const data: (file | directory)[] = await miaoFetchApi.get(virtualDirectory);
|
const data: (file | directory)[] = await miaoFetchApi.get(
|
||||||
virtualDirectory.updateContent(data);
|
virtualDirectory
|
||||||
})();
|
)
|
||||||
|
virtualDirectory.updateContent(data)
|
||||||
|
})()
|
||||||
}
|
}
|
||||||
currentObjects.value[0] = virtualDirectory;
|
currentObjects.value[0] = virtualDirectory
|
||||||
};
|
}
|
||||||
|
|
||||||
const reload = () => {
|
const reload = () => {
|
||||||
setCurrentDirectory(currentDirectory.value);
|
setCurrentDirectory(currentDirectory.value)
|
||||||
};
|
}
|
||||||
|
|
||||||
const openUrl = (
|
const openUrl = (
|
||||||
href: string,
|
href: string,
|
||||||
config?: {
|
config?: {
|
||||||
download?: string;
|
download?: string
|
||||||
target?: string;
|
target?: string
|
||||||
}
|
}
|
||||||
) => {
|
) => {
|
||||||
let { target, download } = config ?? {};
|
let { target, download } = config ?? {}
|
||||||
const a = document.createElement("a");
|
const a = document.createElement('a')
|
||||||
a.setAttribute("href", href);
|
a.setAttribute('href', href)
|
||||||
a.setAttribute("target", target ?? "_blank");
|
a.setAttribute('target', target ?? '_blank')
|
||||||
download && a.setAttribute("download", download);
|
download && a.setAttribute('download', download)
|
||||||
a.click();
|
a.click()
|
||||||
};
|
}
|
||||||
|
|
||||||
const handleBack = () => {
|
const handleBack = () => {
|
||||||
if (currentDirectory.value?.parent) {
|
if (currentDirectory.value?.parent) {
|
||||||
setCurrentDirectory(currentDirectory.value.parent);
|
setCurrentDirectory(currentDirectory.value.parent)
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
|
|
||||||
const handleReload = () => {
|
const handleReload = () => {
|
||||||
reload();
|
reload()
|
||||||
};
|
}
|
||||||
|
|
||||||
const handleItemDelete = async (item: VirtualDirectory | VirtualFile) => {
|
const handleItemDelete = async (item: VirtualDirectory | VirtualFile) => {
|
||||||
const { response } = miaoFetchApi.delete(item, {
|
const { response } = miaoFetchApi.delete(item, {
|
||||||
retry: 5,
|
retry: 5
|
||||||
});
|
})
|
||||||
// todo: 将删除事件统一用一个事件管理中心管理
|
// todo: 将删除事件统一用一个事件管理中心管理
|
||||||
const id = (await response).eventId;
|
const id = (await response).eventId
|
||||||
const { response: res } = miaoFetchApi.query(id);
|
const { response: res } = miaoFetchApi.query(id)
|
||||||
const eventResult = await res;
|
const eventResult = await res
|
||||||
if (eventResult.status === "success") {
|
if (eventResult.status === 'success') {
|
||||||
reload();
|
reload()
|
||||||
}
|
}
|
||||||
};
|
}
|
||||||
|
|
||||||
onMounted(async () => {
|
const handleItemDragStart = async (
|
||||||
await setCurrentDirectory(currentDirectory.value);
|
_event: DragEvent,
|
||||||
// 拖动事件处理
|
item: VirtualDirectory | VirtualFile
|
||||||
const dropFileOption: dropHandlerHooks = {
|
) => {
|
||||||
onDropFiles(files: File[]) {
|
if (item.type === 'file') {
|
||||||
const dragData = dataBus.pop("dragData");
|
dataBus.set('dragData_vFiles', [item])
|
||||||
console.log({ dragData, files });
|
} else {
|
||||||
if (files && files.length > 0) {
|
dataBus.set('dragData_vDirectory', [item])
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleDropVDirectory = async (vDirs: VirtualDirectory[]) => {
|
||||||
|
setCurrentDirectory(vDirs[0])
|
||||||
|
}
|
||||||
|
|
||||||
|
const handleDropFiles = async (files: File[]) => {
|
||||||
currentDirectory.value &&
|
currentDirectory.value &&
|
||||||
uploadQueue.push(files, currentDirectory.value, {
|
uploadQueue.push(files, currentDirectory.value, {
|
||||||
onFinish() {
|
onFinish() {
|
||||||
reload();
|
reload()
|
||||||
},
|
|
||||||
});
|
|
||||||
}
|
}
|
||||||
},
|
})
|
||||||
onEnter() {
|
}
|
||||||
showModel.value += 1;
|
|
||||||
},
|
|
||||||
onEnd() {
|
|
||||||
showModel.value -= 1;
|
|
||||||
},
|
|
||||||
};
|
|
||||||
rootDomRef.value && dropHandler(rootDomRef.value, dropFileOption);
|
|
||||||
|
|
||||||
console.log(await popupInput.value.popup())
|
onMounted(async () => {
|
||||||
});
|
await setCurrentDirectory(currentDirectory.value)
|
||||||
|
})
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style scoped lang="scss">
|
<style scoped lang="scss">
|
||||||
@@ -260,7 +290,7 @@ $bottom-bar-height: 60px;
|
|||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
background-color: #f1f1f1;
|
background-color: #f1f1f1;
|
||||||
|
|
||||||
.container-top-colorbar {
|
.container-top-colorfulBar {
|
||||||
height: 70%;
|
height: 70%;
|
||||||
width: 5px;
|
width: 5px;
|
||||||
margin-left: 10px;
|
margin-left: 10px;
|
||||||
@@ -356,23 +386,23 @@ $bottom-bar-height: 60px;
|
|||||||
}
|
}
|
||||||
|
|
||||||
// transition动画相关
|
// transition动画相关
|
||||||
.miao-directory-item-container {
|
// .miao-directory-item-container {
|
||||||
.container-items {
|
// .container-items {
|
||||||
.dirItem-move {
|
// .dirItem-move {
|
||||||
transition: all 0.2s ease;
|
// transition: all 0.2s ease;
|
||||||
}
|
// }
|
||||||
|
|
||||||
.dirItem-leave-active {
|
// .dirItem-leave-active {
|
||||||
transition: none;
|
// transition: none;
|
||||||
}
|
// }
|
||||||
|
|
||||||
.dirItem-enter-from {
|
// .dirItem-enter-from {
|
||||||
opacity: 0;
|
// opacity: 0;
|
||||||
}
|
// }
|
||||||
|
|
||||||
.dirItem-leave-active {
|
// .dirItem-leave-active {
|
||||||
position: absolute;
|
// position: absolute;
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
}
|
// }
|
||||||
</style>
|
</style>
|
||||||
Reference in new issue
Block a user