![見出し画像](https://assets.st-note.com/production/uploads/images/146282267/rectangle_large_type_2_087151884d9e2239e935e4f9a43d2c9d.png?width=1200)
React Native の Turbo Native Modules の使い方
前回
1. Turbo Native Modules
「Turbo Native Modules」は、「React Nativeアプリ」と「ネイティブコード」を効率的に連携させるための新アーキテクチャです。
2. ネイティブモジュールの呼び出し
2-1. React Nativeプロジェクトの作成
(1) React Nativeプロジェクトの作成。
npx react-native init my_app
cd my_app
2-2. Androidのネイティブモジュールの実装
(1) AndroidStudioでReact Nativeプロジェクトのandroidフォルダを開く。
(2) ネイティブモジュールの実装。
・MyTurboModule.kt
package com.my_app
import com.facebook.react.bridge.Promise
import com.facebook.react.bridge.ReactApplicationContext
import com.facebook.react.bridge.ReactContextBaseJavaModule
import com.facebook.react.bridge.ReactMethod
// ネイティブモジュール
class MyTurboModule(reactContext: ReactApplicationContext) : ReactContextBaseJavaModule(reactContext) {
// ネイティブモジュール名の取得
override fun getName(): String {
return "MyTurboModule"
}
// デバイス名の取得
@ReactMethod
fun getDeviceName(promise: Promise) {
try {
val deviceName = android.os.Build.MODEL
promise.resolve(deviceName)
} catch (e: Exception) {
promise.reject("Error", e)
}
}
}
(3) ネイティブモジュールをJavaScriptから呼び出せるように設定。
「MainApplication.kt」のPackageListに「MyTurboModulePackage」を追加します。
・MyTurboModulePackage.kt
package com.my_app
import com.facebook.react.ReactPackage
import com.facebook.react.bridge.ReactApplicationContext
import com.facebook.react.bridge.NativeModule
import com.facebook.react.uimanager.ViewManager
// モジュールパッケージ
class MyTurboModulePackage : ReactPackage {
// ネイティブモジュールの生成
override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> {
return listOf(MyTurboModule(reactContext))
}
// ビューマネージャの生成
override fun createViewManagers(reactContext: ReactApplicationContext): List<ViewManager<*, *>> {
return emptyList()
}
}
・MainApplication.ktの一部
override val reactNativeHost: ReactNativeHost =
object : DefaultReactNativeHost(this) {
override fun getPackages(): List<ReactPackage> =
PackageList(this).packages.apply {
// 自動リンクできないパッケージは、ここで手動で追加できる
// example: add(MyReactNativePackage())
add(MyTurboModulePackage()) // ★ここに追加
}
2-3. iOSのネイティブモジュールの実装
(1) podのインストール。
cd ios
pod install
cd ..
(2) Xcodeで「ios」内のworkspaceを開き、署名し、iPhoneにインストールできることを確認。
(3) ネイティブモジュールの実装。
Swiftでネイティブモジュールを実装します。
・MyNativeModule
import UIKit
// ネイティブモジュール
@objc(MyNativeModule)
class MyNativeModule: NSObject {
// デバイス名の取得
@objc
func getDeviceName() -> String {
return UIDevice.current.name
}
}
Swiftコードの初回追加時に、ブリッジヘッダー追加ダイアログが開くので、「Create Bridgin Header」ボタンを押します。「<プロジェクト名>-Bridging-Header.h」が生成され、「Build Settings」の「Objective-C Bridging Header」に設定されます。
![](https://assets.st-note.com/img/1720749839140-QtI6pJIXl3.png)
(4) ネイティブモジュールをJavaScriptから呼び出せるように設定。
<プロジェクト名>にはプロジェクト名を指定してください。
・<プロジェクト名>-Bridging-Header.h
#import <React/RCTBridgeModule.h>
・MyTurboModule.h
#import <React/RCTBridgeModule.h>
@interface MyTurboModule : NSObject <RCTBridgeModule>
@end
・MyTurboModule.m
#import "MyTurboModule.h"
#import <React/RCTLog.h>
#import <<プロジェクト名>-Swift.h>
@implementation MyTurboModule
RCT_EXPORT_MODULE();
RCT_EXPORT_METHOD(getDeviceName:(RCTPromiseResolveBlock)resolve rejecter:(RCTPromiseRejectBlock)reject) {
MyNativeModule *nativeModule = [[MyNativeModule alloc] init];
resolve([nativeModule getDeviceName]);
}
@end
2-4. ネイティブモジュールの呼び出し
(1) ネイティブモジュールの定義。
・MyTurboModule.ts
import { TurboModule, TurboModuleRegistry } from 'react-native';
// ネイティブモジュールの定義
export interface Spec extends TurboModule {
getDeviceName(): Promise<string>;
}
export default TurboModuleRegistry.getEnforcing<Spec>('MyTurboModule');
(2) 「App.tsx」の編集。
・App.tsx
import React, { useState } from 'react';
import { Button, Text, SafeAreaView } from 'react-native';
import MyTurboModule from './MyTurboModule';
// アプリ
const App: React.FC = () => {
const [message, setMessage] = useState('');
// ボタンクリック時に呼ばれる
const onClick = () => {
// デバイス名の取得
MyTurboModule.getDeviceName()
.then((deviceName: string) => {
setMessage(deviceName);
})
.catch((error: any) => {
setMessage(error);
});
};
return (
<SafeAreaView style={{ flex: 1, justifyContent: 'center', alignItems: 'center' }}>
<Text style={{ fontSize: 24, marginBottom: 20 }}>{message}</Text>
<Button
onPress={onClick}
title="デバイス名の取得"
/>
</SafeAreaView>
);
};
export default App;
(3) 実行。
npm start
![](https://assets.st-note.com/img/1720166276654-ND4prYtiEo.png?width=1200)
3. カスタムビューの利用
3-1. React Nativeプロジェクトの作成
(1) React Nativeプロジェクトの作成。
npx react-native init my_app
cd my_app
3-2. Androidのカスタムビューの実装
(1) AndroidStudioでReact Nativeプロジェクトのandroidフォルダを開く。
(2) カスタムビューの実装。
「MainApplication.kt」が存在するフォルダに次のコードを追加します。
・MyCustomView.kt
package com.my_app
import android.content.Context
import android.widget.FrameLayout
import android.widget.TextView
import android.view.Gravity
// カスタムビュー
class MyCustomView(context: Context) : FrameLayout(context) {
init {
val textView = TextView(context).apply {
text = "MyCustomView"
gravity = Gravity.CENTER
}
addView(textView)
}
}
(3) カスタムビューをJavaScriptから呼び出せるように設定。
「MainApplication.kt」のPackageListに「MyTurboModulePackage」を追加します。
・MyTurboModulePackage.kt
package com.my_app
import com.facebook.react.ReactPackage
import com.facebook.react.bridge.NativeModule
import com.facebook.react.bridge.ReactApplicationContext
import com.facebook.react.uimanager.SimpleViewManager
import com.facebook.react.uimanager.ThemedReactContext
import com.facebook.react.uimanager.ViewManager
// カスタムビューマネージャ
class MyCustomViewManager : SimpleViewManager<MyCustomView>() {
override fun getName(): String {
return "MyCustomView"
}
override fun createViewInstance(reactContext: ThemedReactContext): MyCustomView {
return MyCustomView(reactContext)
}
}
// モジュールパッケージ
class MyTurboModulePackage : ReactPackage {
// ネイティブモジュールの生成
override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> {
return emptyList()
}
// ビューマネージャの生成
override fun createViewManagers(reactContext: ReactApplicationContext): List<ViewManager<*, *>> {
return listOf(MyCustomViewManager())
}
}
・MainApplication.ktの一部
override val reactNativeHost: ReactNativeHost =
object : DefaultReactNativeHost(this) {
override fun getPackages(): List<ReactPackage> =
PackageList(this).packages.apply {
// 自動リンクできないパッケージは、ここで手動で追加できる
// example: add(MyReactNativePackage())
add(MyTurboModulePackage()) // ★ここに追加
}
3-3. iOSのカスタムビューの実装
(1) podのインストール。
cd ios
pod install
cd ..
(2) Xcodeで「ios」内のworkspaceを開き、署名し、iPhoneにインストールできることを確認。
(3) カスタムビューの実装。
Swiftでカスタムビューマネージャーを実装します。
・MyCustomViewManager.swift
import UIKit
import React
// カスタムビューマネージャー
@objc(MyCustomViewManager)
class MyCustomViewManager: RCTViewManager {
// 名前の取得
override static func moduleName() -> String! {
return "MyCustomView"
}
// ビューの取得
override func view() -> UIView! {
let view = UIView()
// ラベル
let label = UILabel(frame: view.bounds)
label.text = "MyCustomView"
label.textAlignment = .center
label.translatesAutoresizingMaskIntoConstraints = false
view.addSubview(label)
// 制約
NSLayoutConstraint.activate([
label.centerXAnchor.constraint(equalTo: view.centerXAnchor),
label.centerYAnchor.constraint(equalTo: view.centerYAnchor)
])
return view
}
}
Swiftコードの初回追加時に、ブリッジヘッダー追加ダイアログが開くので、「Create Bridgin Header」ボタンを押します。「<プロジェクト名>-Bridging-Header.h」が生成され、「Build Settings」の「Objective-C Bridging Header」に設定されます。
![](https://assets.st-note.com/img/1720749839140-QtI6pJIXl3.png)
(4) カスタムビューをJavaScriptから呼び出せるように設定。
<プロジェクト名>にはプロジェクト名を指定してください。
・<プロジェクト名>-Bridging-Header.h
#import "React/RCTViewManager.h"
・MyTurboModule.m
#import <React/RCTBridgeModule.h> #import <React/RCTViewManager.h>
@interface RCT_EXTERN_MODULE(MyCustomViewManager, RCTViewManager)
@end
3-4. カスタムビューの利用
(1) カスタムビューの定義。
・MyCustomView.tsx
import { requireNativeComponent, ViewStyle } from 'react-native';
// カスタムビューの定義
interface MyCustomViewProps {
style?: ViewStyle;
}
const MyCustomView = requireNativeComponent<MyCustomViewProps>('MyCustomView');
export default MyCustomView;
(2) 「App.tsx」の編集。
・App.tsx
import React from 'react';
import { SafeAreaView } from 'react-native';
import MyCustomView from './MyCustomView';
// アプリ
const App: React.FC = () => {
return (
<SafeAreaView style={{ flex: 1, justifyContent: 'center', alignItems: 'center' }}>
<MyCustomView style={{ width: "100%", height: "100%" }} />
</SafeAreaView>
);
};
export default App;
(2) 実行。
npm start
![](https://assets.st-note.com/img/1720702619764-bL0rVbiHLh.png?width=1200)
4. デバッグ
Android側のデバッグ出力は、通常のAndroid開発と同様、Log.d()で出力してlogcatで確認します。
androud.util.Log.d("my_app", "A>>>");
adb logcat -s my_app
次回
この記事が気に入ったらサポートをしてみませんか?