react-redux useSelector钩子 学习样例 + 详细解析 typeScript版本

 

(一)react-redux useSelector 学习样例 + 详细解析 

npx create-react-app my-project --template typescript
cd my-project

安装依赖

npm install redux react-redux immer antd
npm install @types/react @types/react-dom @types/react-redux --save-dev
npm install ajv@^8.0.0

 项目结构:

package.json

{
  "name": "my-project",
  "version": "0.1.0",
  "private": true,
  "dependencies": {
    "@testing-library/jest-dom": "^5.17.0",
    "@testing-library/react": "^13.4.0",
    "@testing-library/user-event": "^13.5.0",
    "@types/jest": "^27.5.2",
    "@types/node": "^16.18.19",
    "ajv": "^8.17.1",
    "antd": "^5.22.2",
    "immer": "^10.1.1",
    "react": "^18.2.0",
    "react-dom": "^18.2.0",
    "react-redux": "^8.0.5",
    "react-scripts": "5.0.1",
    "redux": "^4.2.1",
    "typescript": "^4.9.5",
    "web-vitals": "^2.1.4"
  },
  "scripts": {
    "start": "react-scripts start",
    "build": "react-scripts build",
    "test": "react-scripts test",
    "eject": "react-scripts eject"
  },
  "eslintConfig": {
    "extends": [
      "react-app",
      "react-app/jest"
    ]
  },
  "browserslist": {
    "production": [
      ">0.2%",
      "not dead",
      "not op_mini all"
    ],
    "development": [
      "last 1 chrome version",
      "last 1 firefox version",
      "last 1 safari version"
    ]
  },
  "devDependencies": {
    "@types/react": "^18.0.26",
    "@types/react-dom": "^18.0.10",
    "@types/react-redux": "^7.1.23"
  }
}
  • public/index.html
<!DOCTYPE html>
<html>
<head>
  <meta charset="UTF-8">
  <title>redux</title>
</head>
<body>
<div id="root"></div>
</body>
</html>
  • src/redux/actions/index.ts
export const SET_GIFT_ITEMS = 'SET_GIFT_ITEMS';

export const setGiftItems = (giftItems: any[]) => ({
    type: SET_GIFT_ITEMS,
    payload: giftItems,
});
  • src/redux/reducers/index.ts
import { combineReducers } from 'redux';
import { SET_GIFT_ITEMS } from '../actions';

const initialSettingInfo = {
    giftOptionIndex: 0,
    giftItems: [],
};

const settingInfo = (state = initialSettingInfo, action: { type: any; payload: any; }) => {
    switch (action.type) {
        case SET_GIFT_ITEMS:
            return {
                ...state,
                giftItems: action.payload,
            };
        default:
            return state;
    }
};

const rootReducer = combineReducers({
    settingInfo,
});

export default rootReducer;
  • src/store/index.ts
import { createStore } from 'redux';
import rootReducer from '../reducers';

const store = createStore(rootReducer);

export default store;
  • src/components
import React, { useState } from 'react';
import { useDispatch, useSelector } from 'react-redux';
import { Select, Button } from 'antd';
import { setGiftItems } from '../redux/actions';

const { Option } = Select;

const giftList = [
    { giftId: 1, giftName: '礼物1' },
    { giftId: 2, giftName: '礼物2' },
    { giftId: 3, giftName: '礼物3' },
];

const GiftSelector = () => {
    const [selectedGiftId, setSelectedGiftId] = useState(null);
    const dispatch = useDispatch();
    // @ts-ignore
    const giftItems = useSelector((state) => state.settingInfo.giftItems);

    const handleChange = (value: React.SetStateAction<null>) => {
        setSelectedGiftId(value);
    };

    const handleAddGift = () => {
        if (selectedGiftId) {
            const selectedGift = giftList.find((gift) => gift.giftId === selectedGiftId);
            const newGiftItems = [...giftItems, selectedGift];
            dispatch(setGiftItems(newGiftItems));
        }
    };

    return (
        <div>
            <Select style={{ width: 200 }} onChange={handleChange} placeholder="选择一个礼物">
                {giftList.map((gift) => (
                    <Option key={gift.giftId} value={gift.giftId}>
                        {gift.giftName}
                    </Option>
                ))}
            </Select>
            <Button type="primary" onClick={handleAddGift} style={{ marginLeft: 10 }}>
                添加
            </Button>
            <div>
                <h3>已添加的礼物:</h3>
                {giftItems.map((gift: { giftId: number; giftName: string  }) => (
                    <div key={gift.giftId}>{gift.giftName}</div>
                ))}
            </div>
        </div>
    );
};

export default GiftSelector;
  • App.tsx
import React from 'react';
import { Provider } from 'react-redux';
import store from './redux/store';
import GiftSelector from './components/GiftSelector';
// import 'antd/dist/antd.css';

const App = () => {
    return (
        <Provider store={store}>
            <GiftSelector />
        </Provider>
    );
};

export default App;
  • index.tsx
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';

ReactDOM.render(
    <React.StrictMode>
        <App />
    </React.StrictMode>,
    document.getElementById('root')
);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

呵呵哒( ̄▽ ̄)"

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值