首页 > 解决方案 > Why is my state not updating after useDispatch

问题描述

Ive got a pretty straightforward set-up. That seems to be alright at least on my unexperienced first glance, however upon trying to dispatch an action to toggle the state, it does not seem to do anything and I can't figure out why.

this is how my store is configured:

import { createAction } from '@reduxjs/toolkit';
import { createReducer, configureStore } from '@reduxjs/toolkit';

// action
export const TOGGLE_QUIZ_MENU_CHOICE = 'TOGGLE_QUIZ_MENU_CHOICE';
export const actionToggleQuizChoices = createAction(TOGGLE_QUIZ_MENU_CHOICE);

// store and reducer
type StoreState = {
  isMultipleChoice: boolean;
}

const initalState = {
  isMultipleChoice: false,
}

const reducer = createReducer(initialState, {
   [actionToggleQuizChoices.type]: (state) => ({
      ...state, 
      isMultipleChoice: !state.isMultipleChoice 
   })
}

const store = configureStore({
   reducer
})

(... then it's obviously passed via <Provider> )
And later down the line in my component:

import React from 'react';
import { connect, useDispatch } from 'react-redux';
import { actionToggleQuizChoices } from '../../../store/actions';

type Props = {
   isMultipleChoice: boolean;
}

const QuizMenu: React.FC<Props> = (props: Props) => {
   const dispatch = useDispatch()

   console.log(props);

   return (
     <button type='button' onClick={() => dispatch(props.actionToggleQuizChoices)} />
   )
}

const mapStateToProps = (state: StoreState): StoreState => ({
    isMultipleChoice: state.isMultipleChoice 
})
const mapDispatchToProps = { actionToggleQuizChoices }

export default connect(
  mapStateToProps,
  mapDispatchToProps
)(QuizMenu);

Now my props seems to be mapped correctly (as do seemingly my actions (though I'm new to ), however my actions don't seem to affect my state.

enter image description here

I've simplified the example for sake of quesiton, but you can see obviously I've clicked the button and the state is not affected

enter image description here

标签: reactjstypescriptreduxreact-reduxstate

解决方案


your problem lies in what you are dispatching.

SHORT: you don't need the useDispatch just do onClick={props.actionToggleQuizChoices}

LONG: your

const mapDispatchToProps = { actionToggleQuizChoices }

will be translated to something like

const mapDispatchToProps = (dispatch) => ({ actionToggleQuizChoices: (...args) => dispatch(actionToggleQuizChoices(....args)) })

then inside of your component what you are actually doing is

dispatch(((...args) => dispatch(actionToggleQuizChoices()))(props.actionToggleQuizChoices))

as you can see you are dispatching a function. Functions are only interpreted either by a custom middleware or if you are using redux-thunk.


推荐阅读