【インタビューAI】Bootstrapからshadcn UIへの変更:高速で軽量なUIの実現
はじめに
1時間の音声を15秒で文字起こしし自然な会話形式に自動変換する「インタビューAI」を個人開発中。
昨日、ReachBestという「AIを活用して高校生の海外大学への出願をサポートするサービス」を創業している、Ryusei君と話をする機会があり、開発しているインタビューAIのデモを見せて、UIはBootstrapで作成していることを伝えたところ、Shadcn UIというUIフレームワークを勧められたので、早速乗り換えることにした。
shadcn UIに変更するメリット
shadcn/uiは、Radix UIとTailwindCSSを用いて開発された、高い自由度を持つUIコンポーネント集。
shadcn UIは、必要なコンポーネントのみを個別にインポートして使用できるため、アプリケーションが軽量になる。これに対して、Bootstrapは通常、全体のスタイルシートをインポートし、その中に不要なスタイルも含まれることが多い。これがファイルサイズや読み込み時間に影響する可能性がある。
また、shadcn UIは、Reactのコンポーネントとして設計されているため、必要に応じてレンダリングされ、DOMの変更も最適化されている。BootstrapのJavaScriptコンポーネントは、依存関係が多く、時にはパフォーマンスに影響を与えることがある。
ReactでBootstrapからshadcn UIに変更する手順
Bootstrapのアンインストール
Bootstrapをプロジェクトのから削除する(今回はfrontend/で実行)。
npm uninstall bootstrap react-bootstrap
shadcn UIのインストール
shadcn UIをプロジェクトに追加する(今回はfrontend/で実行)。
npm install @shadcn/ui
必要な依存関係
shadcn/uiはTailwind CSSをベースにしているため、Tailwind CSSもインストールして設定する必要がある。以下のコマンドを実行して、Tailwind CSSをインストールする。
npm install -D tailwindcss postcss autoprefixer
npx tailwindcss init -p
Tailwind CSSの設定
tailwind.config.js
とpostcss.config.js
が生成されるので、tailwind.config.js
を開いて以下のように設定する。
今回は、ブランドカラーをテーマの拡張として、brand, brand-dark, brand-lightを作成した。
// tailwind.config.js
module.exports = {
content: ["./src/**/*.{js,jsx,ts,tsx}"],
theme: {
extend: {
colors: {
brand: "#3d5a80",
"brand-dark": "#2a4563",
"brand-light": "#4a7ea8",
},
},
},
plugins: [],
};
CSSファイルの設定
src/index.css
(またはプロジェクト内の適切なCSSファイル)を以下のように設定します。
@tailwind base;
@tailwind components;
@tailwind utilities;
App.tsxのコードを変更
アプリケーションのエントリーポイントであるApp.tsx
のコードを、shadcn UIを使ったボタンやナビゲーションの実装に変更する。
// App.tsx
import { onAuthStateChanged } from "firebase/auth";
import React, { useCallback, useEffect, useState } from "react";
import { Link, Navigate, Route, Routes, useNavigate } from "react-router-dom";
import "./App.css";
import Login from "./components/Auth/Login";
import PasswordReset from "./components/Auth/PasswordReset";
import Register from "./components/Auth/Register";
import SubscriptionForm from "./components/SubscriptionForm";
import TitleAndHeaderGenerator from "./components/TitleAndHeaderGenerator/TitleAndHeaderGenerator";
import Transcription from "./components/Transcription/Transcription";
import { deleteAccount, logout } from "./services/authService";
import { auth } from "./services/firebaseConfig";
import Navbar from "./components/Navbar";
import { Button } from "./components/ui/button";
type UsageData = {
続きは、こちらで記載しています。
Discussion