Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

docs(ModalRoot): add info about wrappers of modals #8100

Merged
merged 2 commits into from
Dec 18, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
57 changes: 57 additions & 0 deletions packages/vkui/src/components/ModalRoot/Readme.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,11 @@
Менеджер модальных окон.

- <a href="{{anchor}}">Спецификация</a>
- <a href="{{anchor}}">FAQ</a>
- <a href="{{anchor}}">Могу ли я создавать обёртки для `ModalPage` / `ModalCard`?</a>

# Спецификация

В качестве `children` принимает коллекцию [`ModalPage`](#/ModalPage) и/или [`ModalCard`](#/ModalCard). У каждого модального окна
должен быть уникальный `id`.

Expand Down Expand Up @@ -538,3 +544,54 @@ const App = () => {

<App />;
```

# FAQ

## Могу ли я создавать обёртки для `ModalPage` / `ModalCard`?

Да, но нужно учитывать, что бизнес-логика должна либо вызываться внутри `ModalPage` / `ModalCard`, либо включаться в зависимости от
контекста `useModalRootContext()`, т.к. `ModalRoot` лишь передаёт через контекст свойство `activeModal`, а `ModalPage` / `ModalCard`
сравнивают его значение со своим `id` / `nav` – если совпадает, монтируются; иначе размонтируются.

```jsx static
const SomeAsyncEffect = () => {
const [data, setData] = useState({});
useEffect(function fetchData() {
fetch('...')
.then((r) => r.json())
.then(setData);
}, []);
return <div>{data}</div>;
};

const ModalPageWrapper = ({ id, ...restProps }) => {
const { activeModal } = useModalRootContext();

useEffect(function enableSomeEffect() {
if (id === activeModal) {
/* ... */
}
}, [id, activeModal];

return (
<ModalPage id={id} {...restProps}>
<SomeAsyncEffect />
</ModalPage>
);
};

const App = () => {
return (
<ModalRoot activeModal="example-1">
<ModalPageWrapper id="example-1" />
{/* или */}
<ModalPage id="example-2">
<SomeAsyncEffect />
</ModalPage>
</ModalRoot>
);
};
```

> ⚠️ У `ModalPage` и `ModalCard` есть параметр `keepMounted`, при передаче этого параметра следует учитывать, что компонент будет
> рендериться всегда, поэтому бизнес-логика будет срабатывать в любом случае.
43 changes: 43 additions & 0 deletions styleguide/pages/migration_v7.md
Original file line number Diff line number Diff line change
Expand Up @@ -1033,6 +1033,49 @@ const SomeWrapper = ({ id }) => (

</details>

<details>
<summary>Миграция (бизнес-логика в обёртках)</summary>

```diff
+ const FetchData = () => {
+ const [data, setData] = useState({});
+ useEffect(() => {
+ fetch('...').then((r) => r.json()).then(setData);
+ }, []);
+ return <div>{data}</div>;
+ };

const SomeWrapper = ({ id, ...restProps }) => {
- const [data, setData] = useState({});
- useEffect(() => {
- fetch('...').then((r) => r.json()).then(setData);
- }, []);

+ const { activeModal } = useModalRootContext();
useEffect(function enableSomeEffect() {
+ if (id === activeModal) {
/* ... */
+ }
}, [id, activeModal];

return (
<ModalPage id={id} {...restProps}>
- <div>{data}</div>
+ <FetchData>
</ModalPage>
);
};

<ModalRoot activeModal="m">
<SomeWrapper
id="m"
settlingHeight={100} // или dynamicContentHeight
/>
</ModalRoot>
```

</details>

<hr/>

### [OnboardingTooltip](https://vkcom.github.io/VKUI/7.0.0/#/OnboardingTooltip)
Expand Down
Loading