wheatandcatの開発ブログ

技術系記事を投稿してます

Expoアプリ最新化③: expo-routerでmodalを使用してみる

expo-router に移行した際に、モー遷移を導入したので実装内容を共有する。

PR

github.com

背景

expo-router による通常の画面遷移では、以下の画像のように左側から新しい画面がPushされる形式になる。

この形式だと、画面下部に配置されたボタンを押した際の遷移としてはやや違和感がある。そのため、Expo公式のドキュメントを参考にしながら、モーダル遷移に修正を加えた。

docs.expo.dev

ディレクトリ構成とルーティング

expo-router はファイルベースのルーティング方式を採用しており、ファイルの配置によって画面の構造を表現する。
モーダルは modal.tsx というファイル名で以下のように配置する。

./app
└── (app)
      ├── index.tsx
      ├── _layout.tsx
      ├── modal.tsx   # ← モーダル画面
      ├── items
      ├── login
      ├── memoir

モーダル画面の実装

modal.tsx の実装内容は以下の通り。

app/(app)/modal.tsx/modal.tsx)

import FocusAwareStatusBar from "@/components/layouts/FocusAwareStatusBar";
import theme from "@/config/theme";
import Page from "@/features/memoir/components";
import React from "react";

/**
 * モーダル画面のルートコンポーネント
 */
export default function ModalScreen() {
  return (
    <>
      <FocusAwareStatusBar
        backgroundColor={theme().color.primary.main}
        style="light"
      />
      <Page />
    </>
  );
}

※FocusAwareStatusBar はステータスバーの色を制御するコンポーネント

遷移元の画面の修正

モーダル遷移を呼び出す側では、router.push() の pathname を /modal に変更する。

features/home/components/Connected.tsx

const onMemoir = useCallback(() => {
  const startDate = dayjs()
    .add(-6, "day")
    .format("YYYY-MM-DDT00:00:00+09:00");
  const endDate = dayjs().format("YYYY-MM-DDT00:00:00+09:00");

  router.push({
    pathname: "/modal",   // ← モーダルへの遷移に修正
    params: {
      startDate,
      endDate,
    },
  });
}, [router]);

完成イメージ

expo-routerでのmodalの設計が特殊なので、移行時には注意が必要。