React Router
・アクセスするURLと表示する画面の紐付けを行うライブラリ
まず
npx create-react-app --template typescript react-router
でプロジェクトを作成し、
npm i react-router-dom @types/react-router-dom
でReact Routerを使えるようにしておく。
# 基本的なルート定義
App.tsx
import { BrowserRouter, Route, Routes } from "react-router-dom";
import { Fuga } from "./components/Fuga";
import { Hoge } from "./components/Hoge";
import { Home } from "./components/Home";
import { NotFound } from "./components/NotFound";
function App() {
return (
<>
<BrowserRouter>
<Routes>
{/**
* v5では部分的に一致すればそのコンポーネントを返してたためexactが必要だったが、
* v6では完全一致が必要になったため不要に
*/}
<Route path="" element={<Home />} />
<Route path="hoge" element={<Hoge />} />
<Route path="fuga" element={<Fuga />} />
{/**
* 最後にワイルドカードを使用することで、
* コンポーネントを返してないルートに対しNotFoundを返すことができる
*/}
<Route path="*" element={<NotFound />} />
</Routes>
</BrowserRouter>
</>
);
}
export default App;
ネストしたルート定義
Routeタグの中にRouteを定義することで、ネスト状態のpathをまとめて定義できる。
また途中まで同じパスのルートを配列で定義して、Routeタグの中で回すことができる。
UserRoute.tsx
import { UserIndex } from "../components/User/UserIndex";
import { UserCreate } from "../components/User/UserCreate";
export const UserRouter = [
{
path: 'index',
element: <UserIndex />
},
{
path: 'create',
element: <UserCreate />
}
];
Route.tsx
import { Route, Routes } from "react-router-dom"
import { NotFound } from "../components/NotFound";
import { UserRouter } from "./UserRoute";
export const Router = () => {
return (
<>
<Routes>
<Route path='users'>
{
UserRouter.map((route) => (
<Route key={route.path}
path={route.path}
element={route.element}
/>
))
}
</Route>
{/**
* V5だと*のNotFound定義はネストしたものに対応できずRouteタグ内に書く必要があったが、
* V6は対応可能となった(users/hogeみたいなものでもNotFoundを返す)
*/}
<Route path="*" element={<NotFound />} />
</Routes>
</>
)
}
クエリパラメータを利用したルート定義
Query.tsx
import { useLocation } from "react-router-dom"
export const Query = () => {
/**
* useLocation()の中にはpathnameやkey,stateなどが入っている
* その中にsearchというのがあり、そこにurlの?以降が入っている
*/
const { search } = useLocation()
//クエリパラメータに関する便利メソッドができる
const query = new URLSearchParams(search)
return (
<>
<div>idクエリ {query.get('id')}</div>
<div>nameクエリ {query.get('name')}</div>
</>
);
}
Route.tsx
import { Route, Routes } from "react-router-dom"
import { NotFound } from "../components/NotFound";
import { Query } from "../components/Query";
export const Router = () => {
return (
<>
<Routes>
<Route path="/query" element={<Query />} />
<Route path="*" element={<NotFound />} />
</Routes>
</>
)
}
URLパラメータを利用したルート定義
Url.tsx
import { useParams } from "react-router-dom";
export const Url = () => {
/**
* useParams()でパラメータ部分を取得
* Router定義で/:paramaterとなっているのがuseParamsのなかに入る
*/
const { paramater } = useParams();
return (
<>
{/**
* url/sampleと入力することで、
* パラメータ sampleと出力される
*/}
<p>パラメータ {paramater}</p>
</>
)
}
Route.tsx
import { Route, Routes } from "react-router-dom"
import { NotFound } from "../components/NotFound";
import { Url } from "../components/Url";
export const Router = () => {
return (
<>
<Routes>
{/**
* :がURLパラメータ部分
*/}
<Route path="/url/:paramater" element={<Url />} />
{/**
* urlだけだとNotFoundが返される
*/}
<Route path="*" element={<NotFound />} />
</Routes>
</>
)
}
#画面からの遷移
・Lintタグで囲う(aタグに近いもの)
・useNavigateの使用
Home.tsx
import { FC, memo } from "react";
import { useNavigate } from "react-router-dom";
import { Link } from "react-router-dom";
export const Home: FC = memo(() => {
const navigate = useNavigate()
/**
* navigate()で行きたいパスを指定
*/
const onClickHoge = () => navigate('/hoge')
/**
* 値を入れることで、その値の分だけ戻る/進むことができる
*/
const onClickPrev = () => navigate(-1)
const onClickNext = () => navigate(+1)
return (
<>
Homeのページ
<Link to='/hoge' >hoge</Link>
<Link to='/fuga' >fuga</Link>
<button onClick={onClickPrev}>前へ</button>
<button onClick={onClickNext}>次へ</button>
<button onClick={onClickHoge} >hogeへ遷移</button>
</>
);
});
前回:CSSについて
次回:グローバルstateの管理について