# Hands-on Practice II

## Step-by-step Walkthrough to Build the `AppTravel.jsx` React Application

<figure><img src="/files/bBig85U6LxGBE13qtiRM" alt="" width="563"><figcaption></figcaption></figure>

### **Step 1. Create the React App Structure**

1. Open your terminal and run the following commands to create and navigate to the project directory:

   ```bash
   npm create vite@latest
   >react-scrimba-travel-app
   >React
   >JavaScript
   cd react-scrimba-travel-app
   ```
2. Open visual studio code and open terminal

```bash
npm install
```

3. Install Bootstrap for styling:

```bash

npm install bootstrap
```

4. Import Bootstrap in the App.jsx file:

```jsx
import 'bootstrap/dist/css/bootstrap.min.css';
```

***

### **Step 2. Set Up the Components Folder**

1. Inside the <mark style="color:orange;">`src`</mark> folder, create a new folder named <mark style="color:orange;">`components`</mark>.
2. Add the following files inside the `components` folder:
   * `Header.jsx`
   * `TravelEntry.jsx`
   * `travelData.js`

***

### **Step 3. Add the `travelData.js` File**

1. Add the provided travel data as an array of objects. Example:

   ```javascript
   export default [
     {
       id: 1,
       img: {
         src: "https://scrimba.com/links/travel-journal-japan-image-url",
         alt: "Mount Fuji",
       },
       title: "Mount Fuji",
       country: "Japan",
       googleMapsLink: "https://maps.app.goo.gl/6RLYZDuuuqJ7kNGZ9",
       dates: "12 Jan, 2021 - 24 Jan, 2021",
       text: "Mount Fuji is the tallest mountain in Japan...",
     },
     // Additional travel entries...
     {
       id: 2,
       img: {
         src: "https://scrimba.com/links/travel-journal-australia-image-url",
         alt: "Sydney Opera House",
       },
       title: "Sydney Opera House",
       country: "Australia",
       googleMapsLink: "https://maps.app.goo.gl/Zr17SCrsJeCEKMd36",
       dates: "27 May, 2021 - 8 Jun, 2021",
       text: "The Sydney Opera House is a multi-venue performing arts centre in Sydney. Located on the banks of the Sydney Harbour, it is often regarded as one of the 20th century's most famous and distinctive buildings.",
     },
     {
       id: 3,
       img: {
         src: "https://scrimba.com/links/travel-journal-norway-image-url",
         alt: "Geirangerfjord",
       },
       title: "Geirangerfjord",
       country: "Norway",
       googleMapsLink: "https://maps.app.goo.gl/fhkJuBhmFDv47tiB7",
       dates: "01 Oct, 2021 - 18 Nov, 2021",
       text: "The Geiranger Fjord is a fjord in the Sunnmøre region of Møre og Romsdal county, Norway. It is located entirely in the Stranda Municipality.",
     },
     {
       id: 4,
       img: {
         src: "https://tinyurl.com/2arv9gc3",
         alt: "Jumgal",
       },
       title: "Jumgal Horse Milk",
       country: "Kyrgyzstan",
       googleMapsLink: "https://maps.app.goo.gl/aivBXpgxMDiaTsb88",
       dates: '01 Oct, 2021 - 18 Nov, 2021',
       text: 'It is a mountainous district. Its main rivers are the Kökömeren and its tributaries Jumgal, Suusamyr and Batysh Karakol.',
     },
     {
       id: 5,
       img: {
         src: "https://tinyurl.com/23spwexp",
         alt: "Kel-Suu",
       },
       title: "Kol-Suu , Naryn",
       country: "Kyrgyzstan",
       googleMapsLink: "https://maps.app.goo.gl/3RzgCZA2yg7VrA53A",
       dates: '01 July, 2024 - 04 July, 2024',
       text: 'a spectacular glacial lake set in a rocky canyon whose shear sides drop almost straight down into the lake.',
     },
   ];
   // Additional travel entries...

   ```

***

### Layout Design

1. APP.jsx Layout

```dot
// App.jsx Layout
----------------------------------------------------
|                    [ Header ]                    |<---- Header Component
|--------------------------------------------------|
|                                                  |
|   [ Travel Entry 1 ]                             |<--- TravelEntry component
|   --------------------------------------------   |
|                                                  |
|   [ Travel Entry 2 ]                             |
|   --------------------------------------------   |
|                                                  |
|   [ Travel Entry 3 ]                             |
|   --------------------------------------------   |
|                                                  |
|   ...                                            |
|                                                  |
----------------------------------------------------

```

2. TravelEntry.jsx Layout

```dot
// Some code
------------------------------------------------------------
|                                                          |
|  [ Article Container ]                                   |
|  ------------------------------------------------------  |
|  |                                                    |  |
|  |  [ Image Section ]     [ Details Section ]         |  |
|  |  ------------------     -----------------------    |  |
|  |  |                  |   | [ Marker Icon ] Country  |  |
|  |  |                  |   | [ View on Google Maps ]  |  |
|  |  |   [ Image ]      |   |------------------------  |  |
|  |  |                  |   |   [ Title ]              |  |
|  |  |                  |   |   [ Dates (Italic) ]     |  |
|  |  ------------------     |   [ Description Text ]   |  |
|  ------------------------------------------------------  |
|                                                          |
------------------------------------------------------------

```

{% tabs %}
{% tab title="Header.jsx" %}

```jsx
// Header.jsx component
// 4. Create Header.jsx component

function Header() {
  return (
    <header className="d-flex align-items-center bg-warning p-3 ">
      <img
        src="/src/images/globe.png"
        alt="globe icon"
        style={{ width: '30px', marginRight: '10px' }}
      />
      <h1>My Favorite Travel Places in Kyrgyz</h1>
    </header>
  )
}

export default Header;
```

{% endtab %}

{% tab title="TravelEntry.jsx" %}

```jsx
// TravelEntry.jsx component

// 5. Create TravelEntry.jsx component
import React from 'react'

function TravelEntry({ img, title, country, googleMapsLink, dates, text }) {
  return (
    <article className="container mt-4 p-3 border rounded">
      <div className="row">
        <div className="col-md-4">
          <img src={img.src} alt={img.alt} className="img-fluid rounded" />
        </div>
        <div className="col-md-8">
          <div className="d-flex align-items-center mb-2">
            <img
              src="/src/images/marker.png"
              alt="marker"
              style={{ width: '16px', marginRight: '5px' }}
            />
            <span>{country}</span>
            <a 
              href={googleMapsLink}
              target="_blank"
              rel="noreferrer"
              className="ms-2 text-primary text-decoration-none ">
              View on Google Maps
            </a>
          </div>
          <h2>{title}</h2>
          <p className="text-muted fst-italic">{dates}</p>
          <p className="fs-5">{text}</p>
        </div>
      </div>
    </article>
  )
}

export default TravelEntry

```

{% endtab %}

{% tab title="App.jsx" %}

```jsx
// App.jsx  parent component
import Header from './components/Header'
import TravelEntry from './components/TravelEntry'
import travelData from './components/travelData'
import './App.css'
import 'bootstrap/dist/css/bootstrap.min.css'

function App() {

  return (
    <>
      <div>
        <Header />
        <div className="container">
          {travelData.map((entry) => (
            <TravelEntry key={entry.id} {...entry} />
          ))}
        </div>
      </div>
    </>
  )
}

export default App

```

{% endtab %}

{% tab title="travelData.js" %}

```javascript
// travelData.js 
export default [
  {
    id: 1,
    img: {
      src: "https://scrimba.com/links/travel-journal-japan-image-url",
      alt: "Mount Fuji",
    },
    title: "Mount Fuji",
    country: "Japan",
    googleMapsLink: "https://maps.app.goo.gl/6RLYZDuuuqJ7kNGZ9",
    dates: "12 Jan, 2021 - 24 Jan, 2021",
    text: "Mount Fuji is the tallest mountain in Japan...",
  },
  // Additional travel entries...
  {
    id: 2,
    img: {
      src: "https://scrimba.com/links/travel-journal-australia-image-url",
      alt: "Sydney Opera House",
    },
    title: "Sydney Opera House",
    country: "Australia",
    googleMapsLink: "https://maps.app.goo.gl/Zr17SCrsJeCEKMd36",
    dates: "27 May, 2021 - 8 Jun, 2021",
    text: "The Sydney Opera House is a multi-venue performing arts centre in Sydney. Located on the banks of the Sydney Harbour, it is often regarded as one of the 20th century's most famous and distinctive buildings.",
  },
  {
    id: 3,
    img: {
      src: "https://scrimba.com/links/travel-journal-norway-image-url",
      alt: "Geirangerfjord",
    },
    title: "Geirangerfjord",
    country: "Norway",
    googleMapsLink: "https://maps.app.goo.gl/fhkJuBhmFDv47tiB7",
    dates: "01 Oct, 2021 - 18 Nov, 2021",
    text: "The Geiranger Fjord is a fjord in the Sunnmøre region of Møre og Romsdal county, Norway. It is located entirely in the Stranda Municipality.",
  },
  {
    id: 4,
    img: {
      src: "https://tinyurl.com/2arv9gc3",
      alt: "Jumgal",
    },
    title: "Jumgal Horse Milk",
    country: "Kyrgyzstan",
    googleMapsLink: "https://maps.app.goo.gl/aivBXpgxMDiaTsb88",
    dates: '01 Oct, 2021 - 18 Nov, 2021',
    text: 'It is a mountainous district. Its main rivers are the Kökömeren and its tributaries Jumgal, Suusamyr and Batysh Karakol.',
  },
  {
    id: 5,
    img: {
      src: "https://tinyurl.com/23spwexp",
      alt: "Kel-Suu",
    },
    title: "Kol-Suu , Naryn",
    country: "Kyrgyzstan",
    googleMapsLink: "https://maps.app.goo.gl/3RzgCZA2yg7VrA53A",
    dates: '01 July, 2024 - 04 July, 2024',
    text: 'a spectacular glacial lake set in a rocky canyon whose shear sides drop almost straight down into the lake.',
  },
];
// Additional travel entries...

```

{% endtab %}

{% tab title="images" %}

<div><figure><img src="/files/l2btC9MFiE3BNxAeqcth" alt=""><figcaption><p>marker.png</p></figcaption></figure> <figure><img src="/files/RMtvs3XIiI1nrqE5HfDG" alt=""><figcaption><p>globe.png</p></figcaption></figure></div>
{% endtab %}
{% endtabs %}

### **Step 4. Create the `Header.jsx` Component**

1. This component will display a header with a globe icon and a title.
2. Structure:
   * Use a `div` with Bootstrap classes for a responsive design.
   * Include a globe icon (use an online icon or Font Awesome).
3. Example:
   * Use the `d-flex justify-content-center align-items-center` Bootstrap classes for alignment.
   * Set a background color and padding using Bootstrap utility classes.

***

### **Step 5. Create the `TravelEntry.jsx` Component**

1. This component will display individual travel entries within an `article` container.
2. Structure:
   * Use a two-column layout:
     * **Left Column**: Display the main image.
     * **Right Column**: Include:
       * Map marker icon, country name, and Google Maps link.
       * Title, dates, and description text.
   * Use Bootstrap’s grid system for the layout.
3. Suggested Bootstrap Classes:
   * `row` for the flex-row layout.
   * `col-md-4` for the image column.
   * `col-md-8` for the content column.
   * Use spacing utilities like `mb-3`, `p-2`, etc.

***

### **Step 6. Update `App.jsx`**

1. Import `Header`, `TravelEntry`, and `travelData`.
2. Map over the `travelData` array to dynamically render a `TravelEntry` component for each item.
3. Pass the travel entry data as props to `TravelEntry`.

***

### **Step 7. Applying Bootstrap Styling**

1. **Header.jsx**:
   * Add a background color with `bg-warning` or a custom class.
   * Use text alignment utilities (`text-center`) for centering the title.
2. **TravelEntry.jsx**:
   * Use the grid system (`row`, `col`) for layout.
   * Add spacing with utilities (`mt-3`, `p-3`, etc.).
   * Style the map marker and Google Maps link for better visibility.

***

### **Step 8. Final Steps**

1. Save all files and start the development server:

   ```bash
   npm run dev
   ```
2. Check the following:
   * The header appears at the top with a globe icon and title.
   * Each travel entry is displayed in a two-column layout with the provided data.
   * The application is styled using Bootstrap.

***

### **Step 9. Additional Notes**

* Adjust column widths using Bootstrap’s responsive grid classes (`col-sm`, `col-md`, `col-lg`) for different screen sizes.
* Test the links to ensure that they redirect to Google Maps correctly.
* Enhance accessibility by adding `alt` attributes to images and meaningful `aria-labels` to links.

This procedure ensures you build the application with proper styling using Bootstrap and dynamic rendering using React components. Let me know if you need clarification on any step!


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://reactjs.koida.tech/react-fundamentals/hands-on-practice-ii.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
