在单击时切换字体真棒图标

时间:2019-09-12 14:31:00

标签: javascript reactjs

我想在点击时切换超棒的字体图标。加载页面后,我会查询后端并找出用户是否已注册课程,如果他们被注册,我会显示一个勾号图标,否则会显示一个咖啡图标。

最终目的是使每个单独的图标在单击时变为相反的形状。当前,当我单击图标时,例如,如果我单击杯子图标,它不仅会变成刻度线,还将其余的杯子图标也变成刻度线。如何解决此问题,以便在单击时仅影响单击的图标?

这是我的代码

功能组件

export const CourseCard = ({
  video,
  normaluser,
  adminuser,
  userauthenticated,
  adminauthenticated,
  handleUnroll,
  handleEnroll,
  enrolled,
  unrolled
}) => (
    <Grid item xs={6} md={4} lg={3}>
            {(video.enrolled_students.includes(normaluser) &&
              userauthenticated) ||
            (video.enrolled_students.includes(adminuser) &&
              adminauthenticated) ? (
                <div className="enrol__button">
                  <div>
                    <a href="#" onClick={() => handleUnroll(video.slug)}>

                      <FontAwesomeIcon
                        icon={enrolled ? faCheckSquare : faCoffee}
                      />
                    </a>
                  </div>
                </div>
            ) : (!video.enrolled_students.includes(normaluser) &&
                userauthenticated) ||
              (!video.enrolled_students.includes(adminuser) &&
                adminauthenticated) ? (
                  <div>
                    <a href="#" onClick={() => handleEnroll(video.slug)}>

                      <FontAwesomeIcon
                        icon={unrolled ? faCoffee : faCheckSquare}
                      />
                    </a>
                  </div>
            ) : (
                   ""
            )}
    </Grid>

容器

export class AllCourses extends React.Component {
  constructor(props) {
    super(props);
    this.user = details(AUTHENTICATED);
    this.admin = AdminDetails(AUTHENTICATED);

    const token = localStorage.getItem("token");
    let normaldetail = details(token);
    this.normaluser = normaldetail.user_id;

    let admindetail = AdminDetails(token);
    this.adminuser = admindetail.user_id;

    this.state = {
      enrolled: true,
      unrolled: true
    };
  }

  handleEnroll = slug => {
    this.props.dispatch(Enroll(slug));
    this.setState({unrolled: !this.state.unrolled}); 
  }

  handleUnroll = slug => {
    this.props.dispatch(Enroll(slug));
    this.setState({enrolled: !this.state.enrolled});
  }

  render() {
    const userauthenticated = this.user;
    const adminauthenticated = this.admin;
    const adminuser = this.adminuser;
    const normaluser = this.normaluser;

    const { allCourses } = this.props;
    const {search, enrolled, unrolled} = this.state;

      return (   

                  <div className="container">
                    <Grid
                      container
                      spacing={3}
                      className="courses__row courses__row__medium"
                    >
                      {allCourses.map(video => (
                        <CourseCard
                          key={video.slug}
                          video={video}
                          enrolled={enrolled}
                          unrolled={unrolled}
                          handleEnroll={this.handleEnroll}
                          handleUnroll={this.handleUnroll}
                          normaluser={normaluser}
                          adminuser={adminuser}
                          userauthenticated={userauthenticated}
                          adminauthenticated={adminauthenticated}
                        />
                      ))}
                      ;
                    </Grid>
                  </div>             

      );
}

3 个答案:

答案 0 :(得分:0)

这是因为handleEnroll和handleUnroll设置了在所有课程中共享的状态。从您的描述看来,您似乎希望状态实际上是针对每个课程的。

因此,您应该稍微更改AllCourses

handleEnroll = slug => {
  // This should cause some change to the relevant course in allCourses
   this.props.dispatch(Enroll(slug));
}

handleUnroll = slug => {
  // This should cause some change to the relevant course in allCourses
  this.props.dispatch(Enroll(slug));
}

// Delete this
this.state = {
    enrolled: true,
    unrolled: true
};

然后将CourseCard映射更改为使用video中的属性,而不是使用现已消除的AllCourses状态。

{allCourses.map(video => (
 <CourseCard
     key={video.slug}
     video={video}

     enrolled={video.enrolled}
     unrolled={video.unrolled}

     handleEnroll={this.handleEnroll}
     handleUnroll={this.handleUnroll}
     normaluser={normaluser}
     adminuser={adminuser}
     userauthenticated={userauthenticated}
     adminauthenticated={adminauthenticated}
  />
))}

答案 1 :(得分:0)

由于您要检查Grid组件中是否注册了当前用户(通过查看video.enrolled_students数组是否包括当前用户),所以enrolled和{ {1}}标志似乎不再需要。

因此,在unrolled中,您应该可以将第一个Grid调用更改为just:

<FontAwesomeIcon />

第二个是

<FontAwesomeIcon icon='faCheckSquare' />

此外,您在AllCourses中有一个错字,您在<FontAwesomeIcon icon='faCoffee' /> this.props.dispatch(Enroll(slug));中都打电话给handleEnroll,在第二个电话中很可能是handleUnroll

答案 2 :(得分:0)

您可以将布尔值作为条件,尝试将当前卡密钥与已检查卡密钥进行比较

<FontAwesomeIcon icon={this.props.checkedCard == this.props.key ? faCoffee : faCheckSquare} />

并在您的容器中:

handleEnroll = slug => {
   this.props.dispatch(Enroll(slug));
   this.setState({checked: this.props.key}); 
}

和:

<CourseCard
  key={video.slug}
  video={video}
  checkedCard={this.state.checkedCard}