我正在开发我的第一个React应用程序。这是一种配方应用程序。它有一个成分过滤器。主要组件是Cookbook组件。它有一个Filter组件和一个Recipe组件。
Recipe组件显示加载时的所有配方。过滤器组件显示所有需要的成分或主食。这一部分都很棒。
我现在要做的是当一个人点击一个主食时,让我们说黄油,它会过滤整个食谱清单。我的假设是我需要通过Filter的状态。如何使用这些复选框执行此操作?
这就是我所拥有的:
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
var data = require('./recipes.json');
function IngredientDetailList(props){
const ingredientList = props.ingredientList;
const listItems = ingredientList.map((ingredient, index) =>
<div key={index}>
{ingredient.measurement_amount}
{ingredient.measurement_unit}
{ingredient.ingredient}
</div>
);
return (
<div>{listItems}</div>
)
}
function Recipe(props){
const recipeList = props.cookbook.recipes
const listItems = recipeList.map((recipe) =>
<div key={recipe.id}>
<h2>{recipe.name}</h2>
<IngredientDetailList ingredientList = {recipe.ingredient_list}/>
</div>
);
return(
<div>{listItems}</div>
)
}
class Filter extends React.Component {
constructor(){
super();
this.state = {
checkedStaples: {},
}
}
render(){
const stapleList = this.props.stapleList;
const checkboxItems = stapleList.map((staple, index) =>
<div key = {index}>
<label>
<input type="checkbox" value="{staple}"/>
{staple}
</label>
</div>
);
return (
<form>
{checkboxItems}
</form>
);
}
}
class Cookbook extends React.Component {
constructor(){
super();
this.state ={
cookbook: data
}
}
getStapleList(recipes){
let stapleList = [];
recipes.forEach(function(recipe){
recipe.ingredient_list.forEach(function(list){
stapleList.push(list.needed_staple);
});
});
let flattenedStapleList = stapleList.reduce(function(a,b){
return a.concat(b);
})
return flattenedStapleList
}
render(){
const cookbook = this.state.cookbook;
const stapleList = this.getStapleList(cookbook.recipes);
return(
<div className="cookbook">
<div className="filter-section">
<h1>This is the filter section</h1>
<Filter stapleList = {stapleList}/>
</div>
<div className="recipes">
<h1>This is where the recipes go</h1>
<div className="recipe">
<Recipe cookbook = {cookbook}/>
</div>
</div>
</div>
);
}
}
ReactDOM.render(
<Cookbook />,
document.getElementById('root')
);
答案 0 :(得分:1)
您可以尝试这样做:
// ....
function Recipe(props){
const selectedStaples = props.selectedStaples;
const recipeList = props.cookbook.recipes
const listItems = recipeList.map((recipe) => {
const hasStaple = ingredient_list.reduce(
(_hasStaple, staple) => _hasStaple || selectedStaples.includes(staple),
false
);
// only show recipe if it has a staple
if (selectedStaples.length === 0 || hasStaple)
return (
<div key={recipe.id}>
<h2>{recipe.name}</h2>
<IngredientDetailList ingredientList = {recipe.ingredient_list}/>
</div>
);
}
return null;
}
);
return(
<div>{listItems}</div>
)
}
class Filter extends React.Component {
constructor(){
super();
this.state = {
checkedStaples: {},
}
}
render(){
const stapleList = this.props.stapleList;
const checkboxItems = stapleList.map((staple, index) =>
<div key = {index}>
<label>
<input
type="checkbox"
value="{staple}"
onClick={e => this.props.onChange(staple, e.checked)}
/>
{staple}
</label>
</div>
);
return (
<form>
{checkboxItems}
</form>
);
}
}
class Cookbook extends React.Component {
constructor(){
super();
this.state ={
cookbook: data,
selectedStaples: []
}
}
getStapleList(recipes){
let stapleList = [];
recipes.forEach(function(recipe){
recipe.ingredient_list.forEach(function(list){
stapleList.push(list.needed_staple);
});
});
let flattenedStapleList = stapleList.reduce(function(a,b){
return a.concat(b);
})
return flattenedStapleList
}
handleOnChange(staple, isChecked) {
const selectedStaples = this.state.selectedStaples;
if (isChecked) {
this.setState({
selectedStaples: selectedStaples.push(staple);
})
} else {
this.setState({
selectedStaples: selectedStaples.filter(selectedStaple => selectedStaple !== staple);
})
}
}
render(){
const selectedStaples = this.state.selectedStaples;
const cookbook = this.state.cookbook;
const stapleList = this.getStapleList(cookbook.recipes);
return(
<div className="cookbook">
<div className="filter-section">
<h1>This is the filter section</h1>
<Filter stapleList = {stapleList} onChange={this.handleOnChange.bind(this)}/>
</div>
<div className="recipes">
<h1>This is where the recipes go</h1>
<div className="recipe">
<Recipe cookbook = {cookbook} selectedStaples={selectedStaples} />
</div>
</div>
</div>
);
}
}
ReactDOM.render(
<Cookbook />,
document.getElementById('root')
);
它跟踪cookbook组件中的选定镫骨并将其传递给配方