Lesson 3 - Create NavBar.jsx Component

Step 1. Create NavBar.jsx component inside src/components folder

/*NavBar.jsx  -- before SearchBar component */ 
/** @format **/

function NavBar() {
  return (
    <>
      <nav className="navbar bg-body-tertiary">
        <div className="container-fluid">
          <a className="navbar-brand" href="#">
            <img
              className=" col-md-3 "
              src="../src/assets/react.svg"
              alt="BookShelf Logo"
              width="30"
              height="24"
            />
            Google Book Shelf
          </a>
        </div>
      </nav>
    </>
  )
}

export default NavBar
// Layout Design of NavBar Component
NavBar Component

├── Props
│   ├── query (string) - Current search query
│   └── onSearch (function) - Callback for search submission

├── State
│   └── searchInput (useState) - Tracks input field value

├── Methods
│   └── handleSubmit() - Processes form submission

└── Render Structure
    └── <nav> (navbar)
        └── <div> (container)
            ├── <a> (navbar-brand) - "Google Bookshelf"

            └── <form> (d-flex ms-auto)
                ├── <input> (form-control) - Search text field
                │   ├── value={searchInput}
                │   └── onChange handler

                └── <button> (btn btn-outline-light) - "Search"
// After Searbar Form
// Import necessary libraries
import React, { useState } from 'react';
import PropTypes from 'prop-types';
import 'bootstrap/dist/css/bootstrap.min.css';

const NavBar = ({ query, onSearch }) => {
  const [searchInput, setSearchInput] = useState(query);

  // Handle the form submission
  const handleSubmit = (e) => {
    e.preventDefault();
    onSearch(searchInput.trim()); // Pass the input back to the parent
  };

  return (
    <nav className="navbar navbar-expand-lg navbar-dark bg-dark mb-4">
      <div className="container">
        {/* App Header Title */}
        <a className="navbar-brand" href="#">
          Google Bookshelf
        </a>

        {/* Search Form */}
        <form className="d-flex ms-auto" onSubmit={handleSubmit}>
          <input
            type="text"
            className="form-control me-2"
            placeholder="Search books..."
            value={searchInput}
            onChange={(e) => setSearchInput(e.target.value)}
          />
          <button className="btn btn-outline-light" type="submit">
            Search
          </button>
        </form>
      </div>
    </nav>
  );
};

// Define PropTypes for the component
NavBar.propTypes = {
  query: PropTypes.string.isRequired,
  onSearch: PropTypes.func.isRequired,
};

export default NavBar;

Explanation of NavBar.jsx Code Structure

The NavBar component is responsible for displaying the application header and providing a search bar to handle user queries. Here's a step-by-step breakdown of its functionality:


1. Importing Libraries

import React, { useState } from 'react';
import PropTypes from 'prop-types';
import 'bootstrap/dist/css/bootstrap.min.css';
  • React: Core library for building the component.

  • useState: Manages the state of the search input.

  • PropTypes: Validates the props passed to the component.

  • Bootstrap: Adds styling for the navbar and form elements.


2. Component Declaration

const NavBar = ({ query, onSearch }) => {
  • Props:

    • query: The current search term to initialize the input field.

    • onSearch: A function to handle the search query submission and pass it back to the parent component.


3. Local State for Search Input

const [searchInput, setSearchInput] = useState(query);
  • Purpose:

    • Tracks the user’s input in the search bar.

    • Initializes with the value of query received as a prop.


4. Handling Form Submission

const handleSubmit = (e) => {
  e.preventDefault(); // Prevents page reload
  onSearch(searchInput.trim()); // Triggers the parent function with trimmed input
};
  • Explanation:

    • Prevents the default form submission behavior (page reload).

    • Passes the sanitized input back to the parent component via the onSearch prop.


5. Rendering the Navbar

<nav className="navbar navbar-expand-lg navbar-dark bg-dark mb-4">
  <div className="container">
    {/* App Header Title */}
    <a className="navbar-brand" href="#">
      Google Bookshelf
    </a>

    {/* Search Form */}
    <form className="d-flex ms-auto" onSubmit={handleSubmit}>
      <input
        type="text"jsx
        className="form-control me-2"
        placeholder="Search books..."
        value={searchInput}
        onChange={(e) => setSearchInput(e.target.value)} // Updates local state
      />
      <button className="btn btn-outline-light" type="submit">
        Search
      </button>
    </form>
  </div>
</nav>
  • Header Title:

    • Displays the app name (Google Bookshelf) in the navbar.

    • Styled using Bootstrap's dark theme (navbar-dark bg-dark).

  • Search Form:

    • Input Field:

      • Pre-filled with the query state.

      • Updates the local searchInput state on user input.

    • Search Button:

      • Submits the form and calls the handleSubmit function.

  • Bootstrap Classes:

    • navbar: Styles the container as a navbar.

    • d-flex ms-auto: Aligns the search form to the right.

    • form-control: Styles the input field.

    • btn btn-outline-light: Creates a light-outlined button for the search.


6. Prop Validation

NavBar.propTypes = {
  query: PropTypes.string.isRequired,
  onSearch: PropTypes.func.isRequired,
};
  • Purpose:

    • Ensures query is a required string.

    • Ensures onSearch is a required function to handle search queries.


7. Exporting the Component

export default NavBar;
  • Purpose:

    • Makes the NavBar component reusable in the parent application.


Key Takeaways for Students:

  1. State Management:

    • Learn how to handle local state (searchInput) for form inputs.

    • Pass values between child and parent components using props.

  2. Form Handling:

    • Understand how to prevent the default form behavior (e.preventDefault).

    • Trigger actions using parent-defined callback functions (onSearch).

  3. Bootstrap Integration:

    • Utilize Bootstrap classes to style the navbar and search bar for a polished UI.

  4. Prop Validation:

    • Use PropTypes to validate props for better code reliability.


This component is now ready to integrate into AppBookShelf.jsx.

Last updated