Skip to content

Commit 1cc89a1

Browse files
feat(user-profile): add text animation and 40px size
1 parent 3c28b50 commit 1cc89a1

4 files changed

Lines changed: 110 additions & 25 deletions

File tree

apps/xi.storybook/src/stories/UserProfile.stories.tsx

Lines changed: 60 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -8,21 +8,67 @@ const meta = {
88
layout: 'centered',
99
},
1010
tags: ['autodocs'],
11+
argTypes: {
12+
size: {
13+
control: 'select',
14+
options: ['l', '40', 'm', 's'],
15+
description: 'Размер аватара и текста',
16+
},
17+
userId: {
18+
control: 'number',
19+
description: 'ID пользователя для загрузки аватара',
20+
},
21+
text: {
22+
control: 'text',
23+
description: 'Основной текст (имя)',
24+
},
25+
label: {
26+
control: 'text',
27+
description: 'Подпись под именем',
28+
},
29+
src: {
30+
control: 'text',
31+
description: 'URL кастомного аватара',
32+
},
33+
withOutText: {
34+
control: 'boolean',
35+
description: 'Скрыть текст и подпись',
36+
},
37+
loading: {
38+
control: 'boolean',
39+
description: 'Состояние загрузки',
40+
},
41+
color: {
42+
control: 'select',
43+
options: ['brand'],
44+
description: 'Цвет фолбэка аватара',
45+
},
46+
},
47+
args: {
48+
userId: 1,
49+
text: 'Иван Иванов',
50+
label: 'Разработчик',
51+
size: 'm',
52+
withOutText: false,
53+
loading: false,
54+
color: 'brand',
55+
},
1156
} satisfies Meta<typeof UserProfile>;
1257

1358
export default meta;
1459
type Story = StoryObj<typeof meta>;
1560

1661
export const Default: Story = {
17-
render: () => <UserProfile userId={1} text="Иван Иванов" label="Разработчик" />,
62+
render: (args) => <UserProfile {...args} />,
1863
};
1964

2065
export const Sizes: Story = {
2166
render: () => (
2267
<div className="flex items-center gap-4">
2368
<UserProfile size="l" userId={1} text="Иван Иванов" label="Разработчик" />
24-
<UserProfile size="m" userId={2} text="Петр Петров" label="Дизайнер" />
25-
<UserProfile size="s" userId={3} text="Анна Аннова" />
69+
<UserProfile size="40" userId={2} text="Петр Петров" label="Дизайнер" />
70+
<UserProfile size="m" userId={3} text="Мария Сидорова" label="Менеджер" />
71+
<UserProfile size="s" userId={4} text="Анна Аннова" />
2672
</div>
2773
),
2874
};
@@ -31,23 +77,23 @@ export const Loading: Story = {
3177
render: () => (
3278
<div className="flex items-center gap-4">
3379
<UserProfile loading size="l" userId={1} text="Иван Иванов" label="Разработчик" />
34-
<UserProfile loading size="m" userId={2} text="Петр Петров" label="Дизайнер" />
35-
<UserProfile loading size="s" userId={3} text="Анна Аннова" />
80+
<UserProfile loading size="40" userId={2} text="Петр Петров" label="Дизайнер" />
81+
<UserProfile loading size="m" userId={3} text="Мария Сидорова" label="Менеджер" />
82+
<UserProfile loading size="s" userId={4} text="Анна Аннова" />
3683
</div>
3784
),
3885
};
3986

4087
export const WithoutText: Story = {
41-
render: () => <UserProfile withOutText userId={1} text="Иван Иванов" label="Разработчик" />,
88+
args: {
89+
withOutText: true,
90+
},
91+
render: (args) => <UserProfile {...args} />,
4292
};
4393

4494
export const WithCustomAvatar: Story = {
45-
render: () => (
46-
<UserProfile
47-
userId={1}
48-
text="Иван Иванов"
49-
label="Разработчик"
50-
src="https://example.com/avatar.jpg"
51-
/>
52-
),
95+
args: {
96+
src: 'https://example.com/avatar.jpg',
97+
},
98+
render: (args) => <UserProfile {...args} />,
5399
};

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

packages/pkg.user.profile/UserProfile.tsx

Lines changed: 46 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ export const userProfileVariants = cva('flex flex-row items-center', {
88
variants: {
99
size: {
1010
l: 'h-[48px] gap-2',
11+
'40': 'h-[40px] gap-2',
1112
m: 'h-[32px] gap-2',
1213
s: 'h-[24px] gap-1.5',
1314
},
@@ -21,6 +22,7 @@ export const userProfileTextVariants = cva('text-gray-100', {
2122
variants: {
2223
size: {
2324
l: 'text-[16px]',
25+
'40': 'text-[14px]',
2426
m: 'text-[14px]',
2527
s: 'text-[12px]',
2628
},
@@ -34,6 +36,11 @@ export const userProfileTextVariants = cva('text-gray-100', {
3436
size: 'l',
3537
class: 'bg-gray-10 h-[16px] w-[96px] animate-pulse rounded-[2px]',
3638
},
39+
{
40+
loading: true,
41+
size: '40',
42+
class: 'bg-gray-10 h-[14px] w-[96px] animate-pulse rounded-[2px]',
43+
},
3744
{
3845
loading: true,
3946
size: 'm',
@@ -55,6 +62,7 @@ export const userProfileLabelVariants = cva('font-normal text-gray-60 mt-[-2px]'
5562
variants: {
5663
size: {
5764
l: 'text-[12px]',
65+
'40': 'text-[11px]',
5866
m: 'text-[10px]',
5967
s: '',
6068
},
@@ -68,6 +76,11 @@ export const userProfileLabelVariants = cva('font-normal text-gray-60 mt-[-2px]'
6876
size: 'l',
6977
class: 'bg-gray-10 h-[12px] w-[64px] animate-pulse rounded-[2px]',
7078
},
79+
{
80+
loading: true,
81+
size: '40',
82+
class: 'bg-gray-10 h-[11px] w-[64px] animate-pulse rounded-[2px]',
83+
},
7184
{
7285
loading: true,
7386
size: 'm',
@@ -89,6 +102,7 @@ export const avatarVariants = cva('flex items-center justify-center font-semibol
89102
xxl: 'h-[128px] w-[128px] min-h-[128px] min-w-[128px] rounded-[64px] text-[48px]',
90103
xl: 'h-[64px] w-[64px] min-h-[64px] min-w-[64px] rounded-[32px] text-[24px]',
91104
l: 'h-[48px] w-[48px] min-h-[48px] min-w-[48px] rounded-[24px] text-[16px]',
105+
'40': 'h-[40px] w-[40px] min-h-[40px] min-w-[40px] rounded-[20px] text-[14px]',
92106
m: 'h-[32px] w-[32px] min-h-[32px] min-w-[32px] rounded-[16px] text-[12px]',
93107
s: 'h-[24px] w-[24px] min-h-[24px] min-w-[24px] rounded-[12px] text-[10px]',
94108
},
@@ -100,7 +114,7 @@ export const avatarVariants = cva('flex items-center justify-center font-semibol
100114
});
101115

102116
export interface UserProfileProps extends React.HTMLAttributes<HTMLDivElement> {
103-
size?: 'l' | 'm' | 's';
117+
size?: 'l' | '40' | 'm' | 's';
104118
src?: string;
105119
userId: number | null;
106120
color?: 'brand';
@@ -127,7 +141,15 @@ export const UserProfile = ({
127141
...props
128142
}: UserProfileProps) => {
129143
return (
130-
<div className={cn(userProfileVariants({ size }), className)} {...props}>
144+
<div
145+
className={cn(
146+
userProfileVariants({ size }),
147+
withOutText && 'gap-0',
148+
'transition-[gap] duration-200 ease-linear',
149+
className,
150+
)}
151+
{...props}
152+
>
131153
<Avatar size={size}>
132154
<AvatarImage
133155
src={src || `https://api.sovlium.ru/files/users/${userId}/avatar.webp`}
@@ -139,18 +161,35 @@ export const UserProfile = ({
139161
<AvatarFallback size={size}>{text[0].toUpperCase()}</AvatarFallback>
140162
)}
141163
</Avatar>
142-
{!withOutText && (
143-
<div className={`flex flex-col ${loading && 'gap-1'}`}>
144-
<span className={cn(userProfileTextVariants({ size, loading }), classNameText)}>
164+
<div
165+
className={cn(
166+
'min-w-0 overflow-hidden transition-[max-width,opacity] duration-200 ease-linear',
167+
withOutText ? 'max-w-0 opacity-0' : 'max-w-[16rem] opacity-100',
168+
)}
169+
>
170+
<div className={`flex min-w-0 flex-col overflow-hidden ${loading && 'gap-1'}`}>
171+
<span
172+
className={cn(
173+
'truncate whitespace-nowrap',
174+
userProfileTextVariants({ size, loading }),
175+
classNameText,
176+
)}
177+
>
145178
{!loading && text}
146179
</span>
147180
{size !== 's' && (
148-
<span className={cn(userProfileLabelVariants({ size, loading }), classNameLabel)}>
181+
<span
182+
className={cn(
183+
'truncate whitespace-nowrap',
184+
userProfileLabelVariants({ size, loading }),
185+
classNameLabel,
186+
)}
187+
>
149188
{!loading && label}
150189
</span>
151190
)}
152191
</div>
153-
)}
192+
</div>
154193
</div>
155194
);
156195
};

packages/pkg.user.profile/package.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@xipkg/userprofile",
3-
"version": "4.0.14",
3+
"version": "4.1.0",
44
"main": "./dist/index.mjs",
55
"module": "./dist/index.mjs",
66
"types": "./dist/index.d.mts",
@@ -26,7 +26,7 @@
2626
"lint": "eslint \"**/*.ts*\""
2727
},
2828
"dependencies": {
29-
"@xipkg/avatar": "^3.0.10",
29+
"@xipkg/avatar": "^3.1.0",
3030
"@xipkg/utils": "^1.8.0",
3131
"class-variance-authority": "^0.7.1"
3232
},

0 commit comments

Comments
 (0)