Files
jiang13-forum/frontend/src/components/AsideCheckInStrip.tsx
freefire 9e134916a4 fix: 软刷新齐套前保留旧画面,避免一点击就卸光
Logo/下拉静默预热后一次覆盖;commit 不再先 reset/loading;顺带会话预取与可配置 Feed 排序标签。
2026-09-01 04:56:10 +08:00

106 lines
3.4 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import { CalendarCheck, Check, Gift, Loader2 } from 'lucide-react';
import { useNavigate } from 'react-router-dom';
import { useCheckIn } from '../hooks/useCheckIn';
import { useAuth } from '../hooks/useAuth';
import { loginPath } from '../utils/authRedirect';
/** 右侧栏首块底部:每日签到 */
export default function AsideCheckInStrip() {
const nav = useNavigate();
const { user, loading: authLoading } = useAuth();
const { status, loading, busy, doCheckIn } = useCheckIn(!!user && !authLoading);
// 鉴权未完成:空白,避免「登录签到」→「今日已签到」闪一下
if (authLoading) {
return null;
}
if (!user) {
return (
<div className="widget-checkin">
<div className="widget-checkin-panel widget-checkin-panel--guest">
<div className="widget-checkin-main">
<div className="widget-checkin-icon" aria-hidden>
<CalendarCheck size={18} strokeWidth={2.25} />
</div>
<div className="widget-checkin-info">
<span className="widget-checkin-title"></span>
<span className="widget-checkin-meta"> 515 </span>
</div>
</div>
<button
type="button"
className="widget-checkin-action"
onClick={() => nav(loginPath())}
>
<Gift size={15} aria-hidden />
</button>
</div>
</div>
);
}
// 登录用户status 未到齐前不渲染最终态
if (loading || !status) {
return null;
}
const checkedIn = !!status.checked_in;
const streak = status.streak ?? 0;
const todayPoints = status.today_points ?? 5;
const meta = checkedIn
? (streak > 0 ? `连续 ${streak} 天 · 今日已获得 ${todayPoints} 积分` : `今日已获得 ${todayPoints} 积分`)
: (streak > 0 ? `连续 ${streak} 天 · 今日可得 ${todayPoints} 积分` : `今日签到可得 ${todayPoints} 积分`);
return (
<div className="widget-checkin">
<div
className={`widget-checkin-panel${checkedIn ? ' widget-checkin-panel--done' : ''}`}
>
<div className="widget-checkin-main">
<div className="widget-checkin-icon" aria-hidden>
{checkedIn ? (
<Check size={18} strokeWidth={2.5} />
) : (
<CalendarCheck size={18} strokeWidth={2.25} />
)}
</div>
<div className="widget-checkin-info">
<span className="widget-checkin-title">
{checkedIn ? '今日已签到' : '每日签到'}
</span>
<span className="widget-checkin-meta">{meta}</span>
</div>
{!checkedIn && (
<span className="widget-checkin-reward" aria-hidden>
{todayPoints}
</span>
)}
</div>
{!checkedIn && (
<button
type="button"
className="widget-checkin-action"
disabled={busy}
onClick={doCheckIn}
>
{busy ? (
<>
<Loader2 size={15} className="widget-checkin-action-spinner animate-spin" aria-hidden />
</>
) : (
<>
<Gift size={15} aria-hidden />
</>
)}
</button>
)}
</div>
</div>
);
}