如何将事件传递给作为道具传递的函数本身

时间:2020-12-28 23:59:49

标签: reactjs react-hooks react-props

我正在开发一个联系人列表应用程序。基本上使用几个个人/人的材料用户界面列表。这是一个粗略的概述:

PersonListItem --- 子组件:包含卡片上显示的所有人员详细信息 PersonList -- 父组件:基本上是通过所有的人进行映射并将所有卡片显示为列表

最近,我为每张卡片添加了一个星星组件,想法是如果我想将一个人标记为最喜欢的人,那么我会点击星星,它会变成黄色。

为了实现这一点,我学习并实现了 React 的lift-state-up with hooks 模式。所以现在的流程是这样的:

Child Component => onClick = {someMethod} => someMethod passed as props to Parent => Parent updates prop component => Child re-renders the component

但是现在当我点击任何一个联系人的星星标记收藏时,所有联系人都被标记为收藏。

我想使用 event.target 来获取单个明星的 id 但如何在道具中传递和访问 event.target.id ?

这是我当前的代码:

const PersonListItem = (props) {
    const{person, onSelectChanged, favorite, FavColorColor, markFavorite} = props;

    return(
        <ListItem button
            gender = {undefined}
            onClick = {onSelectChanged}
        <Avatar className = {classes.avatar} src={person.imageLocation === NO_USER_IMAGE : null : person.imageLocation}>
        <IconButton StarOutLinedIcon onClick = {markFavorite} style={{backgroundColor: `${FavColor}`}/>
        <ListItemText primary = 
        {
            {person.name}
            
        }
        secondary = {<div className={classes.smallText}>{person.company}{person.jobTitle}</div>/>
        
        </ListItem>
    )

}

export default PersonListItem;

const PersonList = (props) => {

    const[favorite, setFavorite] = useState(0);
    const[FavColor, setColor] = useState(' ');
    
    const markFavorite = (value) => {
        setFavorite(value = !value);
        {!favorite ? setColor("yellow") : setColor(" ")}
    }
    
    return(
            <div className={classes.root}>
                <MuiList className={props.className} isLoading={isLoading}>
                {
                    !isLoading && person
                    .map((person, index) => {
                        return <PersonListItem key={index}
                                    person = {person}
                                    onSelectChanged = () =>{
                                        HideAdd();
                                    }
                                    markFavorite = {markFavorite} FavColorColor = {FavColor}/>
                                                
                    }
                }
                
                </MuiList>
            </div>
    )

}

export default PersonList;

//Material UI ListItem
classs MuiList extends React.Component{
    
    componentDidMount() {
        i(this.props.fetch)
        {
            this.props.fetch();
        }
    }
    
    render() {
        const attributes = {...this.props};
        delete attributes.isLoading;
        delete attributes.fetch;
        delete attributes.fetchData;
        const items = this.props.isLoading;
                    ? <ListItem key={0}>
                        <CircularProgress/>
                        <ListItemText primary='Loading...'/>
                        </ListItem>
                    : this.props.children;
        return <List {...attributes>{items}</List>
    }
}

export default MuiList;

1 个答案:

答案 0 :(得分:2)

我会用个人 ID 替换一个对象的最喜欢的状态,如果它们是真或假,就会映射。还删除 favColor 状态。它是从收藏夹派生的状态,您不需要此状态。

现在,我将更改 markFavorite 函数(可能将名称更改为 toggleFavorite)。它会从那个人那里收到一个 id。它检查它是否在 favorites 中;如果未定义,则键尚不存在,因此将其标记为收藏),否则仅切换其值:

const[favorites, setFavorites] = useState({});

const markFavorite = (id) => {
  setFavorites(prevFavorites => {
    const favorites = { ...prevFavorites }
    favorites[id] = favorites[id] === undefined || !favorites[id]
    return favorites
  })
}

然后在您的个人映射中,我会将 markFavorite 作为传递 person.id 的箭头函数传递(这里我假设 person 有一个 id,这比从您的地图传递索引要好)。

还传递带有 isFavorite 布尔值的 favorites[person.id]!! 返回布尔值。实际上不需要 !!,因为 undefined 解析为 false ,更多是为了一致性类型)

markFavorite={() => markFavorite(person.id)} isFavorite={!!favorites[person.id]}/>

在您的 PersonListItem 处,您必须将 IconButton 样式定义更改为三元条件:

<IconButton StarOutLinedIcon onClick = {markFavorite} style={{backgroundColor: isFavorite ? 'yellow' : '' }}/>

这样每个人都可以独立标记,不影响其他人。