redux 如何在输入字段中分派更改操作

sh7euo9m  于 2022-12-19  发布在  其他
关注(0)|答案(1)|浏览(124)

我目前正在为一个需要redux的重要任务制作一个小表单。我想创建一个在onChange之后动态更新自己的全局对象。我如何在更改输入时更新全局对象中的更改,以便我可以在任何地方使用它?
这是我的文件Details.js

import React, {useState} from "react";
import { makeStyles } from "@material-ui/core/styles";
import Card from "@material-ui/core/Card";
import CardActions from "@material-ui/core/CardActions";
import CardContent from "@material-ui/core/CardContent";
import Button from "@material-ui/core/Button";
import Typography from "@material-ui/core/Typography";
import TextField from "@material-ui/core/TextField";
import {useSelector , useDispatch} from 'react-redux';
import {setUser} from './Redux/actions';

const useStyles = makeStyles({
  root: {
    minWidth: 400,
    margin: "20px",
  },
  bullet: {
    display: "inline-block",
    margin: "0 2px",
    transform: "scale(0.8)",
  },
  title: {
    fontSize: 14,
  },
  pos: {
    marginBottom: 12,
  },
  text: {
    width: 300,
    margin: "10px",
  },
});

export default function Details() {
  const classes = useStyles();
  const bull = <span className={classes.bullet}>•</span>;
  const [user , setUsers] = useState({
    username:"",
    email:"",
    phone:0,
    age:0,
    month:"",
    batch:"",
    isPaid:0
  })

  const dispatch = useDispatch();
  const handleChange = (e) => {
    setUsers({ ...user, [e.target.name]: e.target.value });
  }
  
  return (
    <Card className={classes.root}>
      <CardContent>
        <Typography
          className={classes.title}
          color="textSecondary"
          variant="h5"
          gutterBottom
        >
          Enter Your Details
        </Typography>
        <TextField
          id="filled-basic"
          label="Full Name"
          variant="filled"
          name = "name"
          className={classes.text}
          onChange = {handleChange}
        />
        <TextField
          id="filled-basic"
          label="Phone number"
          variant="filled"
          name = "phone"
          className={classes.text}
          onChange = {handleChange}
        />
        <TextField
          id="filled-basic"
          label="Email"
          variant="filled"
          name = "email"
          className={classes.text}
          onChange = {handleChange}
        />
        <TextField
          id="filled-basic"
          label="Age"
          variant="filled"
          name = "age"
          className={classes.text}
          onChange = {handleChange}
        />
      </CardContent>
    </Card>
  );
}

actions.js

export  const SET_USER_PROFILE = 'SET_USER_PROFILE';

export const setUser = name => dispatch => {
    dispatch({
        type:SET_USER_PROFILE,
        payload:name
    })
}

reducers.js

import { SET_USER_PROFILE } from "./actions";

const initialState = {
    
}

function userReducer(state = initialState , action){
    switch(action.type){
        case SET_USER_PROFILE:
            return {...state , name:action.payload};
        
        default:
            return state;
    }

}

export default userReducer;

store.js

import {legacy_createStore as createStore , combineReducers , applyMiddleware} from 'redux'
import thunk from "redux-thunk"

import userReducer from './reducers'

const rootReducer = combineReducers({userReducer});

export const Store = createStore(rootReducer , applyMiddleware(thunk))
7gs2gvoe

7gs2gvoe1#

您似乎在询问如何从使用本地组件状态转换为redux状态。
1.将usernameemailphoneage状态移动到userReducer函数的initialState中。

const initialState = {
  username: "",
  email: "",
  phone: "",
  age: ""
};

1.更新userReducer以使用包含要更新的嵌套状态的键和值的操作负载。

const userReducer = (state = initialState, action) => {
  switch (action.type) {
    case SET_USER_PROFILE:
      const { key, value } = action.payload;
      return { ...state, [key]: value };

    default:
      return state;
  }
};

1.更新setUser action creator函数以获取要更新的keyvalue并返回action有效负载。这里没有异步逻辑,因此不需要编写一个Thunk函数,该函数也传递了dispatch函数。

const setUser = (key, value) => ({
  type: SET_USER_PROFILE,
  payload: { key, value }
});

1.更新Details组件以从Redux中选择user状态,并更新handleChange回调以使用适当的有效负载值分派setUser操作。由于这些可能是 * 受控 * 输入,因此您需要在字段上指定value属性并传递适当的状态。

const dispatch = useDispatch();
const { username, email, phone, age } = useSelector((state) => state.user);

const handleChange = (e) => {
  const { name, value } = e.target;
  dispatch(setUser(name, value));
};

return (
  <Card className={classes.root}>
    <CardContent>
      <Typography
        className={classes.title}
        color="textSecondary"
        variant="h5"
        gutterBottom
      >
        Enter Your Details
      </Typography>
      <TextField
        id="filled-basic"
        label="Full Name"
        variant="filled"
        name="username"
        value={username}
        className={classes.text}
        onChange={handleChange}
      />
      <TextField
        id="filled-basic"
        label="Phone number"
        variant="filled"
        name="phone"
        value={phone}
        className={classes.text}
        onChange={handleChange}
      />
      <TextField
        id="filled-basic"
        label="Email"
        variant="filled"
        name="email"
        value={email}
        className={classes.text}
        onChange={handleChange}
      />
      <TextField
        id="filled-basic"
        label="Age"
        variant="filled"
        name="age"
        value={age}
        className={classes.text}
        onChange={handleChange}
      />
    </CardContent>
  </Card>
);

相关问题