Uniwindとは何か?React Native向けTailwind CSSライブラリの特徴と概要を詳しく解説
目次
- 1 Uniwindとは何か?React Native向けTailwind CSSライブラリの特徴と概要を詳しく解説
- 2 Uniwindの導入方法とセットアップ手順:React Nativeプロジェクトへのインストールガイド
- 3 NativeWind・Unistylesとの徹底比較:Uniwindのパフォーマンスと機能の優位性を検証
- 4 Uniwindの主な機能とメリット:Tailwind統合による高速なスタイリングと柔軟性を詳しく紹介
- 5 Uniwind無料版とPro版の違い:機能・パフォーマンス・対応環境・サポート体制・価格面を徹底比較
- 6 実践:Uniwindの使い方とサンプルコード – classNameを使ったReact Nativeコンポーネントのスタイリング例
- 7 Uniwindのスタイリング方法を解説:classNameやカスタムCSSの活用テクニックを詳しく解説
- 8 Uniwindでのテーマ設定とダークモード対応方法:ライト/ダークテーマの切替やカスタムテーマ設定を解説
- 9 プラットフォームごとのスタイルカスタマイズ方法:iOS/Android/Webで異なるデザインを適用する
- 10 Uniwindに関するよくある質問とトラブルシューティング:よくある疑問点とトラブルへの対処法をQ&Aで紹介
Uniwindとは何か?React Native向けTailwind CSSライブラリの特徴と概要を詳しく解説
Uniwind(ユニウィンド)は、React NativeアプリでTailwind CSSのユーティリティクラスをそのまま利用できるようにするためのスタイリングライブラリです。もともと高性能なスタイリングエンジンUnistylesを開発したチームによって作られており、「React Native向けTailwindバインディングの中で最速」と謳われています。Tailwind CSSの“className”プロパティをReact Nativeの全ての標準コンポーネントで直接使用できることが最大の特徴で、開発者はWeb開発でおなじみのTailwindのクラス名をそのままReact Nativeでも指定できます。スタイルはビルド時に計算・キャッシュされ、ランタイムでのオーバーヘッドを極力抑えています。さらに、あらかじめ生成されたスタイルやNitroモジュール(高速なネイティブモジュール)を活用した設計によって、高速なスタイル適用を実現しています(Unistyles v3.0や他のライブラリよりも高速であるとされています)。
Uniwindの特徴として、Tailwind CSS v4に完全対応しており、全てのユーティリティクラス・バリアント(疑似クラスやレスポンシブ対応など)をサポートします。React Nativeの新旧いずれのアーキテクチャでも動作し、Expo Goにも対応(Pro版を除く)しています。また、カラーモード(ライト/ダークモード)や画面サイズ・向きによるスタイルの切り替え(ブレークポイントやオリエンテーション)も組み込みでサポートされており、ユーザーの環境に応じて柔軟にスタイルを変化させることが可能です。Uniwind自身は現在RC版(Release Candidate)として公開されていますが、ドキュメントによれば既にプロダクション利用も想定した安定度を備えているとされています。
まとめると、Uniwindは「React NativeにTailwind CSSの開発体験をもたらす高性能ライブラリ」です。React Native開発者にとって、CSSを書かずにTailwindクラスでスタイリングできる利便性と、ネイティブパフォーマンスを両立したソリューションとなっています。次のセクションから、そんなUniwindの導入方法や他ライブラリとの比較、機能詳細について順に解説していきます。
Uniwindの導入方法とセットアップ手順:React Nativeプロジェクトへのインストールガイド
UniwindをReact Nativeプロジェクトに導入する手順はシンプルで、数分でセットアップが完了します。以下に、Expoプロジェクトを例に具体的な手順をガイドします。
Step 1: ライブラリとTailwind CSSのインストール
プロジェクトにUniwind本体とTailwind CSSパッケージを追加します。npmの場合、次のコマンドでインストールできます。
npm install uniwind@next tailwindcss
※現在(RC版)、npmではuniwind@nextタグを指定する必要があります。
併せて、プロジェクトのルート(あるいはsrcやappディレクトリ)にglobal.cssというファイルを作成し、そこにTailwindとUniwindのスタイルをインポートします。例えば以下のように記述します。
@import 'tailwindcss';
@import 'uniwind';
/* 必要に応じてこの下にカスタムのCSSやテーマ変数を追加 */
さらに、アプリのエントリポイント(通常はApp.tsxやindex.js)でこのCSSファイルをインポートします。App.tsx内で、
import './global.css'; // TailwindとUniwindのグローバルスタイルを読み込み
// ...他のimport
export const App = () => { ... }
のようにインポートしてください(※Expoの場合、index.jsではなくApp.tsx内で読み込むことで、ホットリロードに支障が出ないようにします)。
Step 2: Metroバンドラの設定
UniwindはMetroバンドラに組み込みのプラグインを提供しており、Tailwindのクラスをビルド時に解釈させる必要があります。プロジェクト直下にmetro.config.jsファイルを作成(または既存のものを編集)し、Uniwindの設定を追加します。Expoプロジェクトの場合、以下のような設定になります。
const { getDefaultConfig } = require('expo/metro-config');
const { withUniwindConfig } = require('uniwind/metro');
const config = getDefaultConfig(__dirname);
module.exports = withUniwindConfig(config, {
cssEntryFile: './src/global.css', // 先ほど作成したCSSファイルへのパス
dtsFile: './src/uniwind-types.d.ts' // (オプション) クラス名の型定義出力先
});
上記の設定により、Metro実行時にTailwind CSSのJITコンパイラが働き、使用されている全Tailwindクラスに対応したスタイルが自動生成されます。また、dtsFileを指定すると、プロジェクトに存在するTailwindクラス名の型定義ファイルが生成され、TypeScript環境でclassNameに補完や型チェックが効くようになります。設定を追加したら、一度Metroサーバーを再起動してください。
Step 3: 開発環境での補完設定(オプション)
Visual Studio CodeなどでTailwind IntelliSenseプラグインを利用している場合、React NativeにおけるclassNameプロパティでも補完が効くように設定を追加します。VSCodeならsettings.jsonに以下のように追記します。
{
"tailwindCSS.classAttributes": [
"class", "className", "headerClassName", "contentContainerClassName", ...
// ← 省略:Uniwindで使用される全てのクラスプロップを列挙
],
"tailwindCSS.classFunctions": [
"useResolveClassNames"
]
}
これにより、<View className="…" />や<Text headerClassName="…" />といったUniwind固有のプロップについてもTailwindプラグインが認識し、補完候補を表示するようになります。
以上でセットアップは完了です。Uniwind導入後は、React NativeコンポーネントでclassNameプロパティにTailwindのユーティリティクラスを記述するだけでスタイルを適用できるようになります。もしExpoを利用している場合も、Expo Go上でそのまま動作します(Expo Goは独自ネイティブモジュールを読み込めませんが、Uniwindのフリー版は純粋なJavaScript実装のためExpo Go対応しています)。なお、NativeWindから移行する場合は、Babelのプラグイン設定(nativewind/babelプリセット)を削除し、tailwind.config.jsも不要になる点に注意してください。
NativeWind・Unistylesとの徹底比較:Uniwindのパフォーマンスと機能の優位性を検証
Tailwind CSSをReact Nativeで使うライブラリとしては、NativeWind(有名な既存ライブラリ)やUnistyles(Uniwind開発元が以前リリースした高性能スタイルエンジン)があります。これらとUniwindを比較すると、パフォーマンス面および機能面でいくつか違いが際立ちます。
パフォーマンス比較
ベンチマーク結果によれば、UniwindのパフォーマンスはNativeWindを大きく上回り、Unistyles v3.0とほぼ同等の水準です。React Nativeで1000個のコンポーネントをレンダリングしてスタイル適用するテストでは、NativeWindが約197msかかったのに対しUniwindは約81msで完了し、約2倍以上高速でした。これは、Uniwindがスタイルの解釈を実行時ではなくビルド時に行い、かつキャッシュを駆使していることによります。対してNativeWindは実行時にクラス文字列を解析する部分があるため、初回レンダリングに時間がかかりがちです(もっとも、どちらも2回目以降のレンダリングではキャッシュされ高速になります)。一方、Unistyles v3.0(C++エンジンを使った先代ライブラリ)は約66msとさらに高速ですが、UniwindのPro版ではこのUnistylesエンジンを組み込みネイティブレベルのパフォーマンスを実現する予定です。したがって、現状のフリー版Uniwindは「十分高速(Unistyles 3.0相当)」、将来的に提供されるPro版では「React Nativeにおける最高クラスの高速スタイリング」が期待できます。
機能・使い勝手の比較
Tailwind対応範囲
Uniwind・NativeWindともに基本的なTailwind CSSのユーティリティはサポートしています。ただしUniwindはTailwind CSS v4専用で動作し、最新の@themeディレクティブによるテーマ変数管理など新機能を活用できます。一方NativeWindは(2023年時点で)Tailwind v3ベースであるため、v4の新機能を使うには対応待ちとなります。また、Tailwindの設定ファイル(tailwind.config.js)の扱いも異なります。NativeWindではtailwind.config.jsでテーマやプラグイン設定を行いますが、UniwindはCSSファイル上でテーマ変数を定義する方式に移行しました。そのためUniwind利用時はtailwind.config.js自体が不要で、代わりにglobal.css内でカスタムテーマやCSS変数を設定します。結果として、Uniwindではプロジェクト設定がシンプルになり、テーマ変更もコードではなくCSS編集で対応できる利点があります。
Darkモード・テーマ対応
NativeWindではダークモード対応において
スタイル指定方法
両者ともJSX内でclassNameを使うアプローチですが、NativeWindはBabelプリセットを用いてclassName文字列を解析するのに対し、UniwindはMetroバンドラ拡張でclassNameを解析します。そのため、UniwindではBabel設定が不要で、既存コードに侵入的な変更を加えず導入しやすいです。また、React Native Web(Web対応)については、NativeWindがCSSベースのスタイリングに切り替えることでHoverやグループセレクタなどWeb特有の疑似クラスも扱える強みがありました。UniwindもReact Native Webをサポートし、web:プレフィックスでWeb固有スタイルを出し分けできますが(後述)、Hoverやフォーカス状態のスタイル指定(擬似クラス)については現状サポート情報がありません。この点では、Webも含めたTailwind完全互換性ではNativeWindに軍配が上がる可能性があります。ただし、UniwindはカスタムCSSパーサーを内蔵しており、必要に応じてCSSで擬似クラス付きのスタイルを書くことも可能です(これも後述します)。
アニメーション対応
NativeWindではアニメーション(特にレイアウトや色のアニメーション)を行う際、直接クラスの付け替えでアニメーションさせることは難しく、react-native-reanimatedと組み合わせる場合は
以上のように、UniwindはNativeWindやUnistylesの長所を取り入れつつ、性能面では大幅な改善を遂げています。また、設定ファイル不要やテーマ変数の扱いなど開発体験の簡素化も図られているため、既存プロジェクトからの移行価値は十分にあると言えるでしょう。特にアプリ規模が大きくレンダリング性能を追求したいケースや、Tailwind v4の新機能を活かしたいケースでは、Uniwindの優位性が発揮されます。
Uniwindの主な機能とメリット:Tailwind統合による高速なスタイリングと柔軟性を詳しく紹介
Uniwindが提供する主要な機能と、それによって得られるメリットを整理します。Tailwind CSSとの統合を前提に、React Native開発がどのように効率化・高速化されるのか見てみましょう。
Tailwind CSS v4完全対応
前述の通り、UniwindはTailwind CSSの最新バージョン4に対応しています。これにより全てのユーティリティクラス(レイアウト、色、タイポグラフィ、ボーダー、シャドウなど)やレスポンシブ変種(sm:, md:など)、状態変種(dark:やカスタムテーマ)をフルサポートしています。Web開発者がTailwindで慣れ親しんだクラス体系を、そのままReact Nativeでも使用できるメリットは大きいです。特に、Tailwind v4で導入された@themeディレクティブ(CSS変数を用いたテーマ管理)はUniwindの基盤にもなっており、これを活用することで従来以上に洗練されたテーマ切替・カスタマイズが可能です。
classNameの標準サポートと自動プロップマッピング
UniwindではReact Nativeに含まれる全てのコンポーネントに対してclassNameプロパティが利用可能になっています。例えば<View>や<Text>はもちろん、<Image>, <ScrollView>, <TextInput>などでもclassNameでスタイル指定ができます。また、背景色やレイアウトといった通常のスタイル以外に、コンポーネント固有のプロパティに対しても対応する「◯◯ClassName」プロパティが用意されています。例えばImageBackgroundコンポーネントでは、背景画像自体のスタイルにimageClassName、画像のティントカラーにtintColorClassNameを使うことで、それぞれにTailwindクラス(色ならaccent-…系)を適用できます。他にもTextInputのplaceholderカラーや、ScrollViewのコンテンツコンテナスタイルなど、React Nativeの各種プロップにTailwindクラスでアクセスできるよう自動マッピングされています。これにより、スタイルのために都度StyleSheetやInline styleを記述する必要がほぼ無くなります。
ビルド時コンパイルによる高速化
Uniwind最大の特徴は、スタイル解釈の大部分をビルド時に実行することです。MetroバンドラでUniwindのプラグインが動作し、使用された全Tailwindクラスを解析してRNのStyleSheetオブジェクト群を生成します。そのためアプリ起動時や画面描画時に行われる処理は、各コンポーネントにプリコンパイル済みのスタイルを当てはめるだけで済みます。これに対し、ランタイムコンパイル型のライブラリ(例: tailwind-react-native-classnames 等)では初回描画時に文字列解析が発生するため遅くなりがちですが、Uniwindは初期レンダリングが軽量であるという利点があります。加えて、Uniwindはスタイルの再利用時にキャッシュする戦略も取り、同じクラスの組み合わせであれば再度計算せずに即時適用します。以上により、アプリ全体のパフォーマンス向上(特に画面遷移時のチラつき軽減やリスト表示の滑らかさ向上)につながります。
Expoとの親和性
React NativeユーザーにはExpoを使う開発者も多いですが、Uniwindのフリー版はExpo Goで動作可能です。ネイティブモジュールを追加せずとも動くため、ExpoのManage Workflowでも問題ありません(Metro設定は必要ですが、純粋JSで完結するためExpoでも扱えます)。これは、同じ開発元のUnistylesが新しいアーキテクチャ前提(TurboModules利用)だったのに対し、Uniwindフリー版は従来アーキテクチャ上でも動くよう設計されているためです。将来的にリリースされるPro版はC++ネイティブモジュールを含むためExpo Goでは動きませんが、それでも開発中はフリー版で素早く検証し、本番ビルドではPro版に差し替える、といった使い分けも可能になるでしょう。
高度なカスタムスタイル対応(CSS統合)
Uniwindには独自のCSSパーサーが内蔵されており、Tailwindで用意されたユーティリティに無いスタイルや複雑なスタイルも純粋なCSSを書くことで定義可能です。たとえば「特定クラスに対してドロップシャドウを適用しつつ、複数の子要素をレイアウトする」といったケースで、Tailwindのユーティリティクラスだけでは表現が難しい場合があります。Uniwindではglobal.css内に独自クラスを記述し(通常のCSS記法に近い形でプロパティを書けます)、そのクラス名をJSXのclassNameに指定できます。これにより、Tailwindのカバーしない細かなデザインにも対応できます。また、Tailwindクラスとの併用もシームレスで、一つのclassName文字列中でカスタムCSSクラスと既存ユーティリティを空白区切りで併記することも可能です。
以上のように、Uniwindは「フロントエンドの開発効率」と「ネイティブアプリの性能・柔軟性」の両立を図ったライブラリです。Tailwindのエコシステムをそのまま活かしつつ、React Nativeに特化した機能(プラットフォームセレクタやネイティブ連携)を備えている点で、他のスタイリング手法に比べ強力なメリットを提供しています。
Uniwind無料版とPro版の違い:機能・パフォーマンス・対応環境・サポート体制・価格面を徹底比較
UniwindにはオープンソースでMITライセンスの無料版(フリー版)と、追加機能や高性能化を図った商用のPro版が用意されています。それぞれの違いを、機能やパフォーマンス、サポート面などの観点から比較します。
機能比較
Tailwind対応
無料版・Pro版ともにTailwind CSS v4の全機能をサポートします。ユーティリティクラスやテーマ機能について差異はなく、基本的なスタイリング機能に制限はありません。
テーマシステム
ライト/ダークやカスタムテーマ切替も両版で同様に利用可能です。テーマ関連のAPI(Uniwind.setThemeやuseUniwindフック等)も共通です。
プラットフォームセレクタ
iOS/Android/Webそれぞれへのスタイル出し分け機能も両版で利用できます。したがって、機能面では無料版でもほぼ全てのUniwind機能をカバーしています。
速度・効率
無料版は「Unistyles 3.0と同等」の性能とされています。これはかなり高速な部類ですが、Pro版はさらに「最高クラスのパフォーマンス」を目指しており、無料版を凌ぐ速度でスタイリング処理を行います。
エンジン
無料版はJavaScriptベースで動作し、Metro上でJSによりスタイル計算・適用を行います。一方Pro版はC++で実装されたUnistylesエンジンを使用し、JSとネイティブの橋渡し(JSI/TurboModules経由)でスタイル適用を実行します。これにより、特に大量のスタイル変更時や低スペック端末での安定したパフォーマンスが期待できます。
シャドーツリー更新
無料版では通常のReact再レンダリングを通じてスタイルを更新しますが、Pro版ではShadow Tree(レイアウトツリー)の更新時にReactの再レンダリングを伴わない仕組みを導入しています。これにより、スタイル変更によってコンポーネントの再描画負荷がかからずUIが非常に滑らかになります。
アニメーション
無料版ではclassNameでのアニメーションはサポートしておらず、従来通りAnimatedやreact-native-reanimatedを用いて手動でスタイルを変更する必要があります。しかしPro版ではReanimated 4と連携し、classNameに対するアニメーション指定が可能になります。これにより、UI要素の出現/消失アニメーションやテーマトグル時のなめらかなトランジションが実現できます。
Expo Go対応
無料版はExpo Goで動作しますが、Pro版はExpo Go非対応です。Pro版はカスタム開発クライアントを必要とし、ネイティブコード(C++バインディング)を含むため、Expoで利用する場合はEASビルドやDev Clientが必要になります。
旧アーキテクチャ
無料版はFabricやTurboModulesを必須としないため、旧ブリッジのままでも動作します。Pro版はJSI/TurboModulesベースの実装となるため、React Nativeの新アーキテクチャ対応が事実上必要です(React Native 0.70以降、あるいは設定で新アーキテクチャ有効化)。新規プロジェクトであれば問題ないですが、古いRNバージョンを使っている場合Pro版導入にはアップグレードが伴う可能性があります。
サポート体制とライセンス
無料版はMITライセンスで、個人・商用問わず自由に利用できます。Pro版は商用ライセンス(購入)となり、利用には定められた料金を支払ってライセンス契約をする形です。Pro版はSeatライセンス(開発者ごとの課金)の予定で、購入すれば組織内で無制限のプロジェクトに使用可能とされています。
価格
具体的な価格は記事執筆時点(2025年11月)では未公開ですが、パフォーマンス向上やサポートへの対価として設定される見込みです。一般的にこの種のライブラリでは月額または年間のサブスクリプション形式も考えられます。公式サイトではPro版のウェイトリスト登録が案内されています。
サポート
無料版はコミュニティサポートが中心となります。GitHubのIssuesやDiscussionsでの質疑応答が主な手段です。一方Pro版では優先サポートが提供され、開発元との直接のやり取りや迅速な不具合対応が受けられるとされています。ビジネスクリティカルなアプリであれば、Pro版のサポート体制は安心材料となるでしょう。
どちらを選ぶべきか?
公式ドキュメントでは、「まずは無料版から使って、必要に応じてPro版にアップグレードする」ことが推奨されています。無料版で全機能が使えるため、ほとんどのプロジェクトではまず無料版で十分です。特にスタイル適用の基本機能やライト/ダークテーマ対応などは無料版で網羅されています。そこからパフォーマンス上のボトルネックを感じた場合や、Reanimated統合などPro専用機能が必要になった場合にPro版を検討すれば良いでしょう。Pro版への移行も、パッケージを追加導入して設定を少し変更する程度で済むよう設計されていると考えられるため、将来的なスケールアップにも対応しやすくなっています。
実践:Uniwindの使い方とサンプルコード – classNameを使ったReact Nativeコンポーネントのスタイリング例
それでは、Uniwindを使ったスタイリングの具体例を見てみましょう。基本的なユースケースとして、背景画像付きのコンポーネントにテキストを重ね、そのスタイルをTailwindクラスで記述するコードを紹介します。
import { ImageBackground, Text } from 'react-native';
<ImageBackground
source={{ uri: 'https://example.com/bg.jpg' }}
className="flex-1 justify-center items-center"
imageClassName="opacity-50"
tintColorClassName="accent-blue-500 dark:accent-blue-700"
>
<Text className="text-white text-2xl font-bold">
Hello, Uniwind!
</Text>
</ImageBackground>
上記の例では、ImageBackgroundコンポーネントに対して以下のようにスタイルを適用しています。
className=”flex-1 justify-center items-center”
これはImageBackground全体のスタイルで、コンテナをflexレイアウトで画面全体(flex-1)に広げつつ、子要素(内部のText)を中央寄せ(縦横ともに中央揃え)しています。これらはTailwind CSSのユーティリティクラスで、複数指定する場合はスペース区切りで列挙します。React Nativeのstyleプロップに相当し、Uniwindがこれらをまとめてスタイルオブジェクトに変換して適用します。
imageClassName=”opacity-50″
こちらはImageBackground特有のプロパティで、内部の背景画像のスタイルに適用されます。opacity-50は不透明度50%(半透明)を意味するTailwindクラスで、背景画像が少し透けて見えるようになります。これは通常のstyleではimageStyleプロップに当たりますが、UniwindではimageClassNameとしてTailwindクラスで指定できるようになっています。
tintColorClassName=”accent-blue-500 dark:accent-blue-700″
こちらもImageBackground固有で、背景画像に被せるTint(着色)をTailwindクラスで指定しています。accent-blue-500はテーマに沿った青色を表すクラスで、dark:accent-blue-700はダークテーマ時にやや濃い青色に切り替えるバリアントです。accent-プレフィックスは「色系プロップにカラー値を適用する」Uniwind独自の書き方で、これによりImageBackgroundのtintColorプロップに適切な色が設定されます。
内部の
このように、UniwindではJSX内に直接Tailwindクラスを書くだけでスタイルを定義でき、複数のクラスもスペースで区切って簡潔に指定できます。また、ユニークなポイントとして、React Nativeの各コンポーネントが持つ個別のスタイル用プロップ(imageStyleやtintColorなど)に対応する「◯◯ClassName」プロップが提供されているため、一部スタイルだけ別途StyleSheetを書く必要がありません。
さらに別の例を挙げると、カスタムCSSクラスを活用したスタイリングも可能です。以下は独自に.cardクラスをCSSで定義し、それをTailwindクラスと組み合わせて使う例です。
/* global.css内 */
.card {
background-color: white;
border-radius: 8px;
box-shadow: 0 2px 4px rgba(0, 0, 0, 0.1);
}
.card-header {
font-size: 18px;
font-weight: bold;
color: #333;
}
// JSX内での使用例
上記では、カード風のレイアウトに必要なボックスシャドウや角丸をCSSで定義し、レイアウト部分(パディングp-4やマージンm-2)をTailwindクラスで補完しています。UniwindのCSSパーサーがこれら独自クラスも解析してくれるため、Tailwindと生CSSをミックスしたスタイリングが可能となっています。
Uniwindのスタイリング方法を解説:classNameやカスタムCSSの活用テクニックを詳しく解説
Uniwindを使いこなすためのスタイリングテクニックを、classNameの使い方とカスタムCSSの活用の観点から解説します。
classNameによる基本的なスタイリング
Uniwindでは、React NativeのコンポーネントにclassNameプロパティを追加することで、ほぼ全てのスタイルをTailwindのユーティリティクラスで指定できます。複数のクラスを指定する場合は、Web開発と同様にスペースで区切るだけです(例:className=”px-4 py-2 bg-green-500 rounded-lg”)。これらはコンポーネントのstyleプロパティに対応しており、内部的にはStyleSheetオブジェクトへと変換されます。React Nativeの<View>や<Text>はもちろん、<Image>, <Pressable>などあらゆる組み込みコンポーネントでclassNameが利用可能です。
Tailwindのバリアント(修飾子)もclassName内で使用できます。例えばdark:を付与すればダークモード時に適用されるスタイルを指定でき、sm:やmd:を使えば画面幅に応じたレスポンシブスタイルを指定できます。React Nativeでは画面幅=デバイス幅となるため、smやmdブレークポイントはデバイスの横幅によって判定されます。Uniwindは画面サイズや画面の向き(縦向き・横向き)を検知し、該当するブレークポイントのクラスを適用してくれます。例えば小さい端末ではsm:bg-red-500が適用され大きなタブレットではmd:bg-blue-500が適用される、といった使い方が可能です(ブレークポイントの閾値はTailwind v4標準の値か、CSSで調整もできます)。
特殊なプロパティへのスタイル: 前述の通り、Uniwindではスタイル用プロパティ以外に対してもTailwindクラスを当てる仕組みがあります。これはaccent-◯◯というプリフィックスで実現されています。例として、
カスタムCSSの活用テクニック
Tailwindには豊富なユーティリティがありますが、プロジェクト固有のデザインシステムや複雑なUI要件において「もう少し細かいスタイル」を書きたくなる場合があります。UniwindはカスタムCSSクラスの定義と利用もサポートしており、以下のようなテクニックが役立ちます。
独自クラスの定義
まずglobal.css内で任意のCSSクラスを定義します。記法は通常のCSSに近いですが、単位指定には注意が必要です。React Nativeでは単位指定が無い数値はデバイス独立ピクセル(dp)と解釈されますが、UniwindのCSSパーサーでは例えば50pxのように書く際は50 pxと半角スペースを入れる書式を採用しています。例として、先述の.cardクラスのように.myBox { margin: 10 px; padding: 8 px; }などと書いておけば、10dpのマージン、8dpのパディングを持つクラスとして認識されます。
コンポーネントへの適用
定義したクラスは、他のTailwindクラスと同様に任意のコンポーネントのclassNameに指定できます。複数指定も可能で、組み合わせた場合はカスタムクラス+Tailwindクラスの両方が適用されます。これにより「カスタムスタイルでベースを作り、レイアウト部分はTailwindで微調整」といった使い方ができます。例えば.btn-primaryクラスで共通のボタンスタイル(背景色や角丸、シャドウなど)を定義しつつ、<Button className="btn-primary px-4 py-2 text-base" />のようにpaddingやフォントサイズ部分はTailwind標準クラスで指定する、というアプローチです。
light-dark関数の活用
Tailwind v4からCSS内で使用できるようになったlight-dark()関数にもUniwindは対応しています。これは2つのカラー値を引数に取り、ライトテーマ時は前者、ダークテーマ時は後者を返す便利なCSS関数です。UniwindのCSSパーサーでもこの関数が使えるため、カスタムCSSクラス内でbackground-color: light-dark(#ffffff, #1f2937);のように書けば、テーマ切替時に背景色を自動的に白⇔ダークグレーで出し分けできます。CSS変数を使わず手軽にテーマ対応させたい場合に有用です。
複雑なセレクタの回避
React NativeではネイティブUIに直接スタイルを当てる関係上、Webのようなネストしたセレクタ(.parent .child { … }など)は使えません。UniwindのCSSでも深いネストや子セレクタの指定は推奨されていないため(パフォーマンス上の理由)、カスタムクラスは1コンポーネントにつき1クラス程度の粒度で使うのがベターです。たとえば複数のテキスト要素に共通のスタイルを付与したい場合、各テキストに同じ.highlightTextクラスを付ける、といった運用をするほうが、1つのクラスで子孫セレクタを通じて全部スタイリングするよりもReact Nativeの思想に沿っています。
これらのテクニックを組み合わせることで、Uniwindはシンプルなユーティリティ指向のスタイリングから必要に応じたカスタムデザインまで幅広くカバーできます。Tailwindの利便性を享受しつつ、従来StyleSheetで書いていたような細かな調整も同じCSS体系で書けるため、スタイル管理の一貫性が保ちやすくなるでしょう。
Uniwindでのテーマ設定とダークモード対応方法:ライト/ダークテーマの切替やカスタムテーマ設定を解説
Uniwindのテーマシステムは、React Nativeアプリでライトモード・ダークモードを簡単に切り替えたり、独自の配色テーマを導入したりすることを可能にしています。ここでは、デフォルトのライト/ダークテーマの使い方と、カスタムテーマの追加手順を解説します。
ライト/ダークテーマの基本と自動切替
Uniwindはデフォルトでlightテーマとdarkテーマを組み込み、さらにsystemテーマ(端末の設定に追従するモード)も備えています。開発者は特別な設定をしなくても、Tailwindのクラスにdark:プレフィックスを付与するだけでダークテーマ時のスタイルを定義できます。例えば、以下のように記述します。
<View className="bg-white dark:bg-gray-900 p-4">
<Text className="text-gray-900 dark:text-white">テーマ対応テキスト</Text>
</View>
この例では、通常時は白背景に黒テキスト、ダークテーマ時はダークグレー背景に白テキストとなります。Uniwindではアプリの現在のテーマ(light/dark)を自動判別して、該当するクラス(dark:が付いたクラス)の適用有無を切り替えてくれます。既定では端末設定に合わせて自動的にライト⇔ダークを切替えるsystemテーマが有効になっており(adaptiveThemesがデフォルトtrue)、ユーザーがOS設定でダークモードにするとアプリも自動でダークテーマになります。
もし明示的に現在のテーマを取得したり切り替えたりしたい場合、UniwindのグローバルAPIを使います。import { Uniwind } from ‘uniwind’でUniwindオブジェクトをインポートし、以下のメソッドを利用できます。
Uniwind.setTheme(‘dark’)
アプリ全体のテーマをダークに変更します。これを呼ぶとsystemによる自動追従が無効化され、以降OS設定に関わらずダークテーマが固定で適用されます。
Uniwind.setTheme(‘light’)
ライトテーマに切り替えます(同様にシステム追従はオフになります)。
Uniwind.setTheme(‘system’)
システム設定追従モードに戻します。これを呼ぶと、端末がダークならダークテーマ、ライトならライトテーマに即座に切り替わり、以降はOS設定の変化を監視して追従します。
また、useUniwind()フックを使うと現在適用中のテーマやシステム追従モードかどうかを取得できます。これを利用して、ユーザーにテーマ選択UIを提供することも容易です。ドキュメントにはThemeSwitcherコンポーネントの例も掲載されており、ボタンでlight/dark/systemをトグルする実装が紹介されています。このようにプログラム的なテーマ変更もUniwindはサポートしているため、ユーザーの選択やアプリの状態に応じて柔軟にテーマを制御できます。
カスタムテーマの追加と利用
デフォルトのライト・ダーク以外に、ブランドカラーに合わせたテーマや特別な配色テーマを追加したい場合は、Uniwindのカスタムテーマ機能を利用します。カスタムテーマは無制限に追加可能で、季節イベント用のテーマや高コントラストなアクセシビリティテーマなども実現できます。
カスタムテーマを作成する手順は2ステップです。
ステップ1: CSSでテーマ変数を定義 – global.cssにて、新しいテーマ名のセレクタを使ってCSS変数に値を設定します。Tailwind v4の@variantディレクティブを用いるのがポイントです。例えば「premium」というテーマを追加する場合、global.cssに以下のように記述します。
@layer theme {
:root {
@variant dark { /* Darkテーマの変数定義 */ }
@variant light { /* Lightテーマの変数定義 */ }
@variant premium {
--color-background: #1e1b4b;
--color-foreground: #fef3c7;
--color-primary: #fbbf24;
--color-card: #312e81;
--color-border: #4c1d95;
}
}
}
上記では:root内に@variant premium { … }を追加し、5つのCSSカスタムプロパティ(色関連)を定義しています。重要なのは、全テーマで同じ種類の変数を定義することです。例では–color-background等5つの変数を既存テーマ(dark/light)にも定義しています。こうすることで、Tailwind側が生成するユーティリティクラス(例えばbg-[var(–color-background)]のようなもの)が全てのテーマで対応するようになります。Uniwindは開発モードで、テーマ間で定義のない変数があれば警告してくれるため、変数漏れを検知できます。
ステップ2: Metro設定でテーマを登録 – 次に、metro.config.jsのUniwind設定に新テーマ名を登録します。先ほどの例なら、withUniwindConfigのオプションにextraThemes: [‘premium’]を追加します。
module.exports = withUniwindConfig(config, {
cssEntryFile: './src/global.css',
dtsFile: './src/uniwind-types.d.ts',
extraThemes: ['premium'] // 追加したテーマ名を登録
});
これでビルド時に新テーマ用のスタイルも生成されるようになります。設定変更後はMetroを再起動してください。
以上で準備完了です。あとはUniwind.setTheme(‘premium’)と呼ぶことでプレミアムテーマに切り替わります。あるいは、ユーザーUIから切り替えさせたい場合は、light/darkと同様に選択肢の一つとして扱えばOKです。なおsystemテーマにしている場合、新しく追加したテーマはシステム設定とは無関係なので、systemを無効化(setThemeでプレミアムを選択)しない限り適用されません。
カスタムテーマ適用時のユーティリティクラスについて補足すると、Tailwind v4ではテーマ変数を用いてユーティリティが生成されます。例えば–color-primaryという変数を定義していれば、Tailwindは.text-primaryや.bg-primaryなどのクラスを自動生成します。したがって、追加したテーマでも既存と同じクラス名でスタイルを共有できます。例えばtext-primaryというクラスはライト・ダーク・プレミアムそれぞれで異なる色を表すようになります(各テーマで–color-primaryに設定した値が適用される)。開発者は特定のテーマ専用のクラスを意識する必要はなく、一貫して.bg-primaryなど共通のクラスを使えば、その時点で選択されているテーマの値に自動で切り替わります。
最後にテーマ切替のUXですが、Uniwindはsystemテーマが有効の場合にOSのテーマ変更を監視して即座に切り替える仕組みがあるため、基本的には端末設定に任せるだけで良いでしょう。しかしユーザー自身がアプリ内でテーマを選べるようにするニーズもあります。その場合は先述のUniwind.setThemeをUIイベント(ボタン押下など)に紐付けるだけです。選択肢として’light’ | ‘dark’ | ‘system’ | ‘premium’ | …と用意すれば、ユーザーは任意のテーマをトグルできます。system以外を選べばOS設定無視で固定になり、再度systemを選べば端末設定追従に戻る、という挙動になります。
以上がUniwindにおけるテーマ設定とダークモード対応の概要です。まとめると、Uniwindでは標準でライト・ダークテーマをサポートし、システム設定とも連携可能、さらにCSS変数ベースでいくらでもカスタムテーマを拡張できる柔軟性があります。これらの機能により、ユーザー環境や好みに応じた多様なスタイル提供が容易になっています。
プラットフォームごとのスタイルカスタマイズ方法:iOS/Android/Webで異なるデザインを適用する
モバイルアプリ開発では、iOSとAndroid間で若干異なるデザインにしたい場合があります。またReact Native Webを利用している場合、Webだけ別のスタイルを当てたいこともあるでしょう。Uniwindはこうしたプラットフォーム固有のスタイル適用を、“プラットフォームセレクタ”という簡潔な文法でサポートしています。
プラットフォームセレクタの基本
Uniwindでは、className内でios:…, android:…, web:…というプレフィックスを使うことで、条件的にスタイルを出し分けできます。使い方はシンプルで、Tailwindクラスにプラットフォーム名とコロンを前置するだけです。例えば:
<View className="ios:bg-red-500 android:bg-blue-500 web:bg-green-500">
<Text className="ios:text-white android:text-yellow-50 web:text-black">
プラットフォーム別スタイルのテキスト
</Text>
</View>
この例では、Viewの背景色がiOSでは赤、Androidでは青、Web(React Native Web)では緑に、それぞれ切り替わります。Textの色もiOSでは白、Androidではやや薄い黄色、Webでは黒、とプラットフォームごとに指定されています。
裏側では、Uniwindが実行時に現在のプラットフォームを判定し、該当するクラスのみを適用する仕組みです。React NativeはデフォルトでPlatform.OSという値(’ios’や’android’など)を持っていますが、Uniwindはそれをラップして、上記のような宣言的な記法でスタイルを記述できるようにしています。
なぜプラットフォームセレクタが便利か
従来、プラットフォーム別のスタイルは以下のように実装していました。
import { Platform, View } from 'react-native';
<View style={ Platform.select({
ios: { backgroundColor: 'red' },
android: { backgroundColor: 'blue' }
}) } />
この方法(Platform.select)は記述が冗長であり、かつ他のスタイルとの組み合わせもしづらいという欠点がありました。Uniwindのプラットフォームセレクタを使えば、上記は単にclassName=”ios:bg-red-500 android:bg-blue-500″と書くだけで済みます。メリットとして:
直感的で簡潔
プロパティを書くようなJSX記法ではなく、既存のclassName文字列に付け足すだけなので可読性が高い。
追加のインポート不要
PlatformAPIをインポートする必要がなくなり、ファイル上部がスッキリします。
他のユーティリティとの併用が容易
例えば
さらに、Uniwindのプラットフォームセレクタはテーマ変数とも組み合わせ可能です。例えばダークモードかつiOSの場合だけ適用するスタイルを.dark:ios:text-gray-200のように書くこともできます。内部的に複雑な条件分岐になりますが、Uniwindが解釈して適切に反映してくれます。
サポートされるプラットフォームと応用例
現時点でUniwindがサポートするセレクタは以下の3つです:
・ios – iOSデバイス(iPhone, iPad)で適用。
・android – Androidデバイスで適用。
・web – Web(React Native Web経由のブラウザ環境)で適用。
この他に将来的にWindowsやmacOS(React Native for Windows/macOS)向けのセレクタ追加も考えられますが、少なくとも上記3種で主要な用途はカバーできます。
具体的な応用例としては、
・iOSとAndroidでフォントの種類やサイズを変える(iOSはサンフランシスコフォントで大きめ、AndroidはRobotoフォントで少し小さめ等)。例:
・プラットフォームごとにコンポーネントの余白を調整する。例えばiOSではデフォルトで安全域(Safe Area)が大きいので余白少なめ、Androidは逆に余白多めにする等。例:
・Web版ではモバイルと違いhoverやfocusの概念があるため、Web向けだけ別のUI要素を表示する/隠す。例えば:
また、Uniwindではグローバルなテーマ変数にもプラットフォーム条件を組み込むことができます。@themeディレクティブ内でCSSメディアクエリのprefers-color-schemeならぬ、@mediaでプラットフォームを判定する仕組みが提供されています。具体的には、CSS内で:
@media ios {
--spacing-base: 16px;
}
@media android {
--spacing-base: 12px;
}
のように書いておくと、Tailwind側で生成されるspacing-base(カスタムユーティリティだとして)の値がiOSでは16、Androidでは12となるような使い方ができます。これは高度な機能ですが、テーマ全体でプラットフォーム差を設けたい場合(例えばiOSは全体的に余白広めで、Androidは狭め、といったデザインポリシー差)がある場合に有用です。もっとも通常はここまでせず、classNameレベルの切替で十分でしょう。
まとめると、Uniwindのプラットフォーム別スタイル機能により、一つのコードベースで各プラットフォームに最適化されたUIを実現できます。if文やStyleSheet分割をすることなく、Tailwindクラスの延長で宣言的にスタイル条件を書ける点で、保守性・可読性も高くなっています。iOS/Androidのデザインガイドラインに沿った調整や、Web版でのレイアウト最適化も容易になるでしょう。
Uniwindに関するよくある質問とトラブルシューティング:よくある疑問点とトラブルへの対処法をQ&Aで紹介
最後に、Uniwindの利用にあたって開発者が抱きがちな疑問点や、遭遇する可能性のあるトラブルとその対処法について、Q&A形式でまとめます。
Q1. NativeWindから移行する際の注意点は? Babelプラグインは必要ですか?
A1. Uniwindへ移行する場合、NativeWind特有の設定を削除する必要があります。まず、Babelのプリセット”nativewind/babel”は不要になるため、babel.config.jsから削除してください。UniwindはBabelに依存せずMetro設定で動作するため、Babelプラグインは不要です。また、tailwind.config.jsも基本的に不要になるので(テーマ変数などはCSSで定義するため)、プロジェクトから削除して構いません。その他、NativeWindの型定義ファイル(nativewind.d.ts)も不要になります。全てのクラスはUniwindが自動生成するuniwind-types.d.tsで型定義されるためです。
Q2. Expoプロジェクトでも本当に動きますか?
A2. はい、Expo(Managed Workflow)でもUniwind無料版は問題なく動作します。Expo Goでも追加ネイティブモジュールなしで利用可能であることが公式に明記されています。セットアップ時にはMetro設定をカスタマイズする必要がありますが(前述の通りmetro.config.jsの編集)、それ以外は通常のReact Nativeと同じです。ただし、Uniwind Pro版はExpo Goに対応しておらず、使用する場合はEASビルドでカスタム開発用クライアントを作成する必要があります。
Q3. 特定のTailwindクラスが効いていないようなのですが?
A3. いくつか確認ポイントがあります。まず、Tailwind CSSのバージョンがUniwind対応のv4になっているか確認してください。v3以前の設定や古いユーティリティは効かない可能性があります。また、クラス名のスペルミスや大文字小文字にも注意してください。Uniwind導入時に生成される型定義uniwind-types.d.tsを見ると、使用可能な全クラスが記載されていますので、そちらでクラス名を検索するとスペルの確認ができます。さらに、global.cssを正しく読み込んでいるかもチェックしましょう。稀にimport ‘./global.css’を忘れていたり、誤ったファイルにインポートしているケースがあります。この場合Tailwindのスタイル自体が適用されません。最後に、Metroバンドラを一度再起動してみることも有効です。新しいクラスを追加定義した場合など、ホットリロードでは反映されず再起動が必要なことがあります。
Q4. Safe Area(画面のノッチやホームバー部分の余白)への対応はどうすれば良いですか?
A4. Uniwind自体には、NativeWindが提供していたようなp-safeやm-safeといったユーティリティクラスはありません。そのため、安全領域の処理はReact Nativeの標準的な方法で行います。具体的には、レイアウトコンポーネントとしてreact-native-safe-area-contextの
Q5. ReanimatedやLayout Animationと併用できますか?
A5. 無料版のUniwindでは、レイアウト変更や色変更を滑らかにアニメーションさせたい場合、基本的には手動でスタイルを操作する必要があります。例えばuseStateでクラス名文字列を切り替えるといったことはできますが、その切替自体は瞬間的に適用されるため、アニメーションさせるにはreact-native-reanimatedのアニメート可能な値にバインドするなどの工夫が要ります。現状、classNameプロパティを直接Animated化する仕組みはありません(NativeWindでも同様です)。ただし、Uniwind Pro版ではReanimated v4対応が予定されており、classNameでのスタイル変更をReanimatedのワークレット内で行えるようになる見込みです。つまり将来的には
Q6. 商用アプリに無料版Uniwindを使っても大丈夫ですか?
A6. はい、無料版UniwindはMITライセンスで提供されており、商用プロジェクトでの利用にも何ら制限がありません。ソースコードの改変や再配布もMITに準拠する形で可能です。開発元も「フリー版はあらゆるプロジェクトに使ってもらって構わない」と明言しています。ただし、公式ドキュメントでも案内されているように、プロジェクトの継続的発展を支えるためにPro版の購入やスポンサーシップといった形で支援を検討してもらえるとありがたい、とのことです。無料版で問題なくとも、もしUniwindによって大きな価値を得ている場合は、開発への還元も検討してみてください。
Q7. テーマをカスタム追加したがうまく反映されません
A7. カスタムテーマを追加したのにUniwind.setTheme(‘テーマ名’)で切り替わらない場合、設定手順の漏れがないか確認しましょう。extraThemesへの登録を忘れていないか、全テーマで変数が定義されているかがポイントです。特に後者、例えば新テーマで–color-brandを定義したなら、light/darkの@variant内にも–color-brandを定義しないとTailwind側でクラスが生成されません。この場合Uniwindは開発中にコンソール警告を出すはずなので見逃さないようにしてください。また、Metroを再起動していない場合も新テーマがビルドに反映されないため、テーマ追加時は再ビルドを行いましょう。
Q8. その他トラブルシューティング: 上記以外にも「クラス名が長大で入力が大変」「旧環境で型エラーが出る」等あるかもしれません。クラス名補完については前述の通りVSCode拡張の設定でかなり改善できます。型エラーに関しては、Uniwind導入後に一度Metroを立ち上げて型定義を生成しないとTypeScriptがクラス名を認識できないため、初回起動時に大量の未定義エラーが出ることがあります。その際はnpm startでMetroを起動→すぐ停止、を行ってuniwind-types.d.tsを生成すると解決します。どうしても解決しない問題がある場合は、公式GitHubのDiscussionsやIssueで質問すると開発者やコミュニティからアドバイスを得られるでしょう。
以上、Uniwindに関するQ&Aをまとめました。新しいライブラリではありますが、ドキュメントも充実しており積極的に開発が続けられています。疑問や不安があれば公式リソースを参照しつつ、安全かつ効率的にUniwindを活用してください。