Skip to content

Commit 7f51574

Browse files
committed
优化 paper卡片效果
1 parent 2d70b17 commit 7f51574

File tree

1 file changed

+144
-132
lines changed

1 file changed

+144
-132
lines changed

packages/pure/components/pages/Paper.astro

Lines changed: 144 additions & 132 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ type Paper = {
1717
star?: number
1818
tags?: string[]
1919
paperUrl?: string // 新增论文链接字段
20+
author?: string
2021
}
2122
index?: number
2223
}
@@ -41,56 +42,47 @@ const starCount = data.star ? Math.min(Math.max(data.star, 0), 5) : 0
4142
className
4243
)}
4344
>
44-
{/* Star 评分 - 右上角 + 编号 (仅在大屏幕显示) */}
45-
{
46-
(starCount > 0 || typeof paper.index === 'number') && (
47-
<div class='absolute top-4 right-4 items-center gap-1 z-20 hidden md:flex top-right-rating'>
48-
{starCount > 0 && (
49-
<div class='flex gap-0.5'>
50-
{Array.from({ length: 5 }).map((_, i) => (
51-
<Icon
52-
name='star'
53-
class={cn(
54-
'size-4',
55-
i < starCount ? 'text-yellow-400' : 'text-zinc-200 dark:text-zinc-700'
56-
)}
57-
/>
58-
))}
59-
</div>
60-
)}
61-
{typeof paper.index === 'number' && (
62-
<span class='ml-2 text-xs text-zinc-300 dark:text-zinc-600 font-mono select-none'>
63-
No.{String(paper.index).padStart(2, '0')}
64-
</span>
65-
)}
45+
{/*主内容区*/}
46+
<div class='flex flex-col flex-1 min-w-0 z-10'>
47+
{/* 标题与右上角信息容器 */}
48+
<div class='flex justify-between items-center'>
49+
{/* 标题区域 */}
50+
<div class='space-y-1 flex-1 min-w-0 pr-4'>
51+
<h3 class='text-lg font-medium text-zinc-900 dark:text-zinc-100 leading-tight m-0'>
52+
{data.title}
53+
</h3>
54+
{
55+
data.subTitle && (
56+
<p class='text-sm text-zinc-600 dark:text-zinc-400 leading-normal m-0'>
57+
{data.subTitle}
58+
</p>
59+
)
60+
}
6661
</div>
67-
)
68-
}
6962

70-
{/* 右下角倾斜卡片,仅主图标和链接 (仅在大屏幕显示) */}
71-
<div class='paper-card-icon-preview hidden md:block'>
72-
<div class='paper-preview-container'>
73-
<Icon name={data.isbn ? 'paper_book' : 'paper_article'} class='paper-icon' />
63+
{/* Star 评分 - 右上角 + 编号 (仅在大屏幕显示) */}
7464
{
75-
data.paperUrl && (
76-
<a href={data.paperUrl} target='_blank' rel='noopener noreferrer' class='paper-link'>
77-
View &gt;&gt;
78-
</a>
79-
)
80-
}
81-
</div>
82-
</div>
83-
84-
{/* 主内容区 */}
85-
<div class='flex flex-col flex-1 min-w-0 z-10 pr-0 md:pr-20'>
86-
{/* 标题区域 */}
87-
<div class='space-y-1'>
88-
<h3 class='text-lg font-medium text-zinc-900 dark:text-zinc-100 leading-tight m-0'>
89-
{data.title}
90-
</h3>
91-
{
92-
data.subTitle && (
93-
<p class='text-sm text-zinc-600 dark:text-zinc-400 leading-normal m-0'>{data.subTitle}</p>
65+
(starCount > 0 || typeof paper.index === 'number') && (
66+
<div class='flex items-center gap-1 z-20 hidden md:flex top-right-rating large-screen-stars'>
67+
{starCount > 0 && (
68+
<div class='flex gap-0.5'>
69+
{Array.from({ length: 5 }).map((_, i) => (
70+
<Icon
71+
name='star'
72+
class={cn(
73+
'size-4',
74+
i < starCount ? 'text-yellow-400' : 'text-zinc-200 dark:text-zinc-700'
75+
)}
76+
/>
77+
))}
78+
</div>
79+
)}
80+
{typeof paper.index === 'number' && (
81+
<span class='ml-2 text-xs text-zinc-300 dark:text-zinc-600 font-mono select-none'>
82+
No.{String(paper.index).padStart(2, '0')}
83+
</span>
84+
)}
85+
</div>
9486
)
9587
}
9688
</div>
@@ -168,7 +160,9 @@ const starCount = data.star ? Math.min(Math.max(data.star, 0), 5) : 0
168160
}
169161

170162
{/* 小屏幕底部信息行 */}
171-
<div class='mt-4 pt-3 border-t border-zinc-100 dark:border-zinc-800 flex items-center justify-between md:hidden'>
163+
<div
164+
class='mt-4 pt-3 border-t border-zinc-100 dark:border-zinc-800 flex items-center justify-between md:hidden'
165+
>
172166
<div class='flex items-center gap-3'>
173167
{/* 论文类型图标 */}
174168
<div class='flex items-center gap-1 text-sm text-zinc-500 dark:text-zinc-400'>
@@ -178,125 +172,143 @@ const starCount = data.star ? Math.min(Math.max(data.star, 0), 5) : 0
178172
{/* 论文链接 */}
179173
{
180174
data.paperUrl && (
181-
<a
182-
href={data.paperUrl}
183-
target='_blank'
184-
rel='noopener noreferrer'
175+
<a
176+
href={data.paperUrl}
177+
target='_blank'
178+
rel='noopener noreferrer'
185179
class='text-xs text-zinc-500 dark:text-zinc-400 hover:text-zinc-700 dark:hover:text-zinc-200 transition-colors'
186180
>
187181
View &gt;&gt;
188182
</a>
189183
)
190184
}
191185
</div>
192-
186+
193187
{/* 评分和编号 */}
194188
<div class='flex items-center gap-2'>
195189
{/* 编号 */}
196-
{typeof paper.index === 'number' && (
197-
<span class='text-xs text-zinc-400 dark:text-zinc-500 font-mono select-none'>
198-
No.{String(paper.index).padStart(2, '0')}
199-
</span>
200-
)}
190+
{
191+
typeof paper.index === 'number' && (
192+
<span class='text-xs text-zinc-400 dark:text-zinc-500 font-mono select-none'>
193+
No.{String(paper.index).padStart(2, '0')}
194+
</span>
195+
)
196+
}
201197
{/* 评分 */}
202-
{starCount > 0 && (
203-
<div class='flex gap-0.5'>
204-
{Array.from({ length: 5 }).map((_, i) => (
205-
<Icon
206-
name='star'
207-
class={cn(
208-
'size-3',
209-
i < starCount ? 'text-yellow-400' : 'text-zinc-200 dark:text-zinc-700'
210-
)}
211-
/>
212-
))}
213-
</div>
214-
)}
198+
{
199+
starCount > 0 && (
200+
<div class='flex gap-0.5'>
201+
{Array.from({ length: 5 }).map((_, i) => (
202+
<Icon
203+
name='star'
204+
class={cn(
205+
'size-3',
206+
i < starCount ? 'text-yellow-400' : 'text-zinc-200 dark:text-zinc-700'
207+
)}
208+
/>
209+
))}
210+
</div>
211+
)
212+
}
215213
</div>
216214
</div>
217215
</div>
216+
217+
<!-- 浮动卡片链接 -->
218+
{
219+
data.paperUrl && (
220+
<a
221+
href={data.paperUrl}
222+
target='_blank'
223+
rel='noopener noreferrer'
224+
class='paper-card-link-wrapper hidden md:flex'
225+
aria-label={`View paper: ${data.title}`}
226+
>
227+
<div class='paper-preview-container'>
228+
<Icon name={data.isbn ? 'paper_book' : 'paper_article'} class='paper-icon' />
229+
<span class='paper-link-text'>View</span>
230+
</div>
231+
</a>
232+
)
233+
}
218234
</Tag>
219235

220236
<style>
221-
.paper-card-icon-preview {
237+
/* 确保小屏幕隐藏右上角评分和编号 */
238+
@media (max-width: 767px) {
239+
.top-right-rating {
240+
display: none !important;
241+
}
242+
}
243+
244+
/* 浮动卡片链接容器 */
245+
.paper-card-link-wrapper {
222246
position: absolute;
223-
right: 1.2rem;
224-
bottom: 1.2rem;
225-
width: 6.5rem;
226-
height: 5.2rem;
227-
display: flex;
228-
align-items: flex-end;
229-
z-index: 15;
230-
pointer-events: none;
247+
right: 1.5rem;
248+
bottom: 0;
249+
z-index: 10;
250+
transform: translateY(35%);
251+
transition: transform 0.3s cubic-bezier(0.4, 0, 0.2, 1);
252+
text-decoration: none;
253+
}
254+
255+
.group:hover .paper-card-link-wrapper {
256+
transform: translateY(-10%) scale(1.03);
231257
}
258+
259+
/* 卡片视觉样式 */
232260
.paper-preview-container {
233-
position: relative;
234-
width: 100%;
235-
height: 100%;
236261
display: flex;
237262
flex-direction: column;
238263
align-items: center;
239-
justify-content: flex-end;
264+
justify-content: center;
265+
gap: 0.25rem;
266+
width: 5.5rem;
267+
height: 5.5rem;
268+
padding-bottom: 0.25rem;
240269
border-radius: var(--radius);
241-
border: 1px solid #e2e8f0; /* 亮色下深灰 */
242-
background: var(--background);
243-
user-select: none;
244-
transform: scale(1) rotate(0.18rad) translateY(30%);
245-
transition: transform 300ms ease-out;
246-
will-change: transform;
247-
backface-visibility: hidden;
248-
padding: 0.25rem 0.5rem 0.5rem 0.5rem;
249-
pointer-events: auto;
250-
overflow: hidden;
270+
border: 1px solid rgb(226, 232, 240);
271+
box-shadow: 0 4px 6px -1px rgb(0 0 0 / 0.05), 0 2px 4px -2px rgb(0 0 0 / 0.05);
272+
transition: border-color 0.3s;
251273
}
274+
252275
.dark .paper-preview-container {
253-
background: var(--background);
254-
border-color: #f3f4f6; /* 暗色下浅灰 */
276+
border-color: rgb(39, 39, 42);
255277
}
278+
256279
.group:hover .paper-preview-container {
257-
transform: scale(1.04) rotate(0) translateY(15%);
258-
transition: transform 400ms cubic-bezier(0, 0.9, 0.5, 1.35);
280+
border-color: rgb(203, 213, 225);
259281
}
260-
.paper-icon {
261-
width: 2.5rem;
262-
height: 2.5rem;
263-
color: var(--muted-foreground);
264-
margin-bottom: 0.15rem;
265-
z-index: 2;
282+
283+
.dark .group:hover .paper-preview-container {
284+
border-color: rgb(63, 63, 70);
266285
}
267-
.paper-link {
268-
display: flex;
269-
align-items: center;
270-
font-size: 0.75rem;
286+
287+
.paper-icon {
288+
width: 2.25rem;
289+
height: 2.25rem;
271290
color: var(--muted-foreground);
272-
margin-top: 0.15rem;
273-
text-decoration: none;
274-
pointer-events: auto;
275-
transition: color 0.2s;
276-
z-index: 2;
291+
transition: color 0.3s;
277292
}
278-
.paper-link:hover {
293+
294+
.group:hover .paper-icon {
279295
color: var(--foreground);
280296
}
281-
/* 编号右上角淡色小号字体,主题色自适应 */
282-
.paper-index-no {
283-
margin-left: 0.5rem;
284-
font-size: 0.82rem;
297+
298+
.paper-link-text {
299+
font-size: 0.75rem;
285300
color: var(--muted-foreground);
286-
font-family: var(--font-mono, monospace);
287-
user-select: none;
288-
letter-spacing: 0.04em;
289-
font-weight: 500;
301+
opacity: 0;
302+
transform: translateY(5px);
303+
transition:
304+
opacity 0.2s ease-out 0.1s,
305+
transform 0.2s ease-out 0.1s,
306+
color 0.3s;
290307
}
291-
/* 确保小屏幕隐藏右上角评分和编号 */
292-
@media (max-width: 767px) {
293-
.top-right-rating {
294-
display: none !important;
295-
}
296-
297-
/* 强制隐藏倾斜卡片 */
298-
.paper-card-icon-preview {
299-
display: none !important;
300-
}
308+
309+
.group:hover .paper-link-text {
310+
opacity: 1;
311+
transform: translateY(0);
312+
color: var(--foreground);
301313
}
302314
</style>

0 commit comments

Comments
 (0)