xxxxxxxxxx
// prop drilling method of doing is commented out.
/*
The React Context API uses a Provider and Consumer pattern to share data
throughout an application. The provider role is played by a React component
that makes data available to its descendant components
*/
/*
Context Providers:
React Context objects include a .Provider property that is a React component.
It takes in a value prop to be made available to all its descendent components.
**step 1**: To use the React Context API, we start by creating a React context object,
a named object created by the React.createContext() function.
Context objects include a .Provider property that is a React component.
It takes in a value prop to be stored in the context.
-------------------------------------------
-Example -
<MyContext.Provider value="Hello world!">
<ChildComponent />
</MyContext.Provider>
----------------------------------------------
That value — in this case, the string "Hello world!" — is available to all
its descendent components. Descendent components — in this case, ChildComponent —
can then retrieve the context’s value with React’s useContext() hook.
------------------------------------------------
***Step 2 ***:
import { useContext } from 'react';
import { MyContext } from './MyContext.js'
const ChildComponent = () => {
const value = useContext(MyContext);
return <p>{value}</p>;
}
// Renders <p>Hello, world!</p>
----------------------------------------------
*/
----------------------------------------------------------------------
// MyContext.jsx , insert in a new file or in App.js
import React, { useState, useEffect, createContext } from "react";
export const MyContext = createContext();
----------------------------------------------------------------------
import { useState } from 'react';
import { SearchParams } from "./components/SearchParams";
import {MyContext} from './components/MyContext'
function App() {
// const [animal, setAnimal] = useState("");
const animalHook = useState(""); // we can write above like this.
// const [breed, setBreed] = useState("");
const breedHook = useState("");
// const [location, setLocation] = useState("");
const locationHook = useState("");
// const obj = {
// animal,
// setAnimal,
// breed,
// setBreed,
// location,
// setLocation
// }
return (
// <MyContext.Provider value={{ animal, setAnimal, breed, setBreed, location,
// setLocation }}>
<MyContext.Provider value={{ animalHook, breedHook, locationHook }}>
// value is in double curly quotes because multiple values
// are placed in an object.
<div>
<h1>Adopt</h1>
</div>
<SearchParams
// {...obj}
/>
</MyContext.Provider>
);
}
export default App;
-----------------------------------------------------
// SearchParams.jsx
import {useState} from 'react'
import { Form } from './Form';
export const SearchParams = () => {
return (
<div className="search-params">
<Form
// {...props}
/>
</div>
)
}
---------------------------------------------------------------------
// Form.jsx, this is Consumer Component.
import { useState, useContext } from "react";
import {MyContext} from './AppContext'
const ANIMALS = ["bird", "cat", "dog", "rabbit", "reptile"];
const breeds = ["poodle"];
export const Form = (props) => {
const { animalHook, breedHook, locationHook } = useContext(MyContext); //{}not[]
const [animal, setAnimal] = animalHook;
const [location, setLocation] = locationHook;
const [breed, setBreed] = breedHook;
return (
<>
<form>
<input
type="text"
name="location"
id="location"
placeholder="Location"
// value={props.location}
value={location}
// onChange={(e) => props.setLocation(e.target.value)}
onChange={(e) => setLocation(e.target.value)}
/>
<label htmlFor="animal">
Animal
<select
// value={props.animal}
value={animal}
// onChange={(e) => props.setAnimal(e.target.value)}
onChange={(e) => setAnimal(e.target.value)}
>
<option />
{ANIMALS.map((animal) => (
<option key={animal}>{animal}</option>
))}
</select>
</label>
<label htmlFor="breed">
Breed
<select
// value={props.breed}
value={breed}
// onChange={(e) => props.setBreed(e.target.value)}
onChange={(e) => setBreed(e.target.value)}
>
<option />
{breeds.map((breed) => (
<option key={breed}>{breed}</option>
))}
</select>
</label>
<button>Submit</button>
</form>
</>
);
};