refactor: 重构下载页
- 将download页的文件卡片单独提取为FileCard
This commit is contained in:
83
app/components/pages/download/FileCard.vue
Normal file
83
app/components/pages/download/FileCard.vue
Normal file
@ -0,0 +1,83 @@
|
|||||||
|
<template>
|
||||||
|
<el-card shadow="hover" class="p-4">
|
||||||
|
<template #header>
|
||||||
|
<div class="header-content">
|
||||||
|
<el-icon class="header-icon"><ElIconDocument /></el-icon>
|
||||||
|
<span class="truncate font-medium">{{ file.filename_download }}</span>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<dl class="text-gray-600 space-y-1 mb-6">
|
||||||
|
<div>
|
||||||
|
<dt class="font-semibold inline">类型:</dt>
|
||||||
|
<dd class="inline">{{ file.type }}</dd>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<dt class="font-semibold inline">大小:</dt>
|
||||||
|
<dd class="inline">{{ formatFileSize(file.filesize) }}</dd>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<dt class="font-semibold inline">上传时间:</dt>
|
||||||
|
<dd class="inline">
|
||||||
|
{{ new Date(file.uploaded_on).toLocaleDateString() }}
|
||||||
|
</dd>
|
||||||
|
</div>
|
||||||
|
</dl>
|
||||||
|
<template #footer>
|
||||||
|
<div class="button-group">
|
||||||
|
<el-button type="primary" @click="handleDownload">下载</el-button>
|
||||||
|
<el-button v-if="file.previewable" @click="handlePreview"
|
||||||
|
>预览</el-button
|
||||||
|
>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
</el-card>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script setup lang="ts">
|
||||||
|
const props = defineProps({
|
||||||
|
fileId: {
|
||||||
|
type: String,
|
||||||
|
required: true,
|
||||||
|
},
|
||||||
|
file: {
|
||||||
|
type: Object as PropType<FileMeta>,
|
||||||
|
required: true,
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
const localePath = useLocalePath();
|
||||||
|
const router = useRouter();
|
||||||
|
|
||||||
|
function handleDownload() {
|
||||||
|
const link = document.createElement('a');
|
||||||
|
link.href = `/api/download/${props.fileId}`;
|
||||||
|
link.download = props.file?.filename_download ?? 'download';
|
||||||
|
document.body.appendChild(link);
|
||||||
|
link.click();
|
||||||
|
document.body.removeChild(link);
|
||||||
|
}
|
||||||
|
|
||||||
|
function handlePreview() {
|
||||||
|
router.push(localePath(`/preview/${props.fileId}`));
|
||||||
|
}
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped>
|
||||||
|
.header-content {
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 3px;
|
||||||
|
margin-bottom: 4px;
|
||||||
|
}
|
||||||
|
.header-icon {
|
||||||
|
font-size: 1.5rem;
|
||||||
|
margin-right: 0.5rem;
|
||||||
|
}
|
||||||
|
|
||||||
|
.button-group {
|
||||||
|
display: flex;
|
||||||
|
justify-content: flex-end;
|
||||||
|
align-items: baseline;
|
||||||
|
gap: 1rem;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
@ -5,40 +5,7 @@
|
|||||||
<app-breadcrumb class="breadcrumb" :items="breadcrumbItems" />
|
<app-breadcrumb class="breadcrumb" :items="breadcrumbItems" />
|
||||||
</div>
|
</div>
|
||||||
<div v-if="!pending" class="page-content">
|
<div v-if="!pending" class="page-content">
|
||||||
<el-card shadow="hover" class="p-4">
|
<file-card :file-id="id" :file="file" />
|
||||||
<template #header>
|
|
||||||
<div class="header-content">
|
|
||||||
<el-icon class="header-icon"><ElIconDocument /></el-icon>
|
|
||||||
<span class="truncate font-medium">{{
|
|
||||||
file.filename_download
|
|
||||||
}}</span>
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
<dl class="text-gray-600 space-y-1 mb-6">
|
|
||||||
<div>
|
|
||||||
<dt class="font-semibold inline">类型:</dt>
|
|
||||||
<dd class="inline">{{ file.type }}</dd>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<dt class="font-semibold inline">大小:</dt>
|
|
||||||
<dd class="inline">{{ formatFileSize(file.filesize) }}</dd>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<dt class="font-semibold inline">上传时间:</dt>
|
|
||||||
<dd class="inline">
|
|
||||||
{{ new Date(file.uploaded_on).toLocaleDateString() }}
|
|
||||||
</dd>
|
|
||||||
</div>
|
|
||||||
</dl>
|
|
||||||
<template #footer>
|
|
||||||
<div class="button-group">
|
|
||||||
<el-button type="primary" @click="handleDownload">下载</el-button>
|
|
||||||
<el-button v-if="file.previewable" @click="handlePreview"
|
|
||||||
>预览</el-button
|
|
||||||
>
|
|
||||||
</div>
|
|
||||||
</template>
|
|
||||||
</el-card>
|
|
||||||
</div>
|
</div>
|
||||||
<div v-else>
|
<div v-else>
|
||||||
<el-skeleton :rows="6" animated />
|
<el-skeleton :rows="6" animated />
|
||||||
@ -48,7 +15,6 @@
|
|||||||
|
|
||||||
<script setup lang="ts">
|
<script setup lang="ts">
|
||||||
const route = useRoute();
|
const route = useRoute();
|
||||||
const router = useRouter();
|
|
||||||
const localePath = useLocalePath();
|
const localePath = useLocalePath();
|
||||||
|
|
||||||
const breadcrumbItems = [
|
const breadcrumbItems = [
|
||||||
@ -56,14 +22,13 @@
|
|||||||
{ label: $t('navigation.downloads'), to: localePath('/downloads') },
|
{ label: $t('navigation.downloads'), to: localePath('/downloads') },
|
||||||
];
|
];
|
||||||
|
|
||||||
// 获取路由参数
|
const id = route.params.id as string;
|
||||||
const id = computed(() => route.params.id as string);
|
|
||||||
|
|
||||||
const {
|
const {
|
||||||
data: file,
|
data: file,
|
||||||
pending,
|
pending,
|
||||||
error,
|
error,
|
||||||
} = await useFetch<FileMeta>(`/api/file/${id.value}`);
|
} = await useFetch<FileMeta>(`/api/file/${id}`);
|
||||||
|
|
||||||
if (error.value || !file.value) {
|
if (error.value || !file.value) {
|
||||||
throw createError({
|
throw createError({
|
||||||
@ -71,19 +36,6 @@
|
|||||||
statusMessage: '文件未找到',
|
statusMessage: '文件未找到',
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
function handleDownload() {
|
|
||||||
const link = document.createElement('a');
|
|
||||||
link.href = `/api/download/${id.value}`;
|
|
||||||
link.download = file.value?.filename_download ?? 'download';
|
|
||||||
document.body.appendChild(link);
|
|
||||||
link.click();
|
|
||||||
document.body.removeChild(link);
|
|
||||||
}
|
|
||||||
|
|
||||||
function handlePreview() {
|
|
||||||
router.push(`/preview/${id.value}`);
|
|
||||||
}
|
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<style scoped>
|
<style scoped>
|
||||||
@ -107,22 +59,4 @@
|
|||||||
.breadcrumb {
|
.breadcrumb {
|
||||||
margin-left: auto;
|
margin-left: auto;
|
||||||
}
|
}
|
||||||
|
|
||||||
.header-content {
|
|
||||||
display: flex;
|
|
||||||
align-items: center;
|
|
||||||
gap: 3px;
|
|
||||||
margin-bottom: 4px;
|
|
||||||
}
|
|
||||||
.header-icon {
|
|
||||||
font-size: 1.5rem;
|
|
||||||
margin-right: 0.5rem;
|
|
||||||
}
|
|
||||||
|
|
||||||
.button-group {
|
|
||||||
display: flex;
|
|
||||||
justify-content: flex-end;
|
|
||||||
align-items: baseline;
|
|
||||||
gap: 1rem;
|
|
||||||
}
|
|
||||||
</style>
|
</style>
|
||||||
|
|||||||
Reference in New Issue
Block a user