perf: refine theme detail page

Signed-off-by: Ryan Wang <i@ryanc.cc>
pull/621/head^2
Ryan Wang 2022-09-26 14:50:00 +08:00
parent 28da1ab736
commit f3958ba53a
3 changed files with 93 additions and 74 deletions

View File

@ -36,7 +36,10 @@ const classes = computed(() => {
</div> </div>
<div v-if="$slots.dropdownItems" class="entity-dropdown"> <div v-if="$slots.dropdownItems" class="entity-dropdown">
<FloatingDropdown> <FloatingDropdown>
<div class="entity-dropdown-trigger group-hover:bg-gray-100"> <div
class="entity-dropdown-trigger group-hover:bg-gray-100"
@click.stop
>
<IconMore /> <IconMore />
</div> </div>
<template #popper> <template #popper>

View File

@ -2,14 +2,17 @@
import { import {
IconAddCircle, IconAddCircle,
IconGitHub, IconGitHub,
IconMore,
useDialog, useDialog,
VButton, VButton,
VEmpty, VEmpty,
VModal, VModal,
VSpace, VSpace,
VTag, VTag,
VEntity,
VEntityField,
VStatusDot,
} from "@halo-dev/components"; } from "@halo-dev/components";
import LazyImage from "@/components/image/LazyImage.vue";
import ThemeInstallModal from "./ThemeInstallModal.vue"; import ThemeInstallModal from "./ThemeInstallModal.vue";
import { ref, watch } from "vue"; import { ref, watch } from "vue";
import type { Theme } from "@halo-dev/api-client"; import type { Theme } from "@halo-dev/api-client";
@ -103,6 +106,7 @@ defineExpose({
:body-class="['!p-0']" :body-class="['!p-0']"
:visible="visible" :visible="visible"
:width="888" :width="888"
height="calc(100vh - 20px)"
title="已安装的主题" title="已安装的主题"
@update:visible="onVisibleChange" @update:visible="onVisibleChange"
> >
@ -124,59 +128,83 @@ defineExpose({
</template> </template>
</VEmpty> </VEmpty>
<ul v-else class="flex flex-col divide-y divide-gray-100" role="list"> <ul
v-else
class="box-border h-full w-full divide-y divide-gray-100"
role="list"
>
<li <li
v-for="(theme, index) in themes" v-for="(theme, index) in themes"
:key="index" :key="index"
:class="{
'bg-gray-50': theme.metadata.name === selectedTheme?.metadata?.name,
}"
class="relative cursor-pointer py-4 transition-all hover:bg-gray-100"
@click="handleSelectTheme(theme)" @click="handleSelectTheme(theme)"
> >
<div class="flex items-center"> <VEntity
<div :is-selected="theme.metadata.name === selectedTheme?.metadata?.name"
v-show="theme.metadata.name === selectedTheme?.metadata?.name" >
class="absolute inset-y-0 left-0 w-0.5 bg-primary" <template #start>
></div> <VEntityField>
<div class="w-40 px-4"> <template #description>
<div <div class="w-32">
class="group aspect-w-4 aspect-h-3 block w-full overflow-hidden rounded border bg-gray-100" <div
class="group aspect-w-4 aspect-h-3 block w-full overflow-hidden rounded border bg-gray-100"
>
<LazyImage
:src="theme.spec.logo"
:alt="theme.spec.displayName"
classes="pointer-events-none object-cover group-hover:opacity-75"
>
<template #loading>
<div
class="flex h-full items-center justify-center object-cover"
>
<span class="text-xs text-gray-400">加载中...</span>
</div>
</template>
<template #error>
<div
class="flex h-full items-center justify-center object-cover"
>
<span class="text-xs text-red-400">加载异常</span>
</div>
</template>
</LazyImage>
</div>
</div>
</template>
</VEntityField>
<VEntityField
:title="theme.spec.displayName"
:description="theme.spec.version"
> >
<img <template #extra>
:src="theme.spec.logo"
alt=""
class="pointer-events-none object-cover group-hover:opacity-75"
/>
</div>
</div>
<div class="flex-1">
<VSpace align="start" direction="column" spacing="xs">
<div class="flex items-center gap-2">
<span class="text-lg font-medium text-gray-900">
{{ theme.spec.displayName }}
</span>
<VTag <VTag
v-if="theme.metadata.name === activatedTheme?.metadata?.name" v-if="theme.metadata.name === activatedTheme?.metadata?.name"
> >
当前启用 当前启用
</VTag> </VTag>
</div> </template>
<div> </VEntityField>
<span class="text-sm text-gray-400"> </template>
{{ theme.spec.version }} <template #end>
</span> <VEntityField v-if="theme.metadata.deletionTimestamp">
</div> <template #description>
</VSpace> <VStatusDot v-tooltip="``" state="warning" animate />
</div> </template>
<div class="px-4"> </VEntityField>
<VSpace spacing="lg"> <VEntityField>
<div> <template #description>
<span class="text-sm text-gray-400 hover:text-blue-600"> <a
class="text-sm text-gray-400 hover:text-blue-600"
:href="theme.spec.author.website"
target="_blank"
@click.stop
>
{{ theme.spec.author.name }} {{ theme.spec.author.name }}
</span> </a>
</div> </template>
<div v-if="theme.spec.repo"> </VEntityField>
<VEntityField>
<template #description>
<a <a
:href="theme.spec.repo" :href="theme.spec.repo"
class="text-gray-900 hover:text-blue-600" class="text-gray-900 hover:text-blue-600"
@ -184,36 +212,20 @@ defineExpose({
> >
<IconGitHub /> <IconGitHub />
</a> </a>
</div> </template>
<div> </VEntityField>
<FloatingDropdown> </template>
<IconMore <template #dropdownItems>
class="rounded text-gray-900 hover:bg-gray-200 hover:text-gray-600" <VButton
@click.stop v-close-popper
/> block
<template #popper> type="danger"
<div class="w-48 p-2"> @click="handleUninstall(theme)"
<VSpace class="w-full" direction="column"> >
<VButton 卸载
v-close-popper </VButton>
:disabled=" </template>
theme.metadata.name === </VEntity>
activatedTheme?.metadata?.name
"
block
type="danger"
@click="handleUninstall(theme)"
>
卸载
</VButton>
</VSpace>
</div>
</template>
</FloatingDropdown>
</div>
</VSpace>
</div>
</div>
</li> </li>
</ul> </ul>
<template #footer> <template #footer>

View File

@ -162,7 +162,11 @@ watch([() => route.name, () => route.params], async () => {
> >
启用 启用
</VButton> </VButton>
<VButton :route="{ name: 'ThemeVisual' }" type="secondary"> <VButton
v-if="false"
:route="{ name: 'ThemeVisual' }"
type="secondary"
>
<template #icon> <template #icon>
<IconEye class="h-full w-full" /> <IconEye class="h-full w-full" />
</template> </template>