Skip to content

feat: Reusable and Single Navbar Component for Everyone. #51

@kurawlefaraaz

Description

@kurawlefaraaz

I modified Moderator Navbar on my local system to use .map to add <Link> along with condition. I think this can be appied in other Navbars too so we can merge all navbar into one navbar and render the links based on the conditions like isHod, isClassTeacher, isAdmin etc.

import { useState } from "react";
import { FaCircleUser } from "react-icons/fa6";
import { Link } from "react-router-dom";
import { HiOutlineMenu, HiX } from "react-icons/hi";
import { useUser } from "../../Context/UserContext";

function Navbar() {
  const [menuOpen, setMenuOpen] = useState(false);
  const { user } = useUser();
  const isHod = user?.roles?.some((role) => role.role === "hod");
  const isAdmin = user?.roles?.some((role) => role.role === "admin");

  const navbarItems = [    // FOCUS HERE
    { to: "/", text: "Dashboard", condition: null },
    { to: "/attendance", text: "Attendance", condition: isHod },
    { to: "/faculty", text: "Faculty", condition: null },
    { to: "/report", text: "Reports", condition: isHod },
    { to: "/add-user", text: "User", condition: isAdmin },
  ]
  const visibleItems = navbarItems.filter(item => item.condition === null || item.condition);
  console.log(visibleItems)

  return (
    <>
      <div className="flex justify-between items-center px-6 py-4 border-b border-lightgrey bg-white shadow-sm relative">
        <div className="text-2xl font-bold text-darknavy font-inter tracking-wide">
          Trackademy
        </div>

        {/* pc navbar */}
        <nav className="hidden md:flex items-center gap-8 ">
          {/* // FOCUS HERE */}
          {visibleItems.map((item, index) => 
            <Link key={index} to={item.to} className="hover:text-primary transition-all duration-200 transform hover:-translate-y-0.5 hover:scale-105 text-sm font-medium font-inter text-darknavy">
              {item.text}
            </Link>
          )}

          <Link
            to="/profile"
            className="flex items-center gap-2 text-darknavy hover:text-primary transition-all duration-200 transform hover:-translate-y-0.5 hover:scale-105"
          >
            <FaCircleUser className="text-darknavy size-6 hover:text-primary cursor-pointer transition-all duration-200 transform hover:-translate-y-0.5 hover:scale-105" />
          </Link>
        </nav>

        {/* hamburger Icon */}
        <button
          className="md:hidden text-darknavy text-2xl"
          onClick={() => setMenuOpen(!menuOpen)}
        >
          {menuOpen ? <HiX /> : <HiOutlineMenu />}
        </button>

        {/* mobile dropdown */}
        {menuOpen && (
          <div className="absolute top-full right-0 mt-2 w-48 bg-white border border-gray-200 rounded-lg shadow-md md:hidden z-50">
            {/* // FOCUS HERE */}
            {visibleItems.map((item, index) =>
              <Link key={index} to={item.to} className="block px-4 py-2 text-sm text-darknavy hover:bg-gray-100" onClick={() => setMenuOpen(false)}>
                {item.text}
              </Link>
            )}

            <div className="border-t my-1" />
            <div className="px-4 py-2 flex items-center gap-2">
              <Link
                to="/profile"
                onClick={() => setMenuOpen(false)}
                className="flex items-center gap-2 text-darknavy hover:text-primary"
              >
                <FaCircleUser className="text-darknavy size-5" />
                <span className="text-sm text-darknavy">Profile</span>
              </Link>
            </div>
          </div>
        )}
      </div>
    </>
  );
}

export default Navbar;

Metadata

Metadata

Labels

No labels
No labels

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions