React Native Expo のプロジェクトに Tamagui を導入
Tamagui をお試し中です。Web と React Native の両方に対応しており、モノレポ構成等でコードを共通化できるのが強みの 1 つです。が、今回はシンプルに、React Native Expo 単体のプロジェクトに Tamagui を導入してみます。
事前準備
執筆時の環境
- node v20.10.0
- create-expo-app v2.1.1
- expo v49.0.21
- tamagui v1.82.3
React Native Expo のプロジェクトを作成
まず初めに、create-expo-app
をインストール後、新規の expo プロジェクトを立ち上げましょう。ターミナルから以下のコマンドを実行してください。プロジェクト名は自由に設定していただいて OK です。
npm install --save-dev create-expo-app
npx create-expo-app my-expo-project --template
--template
オプションを付けておくとプロジェクトのテンプレートを選択できます。
今回は Expo Router を使用したかったため、Navigation (TypeScript) - File-based routing with TypeScript enabled
を選択しました。
プロジェクトの作成が完了すると、my-expo-project
ディレクトリの配下にファイル・ディレクトリ群が生成されます。
以降は、my-expo-project
ディレクトリ内に移動して作業していきます。
サーバの立ち上げ
ここで一度 expo サーバを立ち上げてみましょう。ターミナルから以下のコマンドを実行し、表示された QR コードをスマートフォンの Expo Go でスキャンしてください。
npm run start
無事サンプルアプリケーションが表示されれば OK です。
Tamagui の導入
Tamagui をインストールします。
npm install tamagui
併せて、設定を簡便にするため、提供されているテーマなどをインストールしておきます。追々カスタマイズしていくことになるかと思いますが、最初はシンプルにいきましょう。
npm install @tamagui/font-inter
npm install @tamagui/shorthands
npm install @tamagui/themes
続いて、プロジェクトのルートに tamagui.config.ts
を作成します。中身は 公式ドキュメント の Quick Start を参考にしつつ、以下のようにしました。
import { createInterFont } from "@tamagui/font-inter";
import { shorthands } from '@tamagui/shorthands'
import { themes, tokens } from '@tamagui/themes'
import { createTamagui } from 'tamagui'
const headingFont = createInterFont();
const bodyFont = createInterFont();
const appConfig = createTamagui({
themes,
tokens,
shorthands,
fonts: {
heading: headingFont,
body: bodyFont,
},
})
export type AppConfig = typeof appConfig
declare module 'tamagui' {
interface TamaguiCustomConfig extends AppConfig {}
}
export default appConfig
続いて、_layout.tsx に Tamagui の Provider を追加します。今回はプロジェクト全体に適用させたいので、app 直下の _layout.tsx を以下のように変更します。
import FontAwesome from '@expo/vector-icons/FontAwesome';
import { DarkTheme, DefaultTheme, ThemeProvider } from '@react-navigation/native';
import { useFonts } from 'expo-font';
import { SplashScreen, Stack } from 'expo-router';
import { useEffect } from 'react';
import { useColorScheme } from 'react-native';
import { TamaguiProvider } from "tamagui"; // インポートの追加
import appConfig from "../tamagui.config"; // インポートの追加
export {
ErrorBoundary,
} from 'expo-router';
export const unstable_settings = {
initialRouteName: '(tabs)',
};
SplashScreen.preventAutoHideAsync();
export default function RootLayout() {
const [loaded, error] = useFonts({
SpaceMono: require('../assets/fonts/SpaceMono-Regular.ttf'),
Inter: require("@tamagui/font-inter/otf/Inter-Medium.otf"), // フォント追加
InterBold: require("@tamagui/font-inter/otf/Inter-Bold.otf"), // フォント追加
...FontAwesome.font,
});
useEffect(() => {
if (error) throw error;
}, [error]);
useEffect(() => {
if (loaded) {
SplashScreen.hideAsync();
}
}, [loaded]);
if (!loaded) {
return null;
}
return <RootLayoutNav />;
}
function RootLayoutNav() {
const colorScheme = useColorScheme();
// TamaguiProvider で囲む (デフォルトテーマとしてダークテーマを指定)
return (
<ThemeProvider value={colorScheme === 'dark' ? DarkTheme : DefaultTheme}>
<TamaguiProvider config={appConfig} defaultTheme="dark">
<Stack>
<Stack.Screen name="(tabs)" options={{ headerShown: false }} />
<Stack.Screen name="modal" options={{ presentation: 'modal' }} />
</Stack>
</TamaguiProvider>
</ThemeProvider>
);
}
Button を表示してみる
最後に、Tamagui の Button コンポーネント を利用してみましょう。
app/(tabs)/index.tsx
を以下のように書き換えます。
import { Button, YStack } from 'tamagui';
export default function TabOneScreen() {
return (
<YStack padding="$10">
<Button size="$6">Button</Button>
</YStack>
);
}
Expo Go で再度アプリを確認してみます。以下のようにボタンが表示されていれば成功です。
まとめ
本記事では、React Native Expo のプロジェクトに Tamagui を導入する手順を紹介しました。
最後に、本記事で作成したプロジェクトのリポジトリを貼っておきます。
ここまでお読みいただきありがとうございました!
Discussion