我试图通过产品列表过滤用户输入
当用户擦除他们的输入时,我试图实现一个过滤器跟踪器,看看用户是否这样做了,这样数组就会相应地更新
我不知道我的逻辑出了什么问题,但我无法得到返回的过滤值来渲染,相反,我得到了初始状态值。
https://codesandbox.io/s/redux-ing-j4igf?file=/src/Redux.js
index.js:
import ReactDOM from "react-dom";
import { Provider } from "react-redux";
import { createStore } from "redux";
import { reducer } from "./Redux";
import AppWrapper from "./AppWrapper";
const store = createStore(reducer);
const rootElement = document.getElementById("root");
ReactDOM.render(
<Provider store={store}>
<AppWrapper />
</Provider>,
rootElement
);
AppWrapper.js:
import { connect } from "react-redux";
import App from "./App";
import { getInputValue } from "./Redux";
const mapStateToProps = (state) => ({
searchString: state.searchString,
productData: state.productData,
filteredProducts: state.filteredProducts
});
const mapDispatchToProps = (dispatch) => {
return {
filterByValue: (e) => {
let input = e.target.value;
dispatch(getInputValue({ value: input }));
},
triggerUserValue: () => {
dispatch({ type: "TRIGGER_USER_VALUE" });
}
};
};
export default connect(mapStateToProps, mapDispatchToProps)(App);
App.js:
import "./styles.css";
import TemplateCard from "./TemplateCard";
import React from "react";
class App extends React.Component {
render() {
let products = this.props.productData;
return (
<div className="App">
<div className="flex">
<input
placeholder="filter items"
onChange={this.props.filterByValue}
/>
<button onClick={this.props.triggerUserValue}> click me </button>
</div>
<div className="flex">
{products.map((i) => {
return (
<TemplateCard
key={i.id}
title={i.title}
text={i.text}
price={i.price}
imageurl={i.imageurl}
/>
);
})}
</div>
</div>
);
}
}
export default App;
Redux.js:
export const initialState = {
searchString: "",
anotherthingy: "",
productData: [
{
id: 1,
name: "Roses",
title: "Roses",
text: "Beautiful hand picked roses fresh out of our gardins",
price: 9.99
},
{
id: 2,
name: "Dahlia",
title: "Dahlia",
text: "Beautiful hand picked Dahlia fresh out of our gardins",
price: 17.99
},
{
id: 3,
name: "Alstroemerias",
title: "Alstroemerias",
text: "Beautiful hand picked Alstroemerias fresh out of our gardins",
price: 12.99
},
{
id: 4,
name: "Calla lillies",
title: "Calla lillies",
text: "Beautiful hand picked Calla lillies fresh out of our gardins",
price: 16.99
}
],
appliedFilters: []
};
const FILTER_BY_VALUE = "FILTER_BY_VALUE";
export const getInputValue = (payload) => {
return {
type: FILTER_BY_VALUE,
payload
};
};
export const reducer = (state = initialState, action) => {
switch (action.type) {
case FILTER_BY_VALUE:
let newState = Object.assign({}, state);
let value = action.payload.value;
let filteredValues = state.productData.filter((product) => {
return product.name.toLowerCase().includes(value);
});
console.log(filteredValues);
let appliedFilters = state.appliedFilters;
if (value === true) {
let index = appliedFilters.indexOf(FILTER_BY_VALUE);
if (index === -1) appliedFilters.push(FILTER_BY_VALUE);
newState.productData = filteredValues;
} else {
let index = appliedFilters.indexOf(FILTER_BY_VALUE);
appliedFilters.splice(index, 1);
if (appliedFilters.length === 0) {
newState.filteredProducts = newState.productData;
}
}
console.log(newState);
return { ...newState, productData: newState.filteredProducts };
case "TRIGGER_USER_VALUE":
alert(state.searchString);
return state;
default:
return state;
}
};
在您的reducer中,更新FILTER_BY_VALUE
操作的代码,如下所示:-
case FILTER_BY_VALUE:
let newState = Object.assign({}, state);
let value = action.payload.value;
let filteredValues = state.productData.filter((product) => {
return product.name.toLowerCase().includes(value);
});
let appliedFilters = state.appliedFilters;
if (value) {
let index = appliedFilters.indexOf(FILTER_BY_VALUE);
if (index === -1) appliedFilters.push(FILTER_BY_VALUE);
newState.filteredProducts = filteredValues; // changed here to store in filteredProducts
} else {
let index = appliedFilters.indexOf(FILTER_BY_VALUE);
appliedFilters.splice(index, 1);
if (appliedFilters.length === 0) {
newState.filteredProducts = initialState.productData; // get initial productData if there are no filters
}
}
console.log(newState);
return { ...newState, productData: newState.filteredProducts }; // set productData