Я читал документацию для библиотеки Redux и имел этот пример,
В дополнение к чтению состояния компоненты контейнера могут отправлять действия. Аналогичным образом вы можете определить функцию с именем
mapDispatchToProps()
, которая получает метод dispatch() и возвращает реквизиты обратного вызова, которые вы хотите ввести в презентационный компонент.
Это фактически не имеет смысла. Зачем вам mapDispatchToProps
, когда у вас уже есть mapStateToProps
?
Они также предоставляют этот удобный пример кода:
const mapDispatchToProps = (dispatch) => {
return {
onTodoClick: (id) => {
dispatch(toggleTodo(id))
}
}
}
Может кто-нибудь объяснить в простых мирянах, что это за функция и почему она полезна?
Я чувствую, что ни один из ответов не кристаллизовался, почему mapDispatchToProps
полезен.
На это можно ответить только в контексте шаблона container-component
, который я нашел лучше всего понятым в первом чтении:
https://medium.com/@learnreact/container-components-c0e67432e005#.1a9j3w1jl
затем
http://redux.js.org/docs/basics/UsageWithReact.html
Вкратце, ваш components
должен иметь дело только с отображением материала. только место, из которого они должны получить информацию, это их реквизит.
Отделяется от этого беспокойство:
Это то, что containers
для.
Следовательно, "хорошо спроектированный" component
в шаблоне выглядит следующим образом:
class FancyAlerter extends Component {
sendAlert = () => {
this.props.sendTheAlert()
}
render() {
<div>
<h1>Today Fancy Alert is {this.props.fancyInfo}</h1>
<Button onClick={sendAlert}/>
</div>
}}
Посмотрите, как этот компонент получает информацию, которую он отображает из реквизита (который поступает из магазина redux через mapStateToProps
), и он также получает свою функцию действия из своих реквизитов: sendTheAlert()
.
Что там, где mapDispatchToProps
входит: в соответствующем container
FancyButtonContainer.js
function mapDispatchToProps(dispatch) {
return({
sendTheAlert: () => {dispatch(ALERT_ACTION)}
})
}
function mapStateToProps(state} {
return({fancyInfo: "Fancy this:" + state.currentFunnyString})
}
export const FancyButtonContainer = connect(
mapStateToProps, mapDispatchToProps)(
FancyAlerter
)
Интересно, видите ли вы, теперь это container
[1], который знает о редукции и отправке и хранении, состоянии и... материалах.
component
в шаблоне FancyAlerter
, которому рендеринг не нужен никому из этого материала: он получает свой метод для вызова в onClick
кнопки через свои реквизиты.
И... mapDispatchToProps
было полезным средством, которое позволяет уменьшить контейнер, чтобы контейнер легко передавал эту функцию в обернутый компонент на своих реквизитах.
Все это очень похоже на пример todo в документах и другой ответ здесь, но я попытался отобрать его в свете шаблона, чтобы подчеркнуть почему.
(Примечание: вы не можете использовать mapStateToProps
для той же цели, что и mapDispatchToProps
по той причине, что у вас нет доступа к dispatch
внутри mapStateToProp
. Таким образом, вы не можете использовать mapStateToProps
, чтобы предоставить обернутому компоненту метод, который использует dispatch
.
Я не знаю, почему они решили разбить его на две функции отображения - возможно, было бы более уместно иметь mapToProps(state, dispatch, props)
IE одну функцию для выполнения обоих!
[1] Обратите внимание, что я намеренно явно назвал контейнер FancyButtonContainer
, чтобы подчеркнуть, что это "вещь" - идентичность (и, следовательно, существование!) контейнера как "вещи" иногда теряется в сокращении
export default connect(...)
который показан в большинстве примеров
Это в основном стенография. Поэтому вместо того, чтобы писать:
this.props.dispatch(toggleTodo(id));
Вы должны использовать mapDispatchToProps, как показано в вашем примере кода, а затем в другом месте:
this.props.onTodoClick(id);
или, более вероятно, в этом случае вы должны иметь это как обработчик события:
<MyComponent onClick={this.props.onTodoClick} />
Здесь полезное видео Дэн Абрамов: https://egghead.io/lessons/javascript-redux-generating-containers-with-connect-from-react-redux-visibletodolist
mapDispatch
, Redux будет использовать значение по умолчанию. Эта функция mapDispatch
умолчанию просто берет ссылку на функцию dispatch
и выдает ее как this.props.dispatch
.
mapStateToProps() - это утилита, которая помогает вашему компоненту получать обновленное состояние (которое обновляется некоторыми другими компонентами),
mapDispatchToProps() - это утилита, которая поможет вашему компоненту запускать событие действия (диспетчерское действие, которое может вызвать изменение состояния приложения).
mapStateToProps, mapDispatchToProps и подключение из библиотеки react-redux обеспечивает удобный способ доступа к вашему состоянию и функции отправки вашего магазина. Таким образом, в основном соединение - это компонент более высокого порядка, вы также можете использовать его как обертку, если это имеет смысл для вас. Таким образом, каждый раз, когда ваше состояние изменяется, mapStateToProps вызывается с вашим новым состоянием, а затем, когда вы создаете компонент обновления, вы запускаете функцию рендеринга для рендеринга вашего компонента в браузере. mapDispatchToProps также сохраняет ключевые значения в реквизитах вашего компонента, обычно они принимают форму функции. Таким образом вы можете вызвать изменение состояния из вашего компонента onClick, onChange events.
Из документов:
const TodoListComponent = ({ todos, onTodoClick }) => (
<ul>
{todos.map(todo =>
<Todo
key={todo.id}
{...todo}
onClick={() => onTodoClick(todo.id)}
/>
)}
</ul>
)
const mapStateToProps = (state) => {
return {
todos: getVisibleTodos(state.todos, state.visibilityFilter)
}
}
const mapDispatchToProps = (dispatch) => {
return {
onTodoClick: (id) => {
dispatch(toggleTodo(id))
}
}
}
function toggleTodo(index) {
return { type: TOGGLE_TODO, index }
}
const TodoList = connect(
mapStateToProps,
mapDispatchToProps
)(TodoList)
Также убедитесь, что вы знакомы с Реагировать функции безстоящих лиц и Высшее -Закрыть компоненты
mstp
получает state
и props
и позволяет извлекать реквизиты из состояния для перехода к компоненту.
mdtp
получает dispatch
и props
и предназначен для того, чтобы вы могли привязать создателей действий к отправке, поэтому, когда вы выполняете результирующую функцию, действие будет удалено.
Я нахожу, что это только избавляет вас от необходимости выполнять dispatch(actionCreator())
внутри вашего компонента, что делает его более легким для чтения.
https://github.com/reactjs/react-redux/blob/master/docs/api.md#arguments
dispatch
? Откуда это взялось?