T. Gaud
T. Gaud

Reputation: 120

React: Add active class to selected Nav link on click

I'm trying to add an 'active' class to a nav link when it is clicked.

in JQuery I could do something like:

$('.navlink').on('click', function() {
    $("a").removeClass('active');
    $(this).toggleClass('active');
});

This is the closet I've managed to get in React:

export class NavLink extends Component {
constructor(props) {
    super(props);
    this.toggleClass=this.toggleClass.bind(this);
    this.state = {
      isActive: 1,
    }
  }

toggleClass = () => {
    this.setState({ isActive: this.props.id });
  }


render() {
    const { href, name, id } = this.props;
    const classNames = this.state.isActive === id ? "nav-link active" : "nav-link";

    return (
        <a 
        className={classNames} 
        onClick={this.toggleClass.bind(this)} href={href}>{name}</a>
      )
  }
}

The problem is React only re-renders the clicked on link. So once a link has been given a class of active it won't be removed if a different link is clicked.

Upvotes: 1

Views: 2089

Answers (2)

Gabriel
Gabriel

Reputation: 641

I've done something like this before. It is easier to do this through the parent component. I didn't have components for each of my links. I just set their classes before the return in the render. Here is a sample of the code I did that I hope can be helpful to you.

I did the same thing with the onClick and the state just held a selected which held a String representing the name of the nav item. I had a Stories, Comments, and Likes nav links. Their original class was just 'tab'.

render () {
   let storiesClass = 'tab';
   let commentsClass = 'tab';
   let likesClass = 'tab';
   if (this.state.selected === "Stories") {
     storiesClass += 'Selected';
     commentsClass = 'tab';
     likesClass = 'tab';
   } else if (this.state.selected === "Comments") {
     storiesClass = 'tab';
     commentsClass += 'Selected';
     likesClass = 'tab';
   } else {
     storiesClass = 'tab';
     commentsClass = 'tab';
     likesClass += 'Selected';
   }

   return (
       <button className={storiesClass} onClick={this.selectTab("Stories")}>...

Upvotes: 1

Akrion
Akrion

Reputation: 18515

You would need to do something like this in terms of components:

NavLinkList
|--NavLink
|--NavLink

NavLinkList would be the one holding the activeLinkId in its state.

That activeLinkId would then be passed to each Link as prop so when it is changed the Links would re-render.

Also in that NavLinkList you would have the function which would change the activeLinkId on the Links onClick handler.

Upvotes: 1

Related Questions