React with Typescript
Tags: react, typescript
Published: 2022-01-23 10:48:06

---
title: React with Typescript
published: true
description: 
tags: #React #Typescript 
cover_image: https://dev-to-uploads.s3.amazonaws.com/uploads/articles/8zlekc2btagmfu855pf7.png
---

 We will build a simple app for inviting people to our event. 

**1. To start a new Create React App project with TypeScript, you can run:**

```
npx create-react-app my-app --template typescript

# or

yarn create react-app my-app --template typescript
```

**2. Define type definition for our state**
In our **App.tsx** file we can define the type definition

```javascript
import React, { useState } from "react";
import List from "./components/List";
import "./App.css";
import AddToList from "./components/AddToList";

// Type definition
export interface IState {
  people: {
    name: string;
    age: number;
    url: string;
    {/* The question mark is used to mark that variable as an 
       optional variable */}
    note?: string;
  }[];
}

function App() {
  // we can pass our interface to our useState
  const [people, setPeople] = useState<IState["people"]>([
    {
      name: "Jean Luc Tuyishime",
      url: "https://cdn.nba.com/headshots/nba/latest/1040x760/2544.png",
      age: 44,
      note: "Lorem ipsum dollar sit amet",
    },
  ]);

  return (
    <div className="App">
      <p>people invited to my party</p>
      <List people={people} />
      <AddToList people={people} setPeople={setPeople} />
    </div>
  );
}

export default App;

```

We have also imported two files **List.tsx** and **AddToList.tsx** and passed **people** and **setPeople** as props. 

**3. In our List.tsx file**
we can import and pass props with typescript

```javascript
import React from "react";
import { IState as IProps } from "../App";

// Pass props with typescript
const List: React.FC<IProps> = ({ people }) => {
 {/* Here we are returning a JSX element */}
  const renderList = (): JSX.Element[] => {
    return people.map((person) => {
      return (
        <li className="List">
          <div className="List-header">
            <img className="List-img" src={person.url} />
            <h2>{person.name}</h2>
          </div>
          <p>{person.age} years old</p>
          <p className="List-note">{person.note}</p>
        </li>
      );
    });
  };
  return <div>{renderList()}</div>;
};

export default List;
```
**4. In our AddToList.tsx file**

```javascript
import React, { useState } from "react";
import { IState as Props } from "../App";

// Type definition for our state (people) passed as props.
interface IProps {
  people: Props["people"];
  setPeople: React.Dispatch<React.SetStateAction<Props["people"]>>;
}

const AddToList: React.FC<IProps> = ({ people, setPeople }) => {
  const [input, setInput] = useState({
    name: "",
    age: "",
    note: "",
    img: "",
  });
  
// type definition for our event => (e). 
  const handleChange = (
    e: React.ChangeEvent<HTMLInputElement | HTMLTextAreaElement>
  ): void => {
    setInput({
      ...input,
      [e.target.name]: e.target.value,
    });
  };
  
  // void is used here because we are not returning any value
  const handleClick = (): void => {
    if (!input.name || !input.age || !input.img) return;
    setPeople([
      ...people,
      {
        name: input.name,
        age: parseInt(input.age),
        note: input.note,
        url: input.img,
      },
    ]);

    setInput({
      name: "",
      age: "",
      note: "",
      img: "",
    });
  };

  return (
    <div className="AddToList">
      Add To List Component
      <input
        type="text"
        placeholder="Name"
        value={input.name}
        className="AddToList-input"
        onChange={handleChange} 
        name="name"
      />
      <input
        type="text"
        placeholder="Age"
        value={input.age}
        className="AddToList-input"
        onChange={handleChange}
        name="age"
      />
      <input
        type="text"
        placeholder="Image Url"
        value={input.img}
        className="AddToList-input"
        onChange={handleChange}
        name="img"
      />
      <textarea
        placeholder="Notes"
        value={input.note}
        className="AddToList-input"
        onChange={handleChange}
        name="note"
      />
      <button onClick={handleClick} className="AddToList-btn">
        Add To List
      </button>
    </div>
  );
};

export default AddToList;

```