Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
86d4c1f
feat(Reorder): add component reorder
EldarMuhamethanov Sep 30, 2025
462c476
feat(Reorder): improve logic
EldarMuhamethanov Sep 30, 2025
180bb7e
feat(Reorder): fix type
EldarMuhamethanov Sep 30, 2025
6beb263
feat(Reorder): add head reorder component logic
EldarMuhamethanov Sep 30, 2025
b8b4845
fix(Reorder): fix comment
EldarMuhamethanov Sep 30, 2025
c8b4216
fix(Reorder): fix gap calculating
EldarMuhamethanov Sep 30, 2025
96d0571
feat(Reorder): add story
EldarMuhamethanov Oct 1, 2025
fda0b9d
feat(Reorder): add documentation
EldarMuhamethanov Oct 1, 2025
60032b4
docs(Reorder): add docs
EldarMuhamethanov Oct 1, 2025
c0afbea
fix(Reorder): fix baseline tests
EldarMuhamethanov Oct 2, 2025
227218e
Merge branch 'master' into e.muhamethanov/reorder-component
EldarMuhamethanov Oct 2, 2025
1a7ebb6
fix(Reorder): add tests
EldarMuhamethanov Oct 2, 2025
353f570
feat(Reorder): improve code
EldarMuhamethanov Oct 2, 2025
1b3a1c5
feat(Reorder): improve code
EldarMuhamethanov Oct 3, 2025
d5a6725
fix(Reorder): fix type
EldarMuhamethanov Oct 3, 2025
e6ca56b
Merge branch 'master' into e.muhamethanov/reorder-component
EldarMuhamethanov Oct 6, 2025
ec09492
fix(Reorder): fix subcomponents
EldarMuhamethanov Oct 6, 2025
0804ea4
Merge branch 'master' into e.muhamethanov/reorder-component
EldarMuhamethanov Oct 16, 2025
f9406a3
test: add test without subcomponents
EldarMuhamethanov Oct 16, 2025
0a0570f
Merge branch 'master' into e.muhamethanov/reorder-component
EldarMuhamethanov Oct 22, 2025
fb0490b
Merge branch 'master' into e.muhamethanov/reorder-component
EldarMuhamethanov Nov 18, 2025
88687e7
fix: fix format
EldarMuhamethanov Nov 21, 2025
5e98380
Merge branch 'master' into e.muhamethanov/reorder-component
EldarMuhamethanov Jan 15, 2026
928ea77
fix: fix tests
EldarMuhamethanov Jan 15, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 15 additions & 7 deletions packages/vkui/src/components/Cell/Cell.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,9 +7,9 @@ import { useExternRef } from '../../hooks/useExternRef';
import { usePlatform } from '../../hooks/usePlatform';
import type { HasRootRef } from '../../types';
import { Removable, type RemovableProps } from '../Removable/Removable';
import { Reorder } from '../Reorder/Reorder';
import { SimpleCell, type SimpleCellProps } from '../SimpleCell/SimpleCell';
import { CellCheckbox, type CellCheckboxProps } from './CellCheckbox/CellCheckbox';
import { CellDragger } from './CellDragger/CellDragger';
import { DEFAULT_DRAGGABLE_LABEL } from './constants';
import styles from './Cell.module.css';

Expand Down Expand Up @@ -98,15 +98,13 @@ export const Cell: React.FC<CellProps> & {
const rootElRef = useExternRef(getRootRef);

const dragger = draggable ? (
<CellDragger
elRef={rootElRef}
<Reorder.Trigger
className={classNames(styles.dragger, !before && !selectable && styles.controlNoBefore)}
onDragStateChange={setDragging}
onDragFinish={onDragFinish}
data-testid={draggerTestId}
>
{draggerLabel}
</CellDragger>
<Reorder.TriggerIcon>{draggerLabel}</Reorder.TriggerIcon>
</Reorder.Trigger>
) : null;

let checkbox;
Expand Down Expand Up @@ -166,6 +164,7 @@ export const Cell: React.FC<CellProps> & {
if (removable) {
return (
<Removable
Component={draggable ? Reorder.Item : undefined}
className={classNames(cellClasses, className)}
style={style}
getRootRef={rootElRef}
Expand All @@ -188,7 +187,16 @@ export const Cell: React.FC<CellProps> & {
);
}

return (
return draggable ? (
<Reorder.Item
className={classNames(cellClasses, className)}
style={style}
getRootRef={rootElRef}
onReorder={onDragFinish}
>
<SimpleCell {...simpleCellProps} />
</Reorder.Item>
) : (
<div className={classNames(cellClasses, className)} style={style} ref={rootElRef}>
<SimpleCell {...simpleCellProps} />
</div>
Expand Down

This file was deleted.

This file was deleted.

60 changes: 0 additions & 60 deletions packages/vkui/src/components/Cell/CellDragger/CellDragger.tsx

This file was deleted.

4 changes: 0 additions & 4 deletions packages/vkui/src/components/List/List.module.css
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,3 @@
display: grid;
grid-template-columns: minmax(0, 1fr);
}

.placeholder {
display: none;
}
41 changes: 21 additions & 20 deletions packages/vkui/src/components/List/List.tsx
Original file line number Diff line number Diff line change
@@ -1,35 +1,36 @@
import * as React from 'react';
import { DATA_DRAGGABLE_PLACEHOLDER_REACT_PROP } from '../../hooks/useDraggableWithDomApi';
import { classNames } from '@vkontakte/vkjs';
import type { HTMLAttributesWithRootRef } from '../../types';
import { RootComponent } from '../RootComponent/RootComponent';
import { Reorder, type ReorderProps } from '../Reorder/Reorder';
import styles from './List.module.css';

export type ListProps = HTMLAttributesWithRootRef<HTMLDivElement> & {
/**
* Задает отступ между элементами.
*/
gap?: number;
};
export type ListProps = HTMLAttributesWithRootRef<HTMLDivElement> &
Pick<ReorderProps, 'onReorder'> & {
/**
* Задает отступ между элементами.
*/
gap?: number;
};

/**
* @see https://vkui.io/components/cell#list
*/
export const List = ({ children, gap = 0, ...restProps }: ListProps): React.ReactNode => {
export const List = ({
children,
gap = 0,
onReorder,
className,
...restProps
}: ListProps): React.ReactNode => {
return (
<RootComponent
<Reorder.Root
role="list"
baseClassName={styles.host}
baseStyle={{
gridGap: gap,
}}
className={classNames(styles.host, className)}
gap={gap}
onReorder={onReorder}
{...restProps}
>
{children}
<div
aria-hidden
{...DATA_DRAGGABLE_PLACEHOLDER_REACT_PROP}
className={styles.placeholder}
></div>
</RootComponent>
</Reorder.Root>
);
};
3 changes: 2 additions & 1 deletion packages/vkui/src/components/Removable/Removable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import { Icon24Cancel } from '@vkontakte/icons';
import { classNames } from '@vkontakte/vkjs';
import { usePlatform } from '../../hooks/usePlatform';
import { getTextFromChildren } from '../../lib/children';
import type { HTMLAttributesWithRootRef } from '../../types';
import type { HasComponent, HTMLAttributesWithRootRef } from '../../types';
import { IconButton } from '../IconButton/IconButton';
import { RootComponent } from '../RootComponent/RootComponent';
import { RemovableIos } from './RemovableIos';
Expand Down Expand Up @@ -95,6 +95,7 @@ export interface RemovableIosRenderProps {

interface RemovableOwnProps
extends Omit<HTMLAttributesWithRootRef<HTMLDivElement>, 'children'>,
HasComponent,
RemovableProps {
/**
* Расположение кнопки удаления.
Expand Down
107 changes: 107 additions & 0 deletions packages/vkui/src/components/Reorder/Reorder.stories.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,107 @@
import * as React from 'react';
import type { Meta, StoryObj } from '@storybook/react';
import { Icon28MessageOutline } from '@vkontakte/icons';
import { noop } from '@vkontakte/vkjs';
import { withSinglePanel, withVKUILayout } from '../../storybook/VKUIDecorators';
import { CanvasFullLayout, DisableCartesianParam } from '../../storybook/constants';
import { createStoryParameters } from '../../testing/storybook/createStoryParameters';
import { Avatar } from '../Avatar/Avatar.tsx';
import { Flex } from '../Flex/Flex.tsx';
import { Group } from '../Group/Group';
import { IconButton } from '../IconButton/IconButton.tsx';
import { SimpleCell } from '../SimpleCell/SimpleCell.tsx';
import { Reorder, type ReorderProps } from './Reorder';

const story: Meta<ReorderProps> = {
title: 'Utils/Reorder',
component: Reorder,
parameters: createStoryParameters('Reorder', CanvasFullLayout, DisableCartesianParam),
tags: ['Утилиты'],
};

export default story;

type Story = StoryObj<
ReorderProps<{
avatarUrl: string;
name: string;
screenName: string;
}>
>;

export const Playground: Story = {
render: function Render({ items, ...args }) {
const [draggingList, updateDraggingList] = React.useState(items);

const onDragFinish: ReorderProps['onReorder'] = (swappedItems) => {
updateDraggingList(Reorder.onReorder(swappedItems, draggingList));
};

return (
<Reorder.Root gap={10} onReorder={onDragFinish} {...args}>
{draggingList.map((item) => (
<SimpleCell
key={item.screenName}
Component={Reorder.Item}
hasHover={false}
before={
<Flex align="center" gap={10}>
<Reorder.Trigger>
<Reorder.TriggerIcon>Перенести ячейку</Reorder.TriggerIcon>
</Reorder.Trigger>
<Avatar size={48} src={item.avatarUrl} />
</Flex>
}
after={
<IconButton label="Написать сообщение" onClick={noop}>
<Icon28MessageOutline />
</IconButton>
}
subtitle={item.screenName}
onClick={noop}
>
{item.name}
</SimpleCell>
))}
</Reorder.Root>
);
},
args: {
items: [
{
avatarUrl: 'https://avatars.githubusercontent.com/u/61377022',
name: 'Эльдар Мухаметханов',
screenName: 'e.muhamethanov',
},
{
avatarUrl: 'https://avatars.githubusercontent.com/u/5850354',
name: 'Ином Мирджамолов',
screenName: 'inomdzhon',
},
{
avatarUrl: 'https://avatars.githubusercontent.com/u/7431217',
name: 'Вика Жижонкова',
screenName: 'BlackySoul',
},
{
avatarUrl: 'https://avatars.githubusercontent.com/u/14944123',
name: 'Даниил Суворов',
screenName: 'SevereCloud',
},
{
avatarUrl: 'https://avatars.githubusercontent.com/u/32414396',
name: 'Никита Денисов',
screenName: 'qurle',
},
],
},
decorators: [
(Component, context) => (
<Group>
<Component {...context.args} />
</Group>
),
withSinglePanel,
withVKUILayout,
],
};
Loading