mirror of
https://github.com/jxxghp/MoviePilot-Frontend.git
synced 2026-09-05 15:36:49 +08:00
Merge pull request #64 from thofx/thofx_fix_ui
This commit is contained in:
@@ -31,7 +31,7 @@ export default {
|
|||||||
elevation: 0,
|
elevation: 0,
|
||||||
},
|
},
|
||||||
VList: {
|
VList: {
|
||||||
activeColor: 'primary',
|
color: 'primary',
|
||||||
},
|
},
|
||||||
VPagination: {
|
VPagination: {
|
||||||
activeColor: 'primary',
|
activeColor: 'primary',
|
||||||
|
|||||||
@@ -3,6 +3,10 @@
|
|||||||
@tailwind components;
|
@tailwind components;
|
||||||
@tailwind utilities;
|
@tailwind utilities;
|
||||||
|
|
||||||
|
:root{
|
||||||
|
font-family: -apple-system, BlinkMacSystemFont, "PingFang SC", "Microsoft YaHei UI", "Segoe UI", Roboto, Oxygen, Ubuntu, Cantarell, "Fira Sans", "Droid Sans", "Helvetica Neue", Helvetica, Arial, sans-serif;
|
||||||
|
}
|
||||||
|
|
||||||
#nprogress .bar {
|
#nprogress .bar {
|
||||||
background: rgb(var(--v-theme-primary)) !important;
|
background: rgb(var(--v-theme-primary)) !important;
|
||||||
top: env(safe-area-inset-top) !important;
|
top: env(safe-area-inset-top) !important;
|
||||||
|
|||||||
@@ -4,3 +4,18 @@ export function removeEl(selector: string) {
|
|||||||
el?.parentNode?.removeChild(el)
|
el?.parentNode?.removeChild(el)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export function useDefer(maxFrameCount = 1) {
|
||||||
|
const frameCount = ref(0)
|
||||||
|
const refreshFrameCount = () => {
|
||||||
|
requestAnimationFrame(() => {
|
||||||
|
frameCount.value++
|
||||||
|
if (frameCount.value < maxFrameCount)
|
||||||
|
refreshFrameCount()
|
||||||
|
})
|
||||||
|
}
|
||||||
|
refreshFrameCount()
|
||||||
|
return function (showInFrameCount: number) {
|
||||||
|
return frameCount.value >= showInFrameCount
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
@@ -1,6 +1,8 @@
|
|||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
import { ref } from 'vue'
|
|
||||||
import _ from 'lodash'
|
import _ from 'lodash'
|
||||||
|
import type { Ref } from 'vue'
|
||||||
|
import { ref } from 'vue'
|
||||||
|
import { useDefer } from '@/util'
|
||||||
import type { Context } from '@/api/types'
|
import type { Context } from '@/api/types'
|
||||||
import TorrentCard from '@/components/cards/TorrentCard.vue'
|
import TorrentCard from '@/components/cards/TorrentCard.vue'
|
||||||
|
|
||||||
@@ -48,7 +50,7 @@ const editionFilterOptions = ref<Array<string>>([])
|
|||||||
const resolutionFilterOptions = ref<Array<string>>([])
|
const resolutionFilterOptions = ref<Array<string>>([])
|
||||||
|
|
||||||
// 数据列表
|
// 数据列表
|
||||||
const dataList = ref <Array<SearchTorrent>>([])
|
const dataList = ref<Array<SearchTorrent>>([])
|
||||||
|
|
||||||
// 分组后的数据列表
|
// 分组后的数据列表
|
||||||
const groupedDataList = ref<Map<string, Context[]>>()
|
const groupedDataList = ref<Map<string, Context[]>>()
|
||||||
@@ -69,7 +71,7 @@ function initOptions(data: Context) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 计算分组后的列表
|
// 计算分组后的列表
|
||||||
watchEffect(() => {
|
onMounted(() => {
|
||||||
// 数据分组
|
// 数据分组
|
||||||
const groupMap = new Map<string, Context[]>()
|
const groupMap = new Map<string, Context[]>()
|
||||||
// 遍历数据
|
// 遍历数据
|
||||||
@@ -92,10 +94,12 @@ watchEffect(() => {
|
|||||||
groupedDataList.value = groupMap
|
groupedDataList.value = groupMap
|
||||||
})
|
})
|
||||||
|
|
||||||
|
const defer: Ref<Function> = ref(() => true)
|
||||||
|
|
||||||
// 计算过滤后的列表
|
// 计算过滤后的列表
|
||||||
watchEffect(() => {
|
watchEffect(() => {
|
||||||
// 清空列表
|
// 清空列表
|
||||||
dataList.value.splice(0)
|
dataList.value = []
|
||||||
// 匹配过滤函数
|
// 匹配过滤函数
|
||||||
const match = (filter: Array<string>, value: string | undefined) =>
|
const match = (filter: Array<string>, value: string | undefined) =>
|
||||||
filter.length === 0 || (value && filter.includes(value))
|
filter.length === 0 || (value && filter.includes(value))
|
||||||
@@ -126,10 +130,12 @@ watchEffect(() => {
|
|||||||
const firstData = _.cloneDeepWith(matchData[0]) as SearchTorrent
|
const firstData = _.cloneDeepWith(matchData[0]) as SearchTorrent
|
||||||
if (matchData.length > 1)
|
if (matchData.length > 1)
|
||||||
firstData.more = matchData.slice(1)
|
firstData.more = matchData.slice(1)
|
||||||
|
|
||||||
dataList.value.push(firstData)
|
dataList.value.push(firstData)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
defer.value = useDefer(dataList.value.length)
|
||||||
})
|
})
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
@@ -216,12 +222,9 @@ watchEffect(() => {
|
|||||||
</VRow>
|
</VRow>
|
||||||
</VCard>
|
</VCard>
|
||||||
<div class="grid gap-3 grid-torrent-card items-start">
|
<div class="grid gap-3 grid-torrent-card items-start">
|
||||||
<TorrentCard
|
<div v-for="(item, index) in dataList" :key="`${index}_${item.torrent_info.title}_${item.torrent_info.site}`">
|
||||||
v-for="(item, index) in dataList"
|
<TorrentCard v-if="defer(index)" :torrent="item" :more="item.more" />
|
||||||
:key="`${index}_${item.torrent_info.title}_${item.torrent_info.site}`"
|
</div>
|
||||||
:torrent="item"
|
|
||||||
:more="item.more"
|
|
||||||
/>
|
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,5 @@
|
|||||||
<script lang="ts" setup>
|
<script lang="ts" setup>
|
||||||
|
import { ref } from 'vue'
|
||||||
import type { Context } from '@/api/types'
|
import type { Context } from '@/api/types'
|
||||||
import TorrentItem from '@/components/cards/TorrentItem.vue'
|
import TorrentItem from '@/components/cards/TorrentItem.vue'
|
||||||
|
|
||||||
@@ -27,7 +28,7 @@ const filterForm = reactive({
|
|||||||
})
|
})
|
||||||
|
|
||||||
// 数据列表
|
// 数据列表
|
||||||
const dataList = ref <Array<Context>>([])
|
const dataList = ref<Array<Context>>([])
|
||||||
|
|
||||||
// 获取站点过滤选项
|
// 获取站点过滤选项
|
||||||
const siteFilterOptions = ref<Array<string>>([])
|
const siteFilterOptions = ref<Array<string>>([])
|
||||||
@@ -62,7 +63,7 @@ function initOptions(data: Context) {
|
|||||||
// 计算过滤后的列表
|
// 计算过滤后的列表
|
||||||
watchEffect(() => {
|
watchEffect(() => {
|
||||||
// 清空列表
|
// 清空列表
|
||||||
dataList.value.splice(0)
|
dataList.value = []
|
||||||
// 匹配过滤函数
|
// 匹配过滤函数
|
||||||
const match = (filter: Array<string>, value: string | undefined) =>
|
const match = (filter: Array<string>, value: string | undefined) =>
|
||||||
filter.length === 0 || (value && filter.includes(value))
|
filter.length === 0 || (value && filter.includes(value))
|
||||||
@@ -72,18 +73,18 @@ watchEffect(() => {
|
|||||||
if (
|
if (
|
||||||
// 站点过滤
|
// 站点过滤
|
||||||
match(filterForm.site, torrent_info.site_name)
|
match(filterForm.site, torrent_info.site_name)
|
||||||
// 促销状态过滤
|
// 促销状态过滤
|
||||||
&& match(filterForm.freeState, torrent_info.volume_factor)
|
&& match(filterForm.freeState, torrent_info.volume_factor)
|
||||||
// 季过滤
|
// 季过滤
|
||||||
&& match(filterForm.season, meta_info.season_episode)
|
&& match(filterForm.season, meta_info.season_episode)
|
||||||
// 制作组过滤
|
// 制作组过滤
|
||||||
&& match(filterForm.releaseGroup, meta_info.resource_team)
|
&& match(filterForm.releaseGroup, meta_info.resource_team)
|
||||||
// 视频编码过滤
|
// 视频编码过滤
|
||||||
&& match(filterForm.videoCode, meta_info.video_encode)
|
&& match(filterForm.videoCode, meta_info.video_encode)
|
||||||
// 分辨率过滤
|
// 分辨率过滤
|
||||||
&& match(filterForm.resolution, meta_info.resource_pix)
|
&& match(filterForm.resolution, meta_info.resource_pix)
|
||||||
// 质量过滤
|
// 质量过滤
|
||||||
&& match(filterForm.edition, meta_info.edition)
|
&& match(filterForm.edition, meta_info.edition)
|
||||||
)
|
)
|
||||||
dataList.value.push(data)
|
dataList.value.push(data)
|
||||||
})
|
})
|
||||||
@@ -100,26 +101,19 @@ onMounted(() => {
|
|||||||
<template>
|
<template>
|
||||||
<VRow>
|
<VRow>
|
||||||
<VCol>
|
<VCol>
|
||||||
<VList
|
<VList v-if="dataList.length === 0" lines="three" class="rounded">
|
||||||
lines="three"
|
<VListItem>
|
||||||
class="rounded"
|
|
||||||
>
|
|
||||||
<TorrentItem
|
|
||||||
v-for="(item, index) in dataList"
|
|
||||||
:key="`${index}_${item.torrent_info.title}_${item.torrent_info.site}`"
|
|
||||||
:torrent="item"
|
|
||||||
/>
|
|
||||||
<VListItem v-if="dataList.length === 0">
|
|
||||||
<VListItemTitle>没有附合当前过滤条件的资源。</VListItemTitle>
|
<VListItemTitle>没有附合当前过滤条件的资源。</VListItemTitle>
|
||||||
</VListItem>
|
</VListItem>
|
||||||
</VList>
|
</VList>
|
||||||
|
<v-virtual-scroll lines="three" class="rounded" :items="dataList" height="calc(100vh - 156px)">
|
||||||
|
<template #default="{ item }">
|
||||||
|
<TorrentItem :torrent="item" />
|
||||||
|
</template>
|
||||||
|
</v-virtual-scroll>
|
||||||
</VCol>
|
</VCol>
|
||||||
<VCol
|
<VCol xl="2" md="3" class="d-none d-md-block">
|
||||||
xl="2"
|
<VList lines="one" class="rounded" height="calc(100vh - 156px)">
|
||||||
md="3"
|
|
||||||
class="d-none d-md-block"
|
|
||||||
>
|
|
||||||
<VList lines="one" class="rounded">
|
|
||||||
<VListSubheader v-if="siteFilterOptions.length > 0">
|
<VListSubheader v-if="siteFilterOptions.length > 0">
|
||||||
站点
|
站点
|
||||||
</VListSubheader>
|
</VListSubheader>
|
||||||
|
|||||||
@@ -25,13 +25,36 @@ const selected = ref<TransferHistory[]>([])
|
|||||||
|
|
||||||
// 表头
|
// 表头
|
||||||
const headers = [
|
const headers = [
|
||||||
{ title: '标题', key: 'title', sortable: false },
|
{
|
||||||
{ title: '目录', key: 'src', sortable: false },
|
title: '标题',
|
||||||
{ title: '转移方式', key: 'mode', sortable: false },
|
key: 'title',
|
||||||
{ title: '时间', key: 'date', sortable: false },
|
sortable: false,
|
||||||
{ title: '状态', key: 'status', sortable: false },
|
},
|
||||||
{ title: '失败原因', key: 'errmsg', sortable: false },
|
{
|
||||||
{ title: '', key: 'actions', sortable: false },
|
title: '目录',
|
||||||
|
key: 'src',
|
||||||
|
sortable: false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: '转移方式',
|
||||||
|
key: 'mode',
|
||||||
|
sortable: false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: '时间',
|
||||||
|
key: 'date',
|
||||||
|
sortable: false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: '状态',
|
||||||
|
key: 'status',
|
||||||
|
sortable: false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
title: '',
|
||||||
|
key: 'actions',
|
||||||
|
sortable: false,
|
||||||
|
},
|
||||||
]
|
]
|
||||||
|
|
||||||
// 数据列表
|
// 数据列表
|
||||||
@@ -71,13 +94,7 @@ const deleteConfirmDialog = ref(false)
|
|||||||
const confirmTitle = ref('')
|
const confirmTitle = ref('')
|
||||||
|
|
||||||
// 获取订阅列表数据
|
// 获取订阅列表数据
|
||||||
async function fetchData({
|
async function fetchData({ page, itemsPerPage }: { page: number; itemsPerPage: number }) {
|
||||||
page,
|
|
||||||
itemsPerPage,
|
|
||||||
}: {
|
|
||||||
page: number
|
|
||||||
itemsPerPage: number
|
|
||||||
}) {
|
|
||||||
loading.value = true
|
loading.value = true
|
||||||
try {
|
try {
|
||||||
currentPage.value = page
|
currentPage.value = page
|
||||||
@@ -92,7 +109,9 @@ async function fetchData({
|
|||||||
|
|
||||||
dataList.value = result.data.list
|
dataList.value = result.data.list
|
||||||
totalItems.value = result.data.total
|
totalItems.value = result.data.total
|
||||||
searchHintList.value = ['失败', '成功', ...new Set(dataList.value.map(item => item.title || ''))].filter(title => title !== '')
|
searchHintList.value = ['失败', '成功', ...new Set(dataList.value.map(item => item.title || ''))].filter(
|
||||||
|
title => title !== '',
|
||||||
|
)
|
||||||
}
|
}
|
||||||
catch (error) {
|
catch (error) {
|
||||||
console.error(error)
|
console.error(error)
|
||||||
@@ -110,11 +129,6 @@ function getIcon(type: string) {
|
|||||||
return 'mdi-help-circle'
|
return 'mdi-help-circle'
|
||||||
}
|
}
|
||||||
|
|
||||||
// 计算颜色
|
|
||||||
function getStatusColor(status: boolean) {
|
|
||||||
return status ? 'success' : 'error'
|
|
||||||
}
|
|
||||||
|
|
||||||
// 转移方式字典
|
// 转移方式字典
|
||||||
const TransferDict: { [key: string]: string } = {
|
const TransferDict: { [key: string]: string } = {
|
||||||
copy: '复制',
|
copy: '复制',
|
||||||
@@ -136,7 +150,9 @@ async function removeHistory(item: TransferHistory) {
|
|||||||
async function remove(item: TransferHistory, deleteSrc: boolean, deleteDest: boolean) {
|
async function remove(item: TransferHistory, deleteSrc: boolean, deleteDest: boolean) {
|
||||||
try {
|
try {
|
||||||
// 调用删除API
|
// 调用删除API
|
||||||
const result: { [key: string]: any } = await api.delete(`history/transfer?deletesrc=${deleteSrc}&deletedest=${deleteDest}`, {
|
const result: {
|
||||||
|
[key: string]: any
|
||||||
|
} = await api.delete(`history/transfer?deletesrc=${deleteSrc}&deletedest=${deleteDest}`, {
|
||||||
data: item,
|
data: item,
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -154,6 +170,7 @@ async function removeSingle(deleteSrc: boolean, deleteDest: boolean) {
|
|||||||
deleteConfirmDialog.value = false
|
deleteConfirmDialog.value = false
|
||||||
if (!currentHistory.value)
|
if (!currentHistory.value)
|
||||||
return
|
return
|
||||||
|
|
||||||
// 删除
|
// 删除
|
||||||
await remove(currentHistory.value, deleteSrc, deleteDest)
|
await remove(currentHistory.value, deleteSrc, deleteDest)
|
||||||
// 刷新
|
// 刷新
|
||||||
@@ -171,6 +188,7 @@ async function removeBatch(deleteSrc: boolean, deleteDest: boolean) {
|
|||||||
const total = selected.value.length
|
const total = selected.value.length
|
||||||
if (total === 0)
|
if (total === 0)
|
||||||
return
|
return
|
||||||
|
|
||||||
// 已处理条数
|
// 已处理条数
|
||||||
let handled = 0
|
let handled = 0
|
||||||
// 显示进度条
|
// 显示进度条
|
||||||
@@ -182,7 +200,7 @@ async function removeBatch(deleteSrc: boolean, deleteDest: boolean) {
|
|||||||
await remove(item, deleteSrc, deleteDest)
|
await remove(item, deleteSrc, deleteDest)
|
||||||
// 删除完成
|
// 删除完成
|
||||||
handled++
|
handled++
|
||||||
progressValue.value = handled / total * 100
|
progressValue.value = (handled / total) * 100
|
||||||
}
|
}
|
||||||
// 清空选中项
|
// 清空选中项
|
||||||
selected.value = []
|
selected.value = []
|
||||||
@@ -207,6 +225,7 @@ async function deleteConfirmHandler(deleteSrc: boolean, deleteDest: boolean) {
|
|||||||
async function removeHistoryBatch() {
|
async function removeHistoryBatch() {
|
||||||
if (selected.value.length === 0)
|
if (selected.value.length === 0)
|
||||||
return
|
return
|
||||||
|
|
||||||
// 清空当前操作记录
|
// 清空当前操作记录
|
||||||
currentHistory.value = undefined
|
currentHistory.value = undefined
|
||||||
confirmTitle.value = `确认删除 ${selected.value.length} 条记录 ?`
|
confirmTitle.value = `确认删除 ${selected.value.length} 条记录 ?`
|
||||||
@@ -218,11 +237,14 @@ async function removeHistoryBatch() {
|
|||||||
function getRootPath(path: string, type: string, category: string) {
|
function getRootPath(path: string, type: string, category: string) {
|
||||||
if (!path)
|
if (!path)
|
||||||
return ''
|
return ''
|
||||||
|
|
||||||
let index = -2
|
let index = -2
|
||||||
if (type !== '电影')
|
if (type !== '电影')
|
||||||
index = -3
|
index = -3
|
||||||
|
|
||||||
if (category)
|
if (category)
|
||||||
index -= 1
|
index -= 1
|
||||||
|
|
||||||
if (path.includes('/'))
|
if (path.includes('/'))
|
||||||
return path.split('/').slice(0, index).join('/')
|
return path.split('/').slice(0, index).join('/')
|
||||||
else
|
else
|
||||||
@@ -233,6 +255,7 @@ function getRootPath(path: string, type: string, category: string) {
|
|||||||
async function retransferBatch() {
|
async function retransferBatch() {
|
||||||
if (selected.value.length === 0)
|
if (selected.value.length === 0)
|
||||||
return
|
return
|
||||||
|
|
||||||
// 清空当前操作记录
|
// 清空当前操作记录
|
||||||
currentHistory.value = undefined
|
currentHistory.value = undefined
|
||||||
// 重新整理IDS
|
// 重新整理IDS
|
||||||
@@ -329,58 +352,52 @@ const dropdownItems = ref([
|
|||||||
@update:options="fetchData"
|
@update:options="fetchData"
|
||||||
>
|
>
|
||||||
<template #item.title="{ item }">
|
<template #item.title="{ item }">
|
||||||
<div class="d-flex">
|
<div class="d-flex align-center">
|
||||||
<VAvatar><VIcon :icon="getIcon(item.raw.type || '')" /></VAvatar>
|
<VAvatar>
|
||||||
|
<VIcon :icon="getIcon(item.value.type || '')" />
|
||||||
|
</VAvatar>
|
||||||
<div class="d-flex flex-column ms-1">
|
<div class="d-flex flex-column ms-1">
|
||||||
<span class="d-block whitespace-nowrap text-high-emphasis">
|
<span class="d-block whitespace-nowrap text-high-emphasis">
|
||||||
{{ item.raw.title }} {{ item.raw.seasons }}{{ item.raw.episodes }}
|
{{ item.value.title }} {{ item.value.seasons }}{{ item.value.episodes }}
|
||||||
</span>
|
</span>
|
||||||
<small>{{ item.raw.category }}</small>
|
<small>{{ item.value.category }}</small>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</template>
|
</template>
|
||||||
<template #item.src="{ item }">
|
<template #item.src="{ item }">
|
||||||
<small>{{ item.raw.src }} <br>=> {{ item.raw.dest }}</small>
|
<small>{{ item.value.src }} <br>=> {{ item.value.dest }}</small>
|
||||||
</template>
|
</template>
|
||||||
<template #item.mode="{ item }">
|
<template #item.mode="{ item }">
|
||||||
<VChip
|
<VChip variant="outlined" color="primary" size="small">
|
||||||
variant="outlined"
|
{{ TransferDict[item.value.mode] }}
|
||||||
color="primary"
|
|
||||||
size="small"
|
|
||||||
>
|
|
||||||
{{
|
|
||||||
TransferDict[item.raw.mode]
|
|
||||||
}}
|
|
||||||
</VChip>
|
</VChip>
|
||||||
</template>
|
</template>
|
||||||
<template #item.status="{ item }">
|
<template #item.status="{ item }">
|
||||||
<VChip
|
<VChip v-if="item.value.status" color="success" size="small">
|
||||||
:color="getStatusColor(item.raw.status)"
|
成功
|
||||||
size="small"
|
|
||||||
>
|
|
||||||
{{ item.raw.status ? "成功" : "失败" }}
|
|
||||||
</VChip>
|
</VChip>
|
||||||
|
<v-tooltip v-else :text="item.value.errmsg">
|
||||||
|
<template #activator="{ props }">
|
||||||
|
<VChip v-bind="props" color="error" size="small">
|
||||||
|
失败
|
||||||
|
</VChip>
|
||||||
|
</template>
|
||||||
|
</v-tooltip>
|
||||||
</template>
|
</template>
|
||||||
<template #item.date="{ item }">
|
<template #item.date="{ item }">
|
||||||
<small>{{ item.raw.date }}</small>
|
<small>{{ item.value.date }}</small>
|
||||||
</template>
|
|
||||||
<template #item.errmsg="{ item }">
|
|
||||||
<small class="text-error">{{ item.raw.errmsg }}</small>
|
|
||||||
</template>
|
</template>
|
||||||
<template #item.actions="{ item }">
|
<template #item.actions="{ item }">
|
||||||
<IconBtn>
|
<IconBtn>
|
||||||
<VIcon icon="mdi-dots-vertical" />
|
<VIcon icon="mdi-dots-vertical" />
|
||||||
<VMenu
|
<VMenu activator="parent" close-on-content-click>
|
||||||
activator="parent"
|
|
||||||
close-on-content-click
|
|
||||||
>
|
|
||||||
<VList>
|
<VList>
|
||||||
<VListItem
|
<VListItem
|
||||||
v-for="(menu, i) in dropdownItems"
|
v-for="(menu, i) in dropdownItems"
|
||||||
:key="i"
|
:key="i"
|
||||||
variant="plain"
|
variant="plain"
|
||||||
:base-color="menu.props.color"
|
:base-color="menu.props.color"
|
||||||
@click="menu.props.click(item.raw)"
|
@click="menu.props.click(item.value)"
|
||||||
>
|
>
|
||||||
<template #prepend>
|
<template #prepend>
|
||||||
<VIcon :icon="menu.props.prependIcon" />
|
<VIcon :icon="menu.props.prependIcon" />
|
||||||
@@ -397,23 +414,9 @@ const dropdownItems = ref([
|
|||||||
</VDataTableServer>
|
</VDataTableServer>
|
||||||
</VCard>
|
</VCard>
|
||||||
<!-- 底部操作按钮 -->
|
<!-- 底部操作按钮 -->
|
||||||
<span
|
<span v-if="selected.length > 0" class="fixed right-5 bottom-5">
|
||||||
v-if="selected.length > 0"
|
<VBtn icon="mdi-redo-variant" class="me-2" color="primary" size="x-large" @click="retransferBatch" />
|
||||||
class="fixed right-5 bottom-5"
|
<VBtn icon="mdi-trash-can-outline" color="error" size="x-large" @click="removeHistoryBatch" />
|
||||||
>
|
|
||||||
<VBtn
|
|
||||||
icon="mdi-redo-variant"
|
|
||||||
class="me-2"
|
|
||||||
color="primary"
|
|
||||||
size="x-large"
|
|
||||||
@click="retransferBatch"
|
|
||||||
/>
|
|
||||||
<VBtn
|
|
||||||
icon="mdi-trash-can-outline"
|
|
||||||
color="error"
|
|
||||||
size="x-large"
|
|
||||||
@click="removeHistoryBatch"
|
|
||||||
/>
|
|
||||||
</span>
|
</span>
|
||||||
<!-- 底部弹窗 -->
|
<!-- 底部弹窗 -->
|
||||||
<VBottomSheet v-model="deleteConfirmDialog" inset>
|
<VBottomSheet v-model="deleteConfirmDialog" inset>
|
||||||
@@ -422,33 +425,17 @@ const dropdownItems = ref([
|
|||||||
<VCardTitle class="pe-10">
|
<VCardTitle class="pe-10">
|
||||||
{{ confirmTitle }}
|
{{ confirmTitle }}
|
||||||
</VCardTitle>
|
</VCardTitle>
|
||||||
<div class="d-flex flex-column flex-lg-row justify-center my-3">
|
<div class="d-flex flex-column flex-lg-row justify-center my-3">
|
||||||
<VBtn
|
<VBtn color="primary" class="mb-2 mx-2" @click="deleteConfirmHandler(false, false)">
|
||||||
color="primary"
|
|
||||||
class="mb-2 mx-2"
|
|
||||||
@click="deleteConfirmHandler(false, false)"
|
|
||||||
>
|
|
||||||
仅删除历史记录
|
仅删除历史记录
|
||||||
</VBtn>
|
</VBtn>
|
||||||
<VBtn
|
<VBtn color="warning" class="mb-2 mx-2" @click="deleteConfirmHandler(true, false)">
|
||||||
color="warning"
|
|
||||||
class="mb-2 mx-2"
|
|
||||||
@click="deleteConfirmHandler(true, false)"
|
|
||||||
>
|
|
||||||
删除历史记录和源文件
|
删除历史记录和源文件
|
||||||
</VBtn>
|
</VBtn>
|
||||||
<VBtn
|
<VBtn color="info" class="mb-2 mx-2" @click="deleteConfirmHandler(false, true)">
|
||||||
color="info"
|
|
||||||
class="mb-2 mx-2"
|
|
||||||
@click="deleteConfirmHandler(false, true)"
|
|
||||||
>
|
|
||||||
删除历史记录和媒体库文件
|
删除历史记录和媒体库文件
|
||||||
</VBtn>
|
</VBtn>
|
||||||
<VBtn
|
<VBtn color="error" class="mb-2 mx-2" @click="deleteConfirmHandler(true, true)">
|
||||||
color="error"
|
|
||||||
class="mb-2 mx-2"
|
|
||||||
@click="deleteConfirmHandler(true, true)"
|
|
||||||
>
|
|
||||||
删除历史记录、源文件和媒体库文件
|
删除历史记录、源文件和媒体库文件
|
||||||
</VBtn>
|
</VBtn>
|
||||||
</div>
|
</div>
|
||||||
@@ -459,17 +446,19 @@ const dropdownItems = ref([
|
|||||||
v-model="redoDialog"
|
v-model="redoDialog"
|
||||||
:logids="redoIds"
|
:logids="redoIds"
|
||||||
:target="redoTarget"
|
:target="redoTarget"
|
||||||
@done="() => {
|
@done="
|
||||||
redoDialog = false
|
() => {
|
||||||
// 清空当前操作记录
|
redoDialog = false
|
||||||
currentHistory = undefined
|
// 清空当前操作记录
|
||||||
selected = []
|
currentHistory = undefined
|
||||||
// 刷新
|
selected = []
|
||||||
fetchData({
|
// 刷新
|
||||||
page: currentPage,
|
fetchData({
|
||||||
itemsPerPage,
|
page: currentPage,
|
||||||
})
|
itemsPerPage,
|
||||||
}"
|
})
|
||||||
|
}
|
||||||
|
"
|
||||||
@close="redoDialog = false"
|
@close="redoDialog = false"
|
||||||
/>
|
/>
|
||||||
</template>
|
</template>
|
||||||
|
|||||||
Reference in New Issue
Block a user