gpt4 book ai didi

reactjs - 如何使用 redux、immer、react 从数组中删除元素

转载 作者:行者123 更新时间:2023-12-05 01:07:24 26 4
gpt4 key购买 nike

import produce from "immer";

const initialState = {
isLoading: true,
error: "",
burgers: [],
};

export default function (state = initialState, action) {
switch (action.type) {
case "ADD_BURGER_BUCKET": {
return produce(state, (draftState) => {
if (Array.isArray(action.payload)) {
draftState.burgers.push(...action.payload);
} else {
draftState.burgers.push(action.payload);
}
});
}
case "REMOVE_BURGERS_BUCKET": {
return produce(state, (draftState) => {
draftState.burgers = []
});
}
**case "REMOVE_ONE_BURGER_BUCKET": {
return produce(state, (draftState) => {
console.log(action.payload, draftState.burgers) console.log => 3 Proxy {0: {…}}
draftState.burgers.filter(el => el.id !== action.payload)
})
}** HERE THIS ONE DOES NOT WORK!!!
default:
return state;
}
}


return ( <===== BURGER BUTTON
<Burger
key={burger.id}
text={burger.name}
cost={burger.cost}
onClick={() => {
dispatch({
type: "REMOVE_ONE_BURGER_BUCKET",
payload: burger.id, <=== PASS ID TO REDUCER
}); <==== THIS ONE DOESN'T REMOVE THE ELEMENT FROM AN ARRAY
localStorage.setItem("burger", JSON.stringify(burger));
localStorage.setItem(
"burgersBucket",
JSON.stringify(
list.burgers.filter((el) => el.id !== burger.id)
)
);
history.push("/redo");
}}
/>
);
}

我想通过它的 id 从数组中删除元素,但我做不到,这就是我在控制台中得到的

3 代理{0:{…}}

我已经导入了 useselector 和 useDispatch 钩子(Hook)。

完整代码

    import React from "react";

import { Wrapper } from "../../styled/general";
import { Menu, MenuTitle, Burgers } from "../home/homestyled";
import Burger from "../../component/burger";
import { useDispatch, useSelector } from "react-redux";
import { useEffect } from "react";
import { useHistory } from "react-router-dom";

export default function Index() {
const list = useSelector((state) => state.burgerBucket);
const dispatch = useDispatch();
const history = useHistory();

useEffect(() => {
console.log(list.burgers);
if (list.burgers.length > 0) {
localStorage.setItem("burgersBucket", JSON.stringify(list.burgers));
} else {
let burgersBucket = JSON.parse(localStorage.getItem("burgersBucket"));
dispatch({ type: "ADD_BURGER_BUCKET", payload: burgersBucket });
}
}, []);

return (
<Wrapper>
<Menu>
<MenuTitle>My Bucket</MenuTitle>
<Burgers>
{[...list.burgers, { finish: true }, { addMore: true }].map(
(burger) => {
if (burger.addMore) {
return (
<Burger
key={-2}
bg={"lightgreen"}
text={"Додати ще"}
onClick={() => {
history.push("/");
}}
/>
);
}
if (burger.finish) {
return (
<Burger
key={-1}
bg={"#ff5050"}
text={"Завершити"}
onClick={() => {
dispatch({ type: "REMOVE_BURGERS_BUCKET" });
history.push("/");
}}
/>
);
}
return (
<Burger
key={burger.id}
text={burger.name}
cost={burger.cost}
onClick={() => {
dispatch({
type: "REMOVE_ONE_BURGER_BUCKET",
payload: burger.id,
});
localStorage.setItem("burger", JSON.stringify(burger));
localStorage.setItem(
"burgersBucket",
JSON.stringify(
list.burgers.filter((el) => el.id !== burger.id)
)
);
history.push("/redo");
}}
/>
);
}
)}
</Burgers>
</Menu>
</Wrapper>
);
}
enter code here

完整的代码缩减器

import produce from "immer";

const initialState = {
isLoading: true,
error: "",
burgers: [],
};

export default function (state = initialState, action) {
switch (action.type) {
case "ADD_BURGER_BUCKET": {
return produce(state, (draftState) => {
if (Array.isArray(action.payload)) {
draftState.burgers.push(...action.payload);
} else {
draftState.burgers.push(action.payload);
}
});
}
case "REMOVE_BURGERS_BUCKET": {
return produce(state, (draftState) => {
draftState.burgers = []
});
}
case "REMOVE_ONE_BURGER_BUCKET": {
return produce(state, (draftState) => {
console.log(action.payload, draftState.burgers)
draftState.burgers.filter(el => el.id !== action.payload)
})
}
default:
return state;
}
}

也许这个也很重要,这是用户点击汉堡按钮后我被重定向的代码(页面)

完整代码

import React, { useEffect, useState, useContext } from "react";

import { Wrapper } from "../../styled/general";
import { Menu, MenuTitle } from "../home/homestyled";
import {
BurgerIngridients,
IngridientWrapper,
BurgerDetails,
DetailsTitle,
IngridientsDetails,
Total,
DetailsButtonContinue,
} from "./burgerredostyled";
import Ingridient from "../../component/Ingridient";
import IngridientdetailBlock from "../../component/IngridientsDetailBlock";

import { useHistory } from "react-router-dom";
import { useDispatch, useSelector } from "react-redux";
import { useBurger } from "../../hooks/useBurger";

import { sumOfToppings } from "../../helpers/sum";

export default function Index() {
const burger = useSelector((state) => state.burger);
const [toppings, error, isLoading] = useBurger(
"http://localhost:3000/toppings"
);
const dispatch = useDispatch();
const history = useHistory();

useEffect(() => {
if (burger.id) {
localStorage.setItem("burger", JSON.stringify(burger));
} else {
let localStorageBurger = JSON.parse(localStorage.getItem("burger"));
dispatch({ type: "ADD_BURGER", payload: localStorageBurger });
}

for (let i = 0; i < toppings.length; i++) {
for (let j = 0; j < burger.consists_of.length; j++) {
if (burger.consists_of[j].name === toppings[i].name) {
toppings[i].quantity = burger.consists_of[j].quantity;
}
}
}

if (toppings.length > 0) {
dispatch({
type: "ADD_BURGER",
payload: { ...burger, consists_of: toppings },
});
}
}, [isLoading]);

const add = (text, num) => {
for (let i = 0; i < toppings.length; i++) {
if (toppings[i].name === text) {
toppings[i].quantity = num;
}
}
dispatch({
type: "ADD_BURGER",
payload: { ...burger, consists_of: toppings },
});
localStorage.setItem(
"burger",
JSON.stringify({ ...burger, consists_of: toppings })
);
};

if (!isLoading)
return (
<Wrapper>
<Menu>
<MenuTitle>{burger && burger.name}</MenuTitle>
<IngridientWrapper>
<BurgerIngridients>
{burger.consists_of.map(({ name, quantity, id }) => {
return (
<Ingridient
key={id}
text={name}
add={add}
initValue={quantity}
/>
);
})}
</BurgerIngridients>
<BurgerDetails>
<DetailsTitle>
<span>{burger && burger.name} | інформація</span>{" "}
<DetailsButtonContinue
onClick={() => {
dispatch({
type: "ADD_BURGER_BUCKET",
payload: { ...burger, cost: sumOfToppings(burger) },
});
history.push("/bucket");
}}
>
продовжити
</DetailsButtonContinue>
</DetailsTitle>
<IngridientsDetails>
{burger.consists_of
.filter((el) => el.quantity > 0)
.map((el) => {
return (
<IngridientdetailBlock
key={el.id}
text={el.name}
price={el.quantity * el.cost}
qty={el.quantity}
></IngridientdetailBlock>
);
})}
</IngridientsDetails>
<Total>Загалом {sumOfToppings(burger)}(грн.)</Total>
</BurgerDetails>
</IngridientWrapper>
</Menu>
</Wrapper>
);

if (isLoading) {
return <span>loading</span>;
}
}

最佳答案

Array.prototype.filter 不会改变数组,它会创建一个新数组。

所以这个:

draftState.burgers.filter(el => el.id !== action.payload)

实际上并没有改变 draftState.burgers。但这会:

produce(state, (draftState) => {
draftState.burgers = draftState.burgers.filter(el => el.id !== action.payload)
})

关于reactjs - 如何使用 redux、immer、react 从数组中删除元素,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67607377/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com