React Native導入ガイド - 環境構築からクロスプラットフォーム開発のメリットまでを理解する

React Nativeは、クロスプラットフォーム開発を行うためのツールの1つです。JavaScript言語の中で、UIフレームワークのReactを用いてUIの記述と状態管理を行うことで、アプリの動作を組み立てます。本記事では、React Nativeの導入やモバイルアプリ開発の現場で起きがちな課題を解決する手段としての強みについて解説します。

React Native導入ガイド - 環境構築からクロスプラットフォーム開発のメリットまでを理解する

ReactとReact Native
Reactとは/React Nativeとは/React Nativeの正体
React Nativeの環境構築
npm文化圏の流儀にのっとったワークフロー/スタイル定義/npmのライブラリ使用/リッチな機能を追加
広がるReact Nativeの世界
Windows向けのMS公式実装/ブラウザ向けの逆輸入/React Nativeが持つUIの妥当な粒度
React Nativeを軸にした人材戦略
日本のサービス提供者が抱える宿命/増員は茨の道/限られた人数での開発/React Nativeの得意分野と課題/腕力のある器用な人を活かす

プラットフォーム間でソースコードを共有したり、共通の方法論で複数のプラットフォーム向けのアプリを作成したりするための開発手法のことを、クロスプラットフォーム開発と呼びます。React Nativeは、そのクロスプラットフォーム開発を行うためのツールの1つです。JavaScript言語の中で、UIフレームワークのReactを用いてUIの記述と状態管理を行うことで、アプリの動作を組み立てます。

React Nativeの特性をよく理解し、うまく特性にマッチした事業や組織で採用すれば、モバイルアプリ開発の現場で起きがちな課題を解決する手段としてその能力を十全に発揮できます。本記事では、React Nativeの導入、モバイルアプリ開発・人材戦略のためのReact Nativeの強みについて解説します。

ReactとReact Native

まずは、ReactとReact Nativeについて解説しておきましょう。

Reactとは

Reactは、Facebookが開発している、JavaScriptのためのUI管理フレームワークです。基本的にはブラウザ向けのWebアプリケーションの開発に使用されています。

1

2React – ユーザインターフェース構築のための JavaScript ライブラリ

その特徴は大きく分けて2つあります。特殊な記法を用いて、JavaScriptコード内にUIを記述する JSX と、JSXを組み合わせて作成したUIの部品である コンポーネント です。

それぞれ、Reactを使ってUIを作っていくためのパワフルな仕組みです。個別に解説していきましょう。

【Reactの構成要素1】JSXについて

JSXは、JavaScriptコードの中にレイアウトを記述できるようにFacebookが考案した、XMLライクな記法です。以下のページで仕様が公開されています。

ReactでUIを構築する上で、JSXの使用は必須ではありません。しかし、どのようなレイアウトになるのかを想像しやすくなるため、使用が推奨されています。

JSXの簡単な例を挙げてみましょう。Reactでアプリケーション開発を行う際には、以下のようなコードを書くことができます。

import React from 'react';
import { Text } from 'react-native';
import render from './render';

const greeting = <Text>Hello!</Text>;

render(greeting);

式として書かれた <Text> というタグ要素で文字が囲まれているので、どうやら画面に「Hello!」というテキストが表示されそうだ、ということが想像できますね。ですが、「JavaScriptにそんな文法あったっけ?」と思った方もいるはずです。

その通り、JavaScriptの中にはJSXのようなタグ要素を書くことはできません。一度、JSXが書かれたJavaScriptをコンパイルして、JavaScriptとして正しいコードに変換する必要があります。変換には、JavaScriptコンパイラのBabelを用います。

上記の例は、Babelによる変換を行うと、以下のようなコードになります。

import React from 'react';
import { Text } from 'react-native';
import render from './render';

const greeting = React.createElement(Text, null, "Hello!");

render(greeting);

これで、JavaScriptの処理系が読み込めるコードになりました。

実は React.createElement をひたすら並べることでも、Reactを用いたUIの構築はできます。とはいえ、UIの構造を定義するならばXMLライクな記法があったほうが便利なので、JSXの使用が推奨されているのです。

【Reactの構成要素2】コンポーネントの作成

Reactを用いたアプリケーション開発では、再利用可能な画面部品である、 コンポーネント を作成し、これらを組み合わせてUIを構築します。コンポーネントは、JavaScriptのクラスまたは関数として作成できます。本記事では関数での作り方を紹介します。

では、コンポーネントの作り方を見ていきましょう。 ViewText といった基底のコンポーネントの役割については後述しますが、この時点ではレイアウトを区切ったり、テキストを表示したりできる機能を持ったタグだと思っておいてください。コンポーネントの例を示します。

import React from 'react';
import { View, Text } from 'react-native';

// (1)
const Greeting = (props) => {
  return (
    <View>
      <Text>Hello! {props.name}</Text>{/* (2) */}
    </View>
  );
};

// (3)
const App = () => {
  return (
    <View>
      <Greeting name={"Taro"} />{/* (4) */}
      <Greeting name="Jiro" />{/* (5) */}
      <Greeting name="Hanako" />
    </View>
  );
};

export default App;

コンポーネントは慣例として、(1)のようにパスカルケースで名前を付けます。また、関数で作成する場合はprops(プロップス)と呼ばれる引数を渡すことができ、(2)のようにJSXの中で使用できます。文字列として式を展開する場合は {props.name} のように波括弧で囲みます。

こうして作成した Greeting コンポーネントを、(3)の App コンポーネントで使います。コンポーネントはJSXのタグ要素として使用することができます。また、何度でも再利用が可能です。

関数の引数になっていたpropsに値を渡したい場合は、(4)のような形で、属性として値を与えます。この属性は {} で値を囲むのが本来の書き方ですが、文字列を渡すだけの場合は(5)のように {} を省略することもできます。

このようにコンポーネントを組み合わせることで、ReactによるUI構築が行われます。

React Nativeとは

React Nativeは、Facebookが開発している、モバイルアプリ開発のための各種ツール群の総称です。

2015年にReact Nativeが発表されるより少し前に、WebViewを活用した「ハイブリッドアプリ」が市民権を得ていく過程で、各プラットフォームの本来のUIを「ネイティブUI」と呼ぶ文化が一部に生まれました。そういった時代背景から、Reactフレームワークを通じてネイティブUIを扱うためのツールは「React Native」と名付けられたのでした。機械語をネイティブコードと呼ぶ文化を連想してしまいますが、まったくの別物です。

3

4React Native · A framework for building native apps using React

react-native パッケージから提供されるコンポーネントを組み合わせてUIを作成すると、AndroidとiOSのどちらでも動かすことができます。

試しに、前述のコードを動かしてみましょう。少しだけスタイル情報も加えてみます。

import React from 'react';
import { View, Text, StyleSheet } from 'react-native';

const Greeting = (props) => /*省略*/;

const App = () => {
  return (
    <View style={styles.container}>{/* (2) */}
      {/*省略*/}
    </View>
  );
};

export default App;

// (1)
const styles = StyleSheet.create({
  container: {
    flex: 1,
    alignItems: 'center',
    justifyContent: 'center',
  },
});

(1)では、 StyleSheet モジュールを使って、 container という名前のスタイルを定義しました。ここではCSSに準拠した記述ができるので、今回はCSS 3で導入されたレイアウト指定の仕様であるFlexboxの各種プロパティを使って、「自身は画面いっぱいに広がりつつ、中身は上下中央寄せになる」という指定を行いました。これを(2)で View コンポーネントのスタイルとして適用しています。

これを実行した結果が以下です。

5
(左)iOSで実行した様子 (右)Androidで実行した様子

iOSとAndroidそれぞれで、指定した通りに、画面中央にテキストが表示されています。

このようにReact Nativeでは、1つのソースコードを複数のプラットフォームで動かすことができるのです。

代表的なコンポーネントとモジュール

React Nativeでは、モバイルアプリを開発する上で最低限必要になるUIコンポーネントが、ちょうど良い粒度で提供されています。代表的なコンポーネントとして、以下のようなものがあります(表1)。

コンポーネント名 役割
View レイアウトを区切るための基本単位
Text テキストを表示・装飾する
ActivityIndicator 処理待ち
FlatList 配列データを省メモリで並べる
ScrollView 内側のコンテンツが画面をはみ出たらスクロールする
RefreshControl 「引っ張って更新」を付与する

▲表1:代表的なコンポーネント

また、UIとは関係なく、プラットフォームの機能を活用するために、モジュール群も提供されています(表2)。

モジュール名 役割
Alert 簡易なダイアログ表示をする
Dimensions 画面サイズやアプリの表示領域のサイズを取得する
Keyboard キーボードに関する情報を提供する
Animated アニメーションを扱う
StyleSheet コンポーネントに適用するスタイルを管理する
Geolocation 現在地の地理空間情報を取得する(window.navigator.geolocationとして提供)
Fetch 通信を行う(window.fetchとして提供)
Console デバッグログを表示する(window.consoleとして提供)
Require NPMモジュールや別のファイルとして定義されたモジュールを取り込む(window.requireとして提供)

▲表2:代表的なモジュール

これらの機能を活用することによって、実用的なアプリを作れます。

標準ライブラリはブラウザに準拠

React Nativeの標準ライブラリは、基本的にブラウザに準拠したものになっています。 setTimeoutfetch などブラウザでよく使われているAPIで、アプリ開発ができるのです。このおかげで、ブラウザやNode.js向けに作られたライブラリのうち何割かはReact Nativeでもそのまま利用できます。

ただし、後述するようにDOMでビューの管理をしているわけではないので、 document をはじめとしたDOMを扱うためのグローバル変数は提供されていません。あくまでもReactが持つ標準的な仕組みの範囲で、UIを更新していくことになります。こういった点でいうと、jQueryなどでDOMを操作することに慣れている方は、慣れるまでに少し時間がかかるかもしれません。

React Nativeの正体=Reactとスマホアプリのつなぎ役

JavaScriptで記述したHTMLライクなレイアウトが、実際に画面に表示されるのを見て、まず生じる疑問は「これは、ブラウザをアプリ内に組み込む仕組みであるWebViewではないのか?」だと思います。

しかし、React NativeはWebViewではありません。React Nativeは、JavaScript内に定義されたレイアウトを、各プラットフォームのUIコンポーネントに翻訳して描画します。

6
UIコンポーネントが翻訳される

JavaScript側で <ScrollView> というReactコンポーネントを記述した場合に、Androidでは ScrollView 、iOSでは UIScrollView に翻訳されます。React NativeがJavaScriptライブラリとして提供しているすべてのReactコンポーネントは、各プラットフォームの何らかのビューに翻訳されるのです。

2つのレイヤー「UIライブラリ層」「ミドルウェア層」

React Nativeは、次の2つのレイヤーが連携することで成り立っています。

  • UIライブラリ層
  • ミドルウェア層

React Native製のアプリを以下のように図示すると、その立場がわかりやすいかもしれません。

7

AndroidアプリやiOSアプリである以上、画面をつかさどるクラスである ActivityUIViewController は必ず存在しています。そういった「普通のAndroid/iOSアプリ」と呼ぶべき部分と、これまで解説してきたReactコンポーネントの組み合わせでできている「React製アプリ」の部分。この2つの間を埋めるのが、React Nativeです。

UIライブラリ層 は、JavaScriptライブラリとして提供されています。JavaScriptコード内で import { ... } from 'react-native'; の形で読み込まれるものがこれに当たります。主に <View><Text> といったReactコンポーネントを提供します。

一方で、 ミドルウェア層 は、私たちが書いたReactコンポーネントや、前述のUIライブラリ層を動作させるための、あらゆる努力を行います。主に次の部分から成り立っています。

  • JavaScriptの動作環境(JavaScriptCore)
  • JavaScript側でUIライブラリが利用された際に、各プラットフォームのUIに翻訳する、C++と(Java | Objective-C)で作られたミドルウェア

Android開発出身の筆者がReact Nativeに惚れ込んだのは、後者のミドルウェア部分(のAndroid向けJava実装)のコードを読んだ際に、筆者にも読めるくらいに複雑過ぎないコードで実現されていて感動したのがきっかけでした。また、このミドルウェア層はネイティブモジュールという仕組みを用いて自分で拡張したり、自作のUIコンポーネントを組み込んだりできます。Android SDKやiOS SDKでの開発に慣れ親しんだ人であれば作成が難しくないのも、魅力的な点です。

React Nativeの魅力は「ブラウザらしさ」と「Android/iOSアプリらしさ」の二面性

React Nativeは、Reactによるブラウザアプリ開発とAndroid/iOSアプリ開発の、いわば“いいとこ取り”をしたような特色を持っています

JavaScriptのエンジンはSafariのものを借りてきていますし、標準ライブラリもブラウザに実装されているものの多くを再現しています。Reactで使えるコンポーネントも、ブラウザとは少しラインアップが違うものの、慣れればブラウザアプリを作る時と近い感覚で、自作のコンポーネントを素早く組み立てていくことができるでしょう。React Nativeは、JavaScriptエンジニアにとって「クセの強いブラウザ」と見なすことができると、筆者は考えています。

その一方で、視点を変えてみると、React NativeはAndroidの Activity やiOSの UIViewController の上で、ネイティブUIを描画しているという側面があります。JavaScriptやReactという特殊なUI記述言語を読み込んで、更新指示を受け取ることができる……そんな特殊能力を持った FrameLayoutUIView で作られたUIライブラリとしてReact Nativeを捉えることもできます。AndroidやiOSでのアプリ開発に慣れた方には、こちらの方がしっくりくるかもしれません。

基本的には「クセの強いブラウザ」として見なして開発を行い、Android/iOSのプラットフォーム機能を使いたくなった場合は、Android SDKやiOS SDKの助けを借りて「ブラウザ」の機能を拡張できる。そんな開発スタイルが、React Nativeには適しています。

それでは、実際の開発の流れを追いながら、ブラウザアプリ開発と近い感覚でできる部分や、ネイティブUIで拡張できることの強みについて、見ていきましょう。

React Nativeの環境構築

React Nativeでの開発を行う場合、事前に以下の環境をセットアップする必要があります。

  • AndroidアプリのHello Worldができる環境(JDKやAndroid Studioのインストールなど)
  • iOSアプリのHello Worldができる環境(XcodeやCocoaPodsのインストールなど)
  • Node.jsの実行環境

ここの環境を全てそろえようとすると難易度が高めになります。もし実際にセットアップから試してみたい方は、公式ドキュメントの"React Native CLI Quick Start"の項に、より詳しい解説がありますので、そちらをお読みください。

npm文化圏の流儀にのっとったワークフロー

エンジニアHubに会員登録すると
続きをお読みいただけます(無料)。
登録のメリット
  • すべての過去記事を読める
  • 過去のウェビナー動画を
    視聴できる
  • 企業やエージェントから
    スカウトが届く