Comments 13

в приведенных фрейворках слоты появились потому, что там для рендера везде используются шаблоны со своим неповторимым синтаксисом, а в реакте всё является функциями и render props — самый естественный подход

Согласен, но в renderProps мне не хватает семантики, чтобы вёрстка говорила сама за себя. И тут, возможно, дело вкуса. Мне, чем сложнее компоненты отрисовываются в renderProps, тем сложнее читать:


<Dialog>
  <CloseSlot>
    <button>close me</button>
  </CloseSlot>
  ...
</Dialog>

И


<Dialog
  renderCloseButton={() => <button>close me</button>}
>
  ...
</Dialog>

1) Так зачем передавать функцию?


<Dialog close={<button>close</button>} />

2) Как обеспечить обязательность слотов на уровне typescript?

1) Согласен
2) Под обязательностью вы имеете в виду как сделать использование слота обязательным? Чтобы пользователь компонента не мог игнорировать слот и был обязан что-то в него положить? К сожалению, насколько я знаю TypeScript и типизацию JSX, это нельзя выразить типами.


Справедливые замечания, спасибо!

Я не часто пишу на react, но вроде же можно было описать props компонента при помощи интерфейса и ts даже проверял такие места. Почему бы и не указать в этом же интерфейсе функцию как prop?


UPD. Действительно, можно.
https://codesandbox.io/s/focused-field-3oq5w?file=/src/App.tsx

с поддержкой параметризации слотов.

Получить доступ к дефолтному содержимому слота тоже можно? Что-то типа:


<MySlot>
  {params => (<div>Param is {params.myParam} and {params.defaultSlotContent}</div>)}
</MySlot>

P.S.: о том, какими должны быть слоты, неплохо рассказал Константин Лебедев в этой статье.

defaultSlotContent нету, но можно легко добавить. Пожалуй, так и сделаю!


За ссылку на статью спасибо! Идеи похожи, и там есть преимущества (не надо руками передавать children) и недостатки (привязка по строковому имени ломает навигацию в IDE).


Но представленный там способ требует намного большей интеграции в проект – компоненты должны создаваться через фабрику. Не хотелось бы настолько завязываться на утилитарную библиотеку.

Да писали уже про это тут https://habr.com/ru/post/475170/


Всякий раз когда у меня появляется желание написать свою версию слотов для React я говорю себе — не делай этого!


А если заменить "фатальный недостаток" на "фича" то и проблемы решатся сами собой.

Я пишу что-то вроде такого:

<Select items={[]} />

<Select items={[]} slotItem={<CustomItem />} />

Компонент реализует нужную вёрстку и логику по умолчанию, а если нужно заменить какую-то часть, то создаём для этого слот и передаём в него произвольный компонент. Все слоты считаются необязательными параметрами и без них компонент должен правильно работать.
Only those users with full accounts are able to leave comments. Log in, please.