收口前端平台组件能力
新增 PlatformAsyncStatePanel 统一 profile 异步状态骨架 扩展 PlatformSegmentedTabs 支持滚动 tab 并接入创作入口与发现页 统一 PixelCloseButton 复用 PlatformModalCloseButton 像素关闭能力 抽取平台入口泥点前置提示弹层并收紧阻断语义 补充组件收口文档与共享决策记录
This commit is contained in:
@@ -4,6 +4,7 @@ import type { ReactNode } from 'react';
|
||||
import communityQqQrImage from '../../../media/social-media-group/qq.png';
|
||||
import communityWechatQrImage from '../../../media/social-media-group/wechat.png';
|
||||
import type { ProfileReferralInviteCenterResponse } from '../../../packages/shared/src/contracts/runtime';
|
||||
import { PlatformAsyncStatePanel } from '../common/PlatformAsyncStatePanel';
|
||||
import { CopyFeedbackButton } from '../common/CopyFeedbackButton';
|
||||
import { PlatformActionButton } from '../common/PlatformActionButton';
|
||||
import { PlatformEmptyState } from '../common/PlatformEmptyState';
|
||||
@@ -134,144 +135,154 @@ export function PlatformProfileReferralModal({
|
||||
</div>
|
||||
);
|
||||
} else if (panel === 'redeem') {
|
||||
content = isLoading ? (
|
||||
<div className="mt-5 space-y-3">
|
||||
<div className="h-12 animate-pulse rounded-xl bg-zinc-100" />
|
||||
<div className="h-11 animate-pulse rounded-xl bg-zinc-100" />
|
||||
</div>
|
||||
) : center?.hasRedeemedCode ? (
|
||||
<PlatformEmptyState
|
||||
surface="subpanel"
|
||||
size="inline"
|
||||
tone="base"
|
||||
className="mt-5"
|
||||
>
|
||||
已填写邀请码
|
||||
</PlatformEmptyState>
|
||||
) : (
|
||||
<form
|
||||
className="mt-5 space-y-3"
|
||||
onSubmit={(event) => {
|
||||
event.preventDefault();
|
||||
onSubmitRedeemCode();
|
||||
}}
|
||||
>
|
||||
<PlatformTextField
|
||||
value={redeemCode}
|
||||
onChange={(event) => onRedeemCodeChange(event.target.value)}
|
||||
size="lg"
|
||||
density="roomy"
|
||||
tone="rose"
|
||||
className="rounded-xl text-center font-black uppercase tracking-[0.16em]"
|
||||
placeholder="邀请码"
|
||||
aria-label="邀请码"
|
||||
autoComplete="off"
|
||||
autoFocus
|
||||
/>
|
||||
<PlatformActionButton
|
||||
type="submit"
|
||||
surface="profile"
|
||||
fullWidth
|
||||
size="md"
|
||||
className="rounded-xl"
|
||||
disabled={isSubmittingRedeem || !normalizedRedeemCode}
|
||||
>
|
||||
{isSubmittingRedeem ? '提交中' : '提交'}
|
||||
</PlatformActionButton>
|
||||
</form>
|
||||
);
|
||||
} else if (isLoading) {
|
||||
content = (
|
||||
<div className="mt-5 space-y-3">
|
||||
<div className="h-20 animate-pulse rounded-xl bg-zinc-100" />
|
||||
<div className="h-10 animate-pulse rounded-xl bg-zinc-100" />
|
||||
</div>
|
||||
<PlatformAsyncStatePanel
|
||||
isLoading={isLoading}
|
||||
loadingState={
|
||||
<div className="mt-5 space-y-3">
|
||||
<div className="h-12 animate-pulse rounded-xl bg-zinc-100" />
|
||||
<div className="h-11 animate-pulse rounded-xl bg-zinc-100" />
|
||||
</div>
|
||||
}
|
||||
isEmpty={Boolean(center?.hasRedeemedCode)}
|
||||
emptyState={
|
||||
<PlatformEmptyState
|
||||
surface="subpanel"
|
||||
size="inline"
|
||||
tone="base"
|
||||
className="mt-5"
|
||||
>
|
||||
已填写邀请码
|
||||
</PlatformEmptyState>
|
||||
}
|
||||
>
|
||||
<form
|
||||
className="mt-5 space-y-3"
|
||||
onSubmit={(event) => {
|
||||
event.preventDefault();
|
||||
onSubmitRedeemCode();
|
||||
}}
|
||||
>
|
||||
<PlatformTextField
|
||||
value={redeemCode}
|
||||
onChange={(event) => onRedeemCodeChange(event.target.value)}
|
||||
size="lg"
|
||||
density="roomy"
|
||||
tone="rose"
|
||||
className="rounded-xl text-center font-black uppercase tracking-[0.16em]"
|
||||
placeholder="邀请码"
|
||||
aria-label="邀请码"
|
||||
autoComplete="off"
|
||||
autoFocus
|
||||
/>
|
||||
<PlatformActionButton
|
||||
type="submit"
|
||||
surface="profile"
|
||||
fullWidth
|
||||
size="md"
|
||||
className="rounded-xl"
|
||||
disabled={isSubmittingRedeem || !normalizedRedeemCode}
|
||||
>
|
||||
{isSubmittingRedeem ? '提交中' : '提交'}
|
||||
</PlatformActionButton>
|
||||
</form>
|
||||
</PlatformAsyncStatePanel>
|
||||
);
|
||||
} else {
|
||||
content = (
|
||||
<div className="mt-5 space-y-3">
|
||||
<PlatformSubpanel
|
||||
as="div"
|
||||
surface="flat"
|
||||
radius="xs"
|
||||
padding="md"
|
||||
className="text-center"
|
||||
>
|
||||
<PlatformFieldLabel
|
||||
variant="section"
|
||||
className="block text-[11px] text-zinc-500"
|
||||
>
|
||||
邀请码
|
||||
</PlatformFieldLabel>
|
||||
<div className="mt-1 text-3xl font-black tracking-[0.16em] text-[#ff4056]">
|
||||
{center?.inviteCode ?? '--------'}
|
||||
<PlatformAsyncStatePanel
|
||||
isLoading={isLoading}
|
||||
loadingState={
|
||||
<div className="mt-5 space-y-3">
|
||||
<div className="h-20 animate-pulse rounded-xl bg-zinc-100" />
|
||||
<div className="h-10 animate-pulse rounded-xl bg-zinc-100" />
|
||||
</div>
|
||||
</PlatformSubpanel>
|
||||
<PlatformStatusMessage
|
||||
tone="warning"
|
||||
surface="profile"
|
||||
size="md"
|
||||
className="space-y-0.5 px-3.5 font-semibold"
|
||||
>
|
||||
<div>
|
||||
{`邀请一个用户注册,双方都可以获得${center?.rewardPoints ?? 30}泥点。`}
|
||||
</div>
|
||||
<div>每日最多获得十次邀请奖励。</div>
|
||||
</PlatformStatusMessage>
|
||||
<CopyFeedbackButton
|
||||
state={copyInviteState}
|
||||
onClick={onCopyInvite}
|
||||
disabled={!center?.inviteCode}
|
||||
idleLabel="复制邀请"
|
||||
copiedLabel="已复制"
|
||||
failedLabel="复制失败"
|
||||
idleIcon={<Copy className="h-4 w-4" />}
|
||||
actionSurface="profile"
|
||||
actionSize="md"
|
||||
actionFullWidth
|
||||
className="gap-2 rounded-xl"
|
||||
/>
|
||||
<PlatformSubpanel as="div" surface="flat" radius="xs" padding="sm">
|
||||
<PlatformFieldLabel
|
||||
variant="section"
|
||||
className="block text-zinc-900"
|
||||
}
|
||||
>
|
||||
<div className="mt-5 space-y-3">
|
||||
<PlatformSubpanel
|
||||
as="div"
|
||||
surface="flat"
|
||||
radius="xs"
|
||||
padding="md"
|
||||
className="text-center"
|
||||
>
|
||||
成功邀请
|
||||
</PlatformFieldLabel>
|
||||
{center?.invitedUsers?.length ? (
|
||||
<div className="mt-3 max-h-44 space-y-2 overflow-y-auto pr-1">
|
||||
{center.invitedUsers.map((user) => (
|
||||
<PlatformSubpanel
|
||||
as="div"
|
||||
key={`${user.userId}-${user.boundAt}`}
|
||||
surface="soft"
|
||||
radius="xs"
|
||||
padding="row"
|
||||
className="flex items-center gap-3"
|
||||
>
|
||||
<ProfileReferralUserAvatar
|
||||
name={user.displayName}
|
||||
avatarUrl={user.avatarUrl}
|
||||
/>
|
||||
<div className="min-w-0 flex-1">
|
||||
<div className="truncate text-sm font-bold text-zinc-900">
|
||||
{user.displayName || '玩家'}
|
||||
</div>
|
||||
</div>
|
||||
</PlatformSubpanel>
|
||||
))}
|
||||
</div>
|
||||
) : (
|
||||
<PlatformEmptyState
|
||||
surface="subpanel"
|
||||
size="compact"
|
||||
className="mt-3 text-center text-xs font-semibold leading-normal"
|
||||
<PlatformFieldLabel
|
||||
variant="section"
|
||||
className="block text-[11px] text-zinc-500"
|
||||
>
|
||||
暂无成功邀请
|
||||
</PlatformEmptyState>
|
||||
)}
|
||||
</PlatformSubpanel>
|
||||
</div>
|
||||
邀请码
|
||||
</PlatformFieldLabel>
|
||||
<div className="mt-1 text-3xl font-black tracking-[0.16em] text-[#ff4056]">
|
||||
{center?.inviteCode ?? '--------'}
|
||||
</div>
|
||||
</PlatformSubpanel>
|
||||
<PlatformStatusMessage
|
||||
tone="warning"
|
||||
surface="profile"
|
||||
size="md"
|
||||
className="space-y-0.5 px-3.5 font-semibold"
|
||||
>
|
||||
<div>
|
||||
{`邀请一个用户注册,双方都可以获得${center?.rewardPoints ?? 30}泥点。`}
|
||||
</div>
|
||||
<div>每日最多获得十次邀请奖励。</div>
|
||||
</PlatformStatusMessage>
|
||||
<CopyFeedbackButton
|
||||
state={copyInviteState}
|
||||
onClick={onCopyInvite}
|
||||
disabled={!center?.inviteCode}
|
||||
idleLabel="复制邀请"
|
||||
copiedLabel="已复制"
|
||||
failedLabel="复制失败"
|
||||
idleIcon={<Copy className="h-4 w-4" />}
|
||||
actionSurface="profile"
|
||||
actionSize="md"
|
||||
actionFullWidth
|
||||
className="gap-2 rounded-xl"
|
||||
/>
|
||||
<PlatformSubpanel as="div" surface="flat" radius="xs" padding="sm">
|
||||
<PlatformFieldLabel
|
||||
variant="section"
|
||||
className="block text-zinc-900"
|
||||
>
|
||||
成功邀请
|
||||
</PlatformFieldLabel>
|
||||
{center?.invitedUsers?.length ? (
|
||||
<div className="mt-3 max-h-44 space-y-2 overflow-y-auto pr-1">
|
||||
{center.invitedUsers.map((user) => (
|
||||
<PlatformSubpanel
|
||||
as="div"
|
||||
key={`${user.userId}-${user.boundAt}`}
|
||||
surface="soft"
|
||||
radius="xs"
|
||||
padding="row"
|
||||
className="flex items-center gap-3"
|
||||
>
|
||||
<ProfileReferralUserAvatar
|
||||
name={user.displayName}
|
||||
avatarUrl={user.avatarUrl}
|
||||
/>
|
||||
<div className="min-w-0 flex-1">
|
||||
<div className="truncate text-sm font-bold text-zinc-900">
|
||||
{user.displayName || '玩家'}
|
||||
</div>
|
||||
</div>
|
||||
</PlatformSubpanel>
|
||||
))}
|
||||
</div>
|
||||
) : (
|
||||
<PlatformEmptyState
|
||||
surface="subpanel"
|
||||
size="compact"
|
||||
className="mt-3 text-center text-xs font-semibold leading-normal"
|
||||
>
|
||||
暂无成功邀请
|
||||
</PlatformEmptyState>
|
||||
)}
|
||||
</PlatformSubpanel>
|
||||
</div>
|
||||
</PlatformAsyncStatePanel>
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user