0

I am trying to add 'active' as className to my each in sidebar component. What I want is that whichever gets activated, it should attach class 'active' to it and then set CSS accordingly. I tried using react-router location props referring to this SO answer: https://stackoverflow.com/a/42766792/11349591, but unable to follow the syntax/result properly.

Here is my code for Sidebar.js

import React, {Component} from 'react'
import { NavLink, Link } from 'react-router-dom'
import '../../css/active.css';


export default function SideBar(){
    const { location } = this.props;

    const dashboardClass = location.pathname === "/" ? "active" : "";
    const userClass = location.pathname.match(/^\/user/) ? "active" : "";
    const listClass = location.pathname.match(/^\/list/) ? "active" : "";
        return (
            <div style={{flexBasis: '200px', backgroundColor: 'gray'}}>
                <nav style={{textAlign:'left'}}>
                    <ul className="side-bar">
                        <li className={dashboardClass}>
                            <i class="fa fa-pie-chart fa-2x" aria-hidden="true" style={{color:'#ccc'}}></i>
                            <Link to="/dashboard">
                                Dashboard
                            </Link>
                        </li>
                        <li className={userClass}>
                            <i class="fa fa-user-circle fa-2x" aria-hidden="true" style={{color:'#ccc'}}></i>
                            <Link to="/user" >User</Link>
                        </li>
                        <li className={listClass}>
                            <i class="fa fa-list-alt fa-2x" aria-hidden="true" style={{color:'#ccc'}}></i>
                            <Link to="/list">Table List</Link>
                        </li>
                    </ul>
                </nav>
            </div>
        )
}

App.js (Home component render Sidebar and Dashboard component)

function App() {
  return (
    <div className="App">
      <Switch>
          <Route exact path="/" component={Home} />

          <Route path="/register" component={Register} />

          <Route path="/login" component={Login} />
      </Switch>
    </div>
  );
}

Home.js

export default class Home extends Component {
    render() {
        return (
            <div style={{display: 'flex', flexDirection: 'row'}}>
                <SideBar/>
                <Dashboard/>
            </div>
        )
    }
}

My console report this problem: TypeError: Cannot read property 'props' of undefined

program_bumble_bee
  • 439
  • 2
  • 25
  • 57

2 Answers2

0

You are trying to access this.props from a functional component and that's only possible in class based components. Change your code to this:

export default function SideBar({ location }){
   // Rest of the code

You also need to pass the router props down from Home to Sidebar component:

export default class Home extends Component {
    render() {
        return (
            <div style={{display: 'flex', flexDirection: 'row'}}>
                <SideBar {...this.props}/> // Pass the props down
                <Dashboard/>
            </div>
        )
    }
}
Clarity
  • 10,730
  • 2
  • 25
  • 35
  • That's because another component is rendered then, which doesn't have your sidebar. If you want Sidebar to be visible everywhere, you need to add it outside of Home component. – Clarity Oct 05 '19 at 11:19
  • But I want the sidebar to remain on left every time. Can you suggest a fix for this? – program_bumble_bee Oct 05 '19 at 11:22
  • Just lift it up from the Home to App component and style accordingly. – Clarity Oct 05 '19 at 11:23
  • Same problem still persists. If I provide like this: ` ....`. And if I provide like this: `
    ....`, then it give same props related error.
    – program_bumble_bee Oct 05 '19 at 11:31