はじめに
30代未経験からエンジニアを目指して勉強中のYNと申します。
JavaScriptでReactが書ける人向けの、React × TypeScript入門記事です。
新しいReactプロジェクトつくる
npx create-recact-app <your-pjt-name> --typescript
コードを書き始める前に
SnippetからReactコンポーネントのテンプレートを作る
まずはSnippetを作ると楽です。
VScodeであれば、Snippetを使って一瞬でコンポーネントのテンプレートを持って来れます。
cmd + shift + p
> Preference:Configure User Snippets
> typescriptreact
でスニペットの設定ができます。 typescriptreact.json
を下記のように変更します。
{
"Typescript React Function Component": {
"prefix": "rh",
"body": [
"import React from 'react'",
"",
"interface ${TM_FILENAME_BASE}Props {",
"$1",
"}",
"",
"export const $TM_FILENAME_BASE: React.FC<${TM_FILENAME_BASE}Props> = ({$2}) => {",
"\t\treturn ($3);",
"}"
],
"description": "Typescript React Function Component"
}
}
オートサジェストを有効にする
TypeScriptを使うメリットの一つに、型指定によるオートサジェストにあります。 試しにpropsの場所でCtrl
+Space
を押すと、指定可能なpropsの一覧が表示されます。
VScodeであれば、デフォルトでCtrl
+Space
で有効になっているはずです。
もし作動しなければ、(Macの場合)システム環境設定
> キーボード
> ショートカット
で Ctrl
+Space
の既存ショートカットを無効化しましょう。
Reactコンポーネントの基本
Function Component
interfaceで型を定義し、React.FC
にgenericsとして渡します。
import React from "react";
interface Props {
text: string;
ok?: boolean;
i?: number;
}
export const TextField: React.FC<Props> = ({text ="hello", i=1, ok=true }) => {
return (
...
);
};
onClick
マウスホバーすれば、定義すべき型がわかります。
import React from 'react';
interface OnclickProps {
onClick?: (event: React.MouseEvent<HTMLDivElement, MouseEvent>) => void;
// divタグのonClickにカーソルを合わせると、この型を指定すればいいことがわかる
text?: string;
}
const Onclick: React.FC<OnclickProps> = ({ onClick, text }) => {
return <div onClick={onClick}>{text}</div>;
};
export const Click: React.FC<OnclickProps> = () => {
const logText = (e: React.MouseEvent<HTMLDivElement, MouseEvent>) =>
console.log(e.target);
return <Onclick onClick={logText} text={'hello!!'} />;
};
Hooks
###useState
Hooksもgenericsで型を定義します。
import React, { useState } from 'react';
interface CounterProps {
initialCount: number;
}
export const Counter: React.FC<CounterProps> = ({ initialCount }) => {
const [count, setCount] = useState<number>(initialCount); // countの型をgenericsで指定
return (
<>
<button onClick={() => setCount(count + 1)}>+</button>
<div>{count}</div>
</>
);
};
###useReducer
ActionやStateもtypeやinterfaceを使って型を定義します。
import React, { useReducer } from "react";
type Actions =
| { type: "add"; text: string }
| {
type: "remove";
idx: number;
};
interface Todo {
text: string;
complete: boolean;
}
type State = Todo[];
const TodoReducer = (state: State, action: Actions) => {
switch (action.type) {
case "add":
return [...state, { text: action.text, complete: false }];
case "remove":
return state.filter((_, i) => action.idx !== i);
default:
return state;
}
};
export const ReducerExample: React.FC = () => {
const [todos, dispatch] = useReducer(TodoReducer, []);
return (
<div>
{JSON.stringify(todos)}
<button
onClick={() => {
dispatch({ type: "add", text: "..." });
}}
>
+
</button>
</div>
);
};