Когда я должен использовать React.cloneElement против this.props.children?

Я все еще новичок в React, и во многих примерах в Интернете я вижу эту вариацию в рендеринге дочерних элементов, которая мне кажется запутанной. Обычно я вижу это:

class Users extends React.Component {
  render() {
    return (
      <div>
        <h2>Users</h2>
        {this.props.children}
      </div>
    )
  }
}

Но тогда я вижу такой пример:

<ReactCSSTransitionGroup
     component="div"
     transitionName="example"
     transitionEnterTimeout={500}
     transitionLeaveTimeout={500}
     >
     {React.cloneElement(this.props.children, {
       key: this.props.location.pathname
      })}
</ReactCSSTransitionGroup>

Теперь я понимаю API, нодокументы не совсем ясно, когда я должен его использовать.

Так что же делать одному, а другому нет? Может ли кто-нибудь объяснить мне лучшие примеры?

 iurii29 июн. 2017 г., 13:21
youtube.com/watch?v=hEGg-3pIHlE этот парень показывает, как он использует cloneElement. Проверьте это для некоторых примеров

Ответы на вопрос(3)

props.children не настоящие дети; Этоdescriptor из детей. Так что на самом деле вам нечего менять; вы не можете менять реквизиты или редактировать какие-либо функции; ты можешь толькоread from it, Если вам нужно внести какие-либо изменения, вы должны создатьnew elements с помощьюReact.CloneElement.

https://egghead.io/lessons/react-use-react-cloneelement-to-extend-functionality-of-children-components

Пример:

Основная функция рендеринга компонента, такого какApp.js:

render() {   
    return(
            <Paragraph>
              <Sentence>First</Sentence>
              <Sentence>Second</Sentence>
              <Sentence>Third</Sentence>
            </Paragraph>   
    ) 
}

Теперь скажем, вам нужно добавитьonClick каждому ребенкуParagraph; так в вашемParagraph.js ты можешь сделать:

render() {
        return (
          <div>
          {React.Children.map(this.props.children, child => {
            return React.cloneElement(child, {
              onClick: this.props.onClick })   
         })}
         </div>
       ) 
}

тогда просто вы можете сделать это:

render() {   
  return(
        <Paragraph onClick={this.onClick}>
          <Sentence>First</Sentence>
          <Sentence>Second</Sentence>
          <Sentence>Third</Sentence>
        </Paragraph>   
   ) 
}

Замечания: React.Children.map Функция будет видеть толькоtop level элементы, он не видит ничего из того, что эти элементы отображают; Это означает, что вы предоставляете прямой реквизит для детей (здесь<Sentence /> элементы). Если вам нужно, чтобы реквизит был передан дальше, скажем, у вас будет<div></div> внутри одного из<Sentence /> элементы, которые хотят использоватьonClick опора тогда в этом случае вы можете использоватьContext API сделать это. СделатьParagraph поставщик иSentence элементы как потребитель.

 SeaWarrior40417 авг. 2018 г., 03:11
Это четкий ответ на примере реального мира. Нужно больше голосов.
 jakeforaker09 сент. 2018 г., 19:07
Согласитесь с @ SeaWarrior404 - я полагаю, что OP ищет итерацию по коллекции, а не по одному дочернему элементу, потому что его пользовательский интерфейс имеет заголовок «Users» / множественное число. С помощьюReact.Children.map в сочетании сReact.cloneElement как указывает @vennesa, очень мощный
Решение Вопроса

React.cloneElement Пример работает только в том случае, если ваш ребенок является единственным элементом React.

Почти для всего{this.props.children} это тот, который вы хотите. Клонирование полезно в некоторых более сложных сценариях, когда родительский элемент отправляет элемент, а дочерний компонент должен изменить некоторые реквизиты для этого элемента или добавить такие элементы, как ref для доступа к реальному элементу DOM.

В приведенном выше примере родительский элемент, который дает дочерний элемент, не знает о ключевом требовании для компонента, поэтому он создает копию предоставленного ему элемента и добавляет ключ на основе некоторого уникального идентификатора в объекте. Для получения дополнительной информации о том, что делает ключ:https://facebook.github.io/react/docs/multiple-components.html

React.cloneElement не строго связан сthis.props.children.

Это полезно, когда вам нужно клонировать реагирующие элементы (PropTypes.element) добавлять / переопределять реквизиты, не желая, чтобы родитель знал об этих внутренних компонентах (например, присоединяя обработчики событий или назначаяkey/ref атрибуты).

Также реагируют элементынеизменный.

React.cloneElement (element, [props], [... children]) почти эквивалентен:<element.type {...element.props} {...props}>{children}</element.type>

Тем не менееchildren prop in React особенно используется для локализациисостав), в паре сReact.Children API иReact.cloneElement, компонент, который использует props.children, может обрабатывать больше логики (например, переходы состояний, события, измерения DOM и т. д.) внутренне, уступая часть рендеринга тому, где он используется, React Router<switch/> или составной компонент<select/> Вот несколько замечательных примеров.

И последнее, что стоит упомянуть, это то, что реагирующие элементы не ограничиваются props.children.

function SplitPane(props) {
  return (
    <div className="SplitPane">
      <div className="SplitPane-left">
        {props.left}
      </div>
      <div className="SplitPane-right">
        {props.right}
      </div>
    </div>
  );
}

function App() {
  return (
    <SplitPane
      left={
        <Contacts />
      }
      right={
        <Chat />
      } />
  );
}

Это могут быть любые реквизиты, которые имеют смысл, ключ был в том, чтобы определить хороший контракт для компонента, чтобы его потребители могли быть отделены от базовых деталей реализации, независимо от того, использует ли онReact.Children, React.cloneElement, или дажеReact.createContext.

 Adeel Imran25 сент. 2018 г., 17:54
Это отлично.

Ваш ответ на вопрос