搭建環境:https://reactnative.cn/docs/getting-started/,
分mac/win/linux,平臺分android/ios。node
使用rn建立一個項目和把rn技術集成到一個現有的原生項目是有差異的。react
//建立和運行一個rn項目: react-native init AwesomeProject cd AwesomeProject react-native run-ios
編譯和運行須要一段時間...耐心等待..根據rn版本的不一樣,ios虛擬機也不不一樣,好比最新的0.57版本的是iphoneX,低版本的rn默認創造的ios虛擬機就老一點。linux
注意官網中特別提到:android
!!!注意!!!:init 命令默認會建立最新的版本,而目前最新的 0.45 及以上版本須要下載 boost
等幾個第三方庫編譯。這些庫在國內即使FQ也很難下載成功,致使不少人沒法運行iOS項目!!!中文網在論壇中提供了這些庫的國內下載連接。若是你嫌麻煩,又沒有對新版本的需求,那麼能夠暫時建立0.44.3的版本。webpack
我在rn版本0.57.5,react-cli版本2.0.1直接init建立項目沒有遇到以上問題。ios
https://github.com/ZhangMingZhao1/react-native-pratice/tree/master/earphone_guidegit
這裏以一個rn集成到ios object-c爲例,現實中這種狀況可能也更多一些。github
用xcode新建一個單頁面應用,語言選擇object-c,名字爲ReactNativeDemo,在項目根目錄下,新建ReactNative文件夾,用於存放跟reactnative相關文件。(後面簡稱rn)web
在rn文件夾中新建一個package.json,內容爲:npm
{ "name": "ReactNativeDemo", "version": "0.0.1", "private": true, "scripts": { "start": "node node_modules/react-native/local-cli/cli.js start" }, "dependencies": { "react": "16.0.0", "react-native": "0.51.0" } }
注意版本嚴格規定
進入rn文件夾,npm install,在rn文件夾新建index.js,之前版本是inex.ios.js。
內容爲:
import React, { Component } from 'react'; import { AppRegistry, StyleSheet, Text, View } from 'react-native'; class ScoresView extends React.Component { render() { var contents = this.props['scores'].map((score) => ( <Text key={score.name}> {score.name}:{score.value} {'\n'} </Text> )); return ( <View style={styles.container}> <Text style={styles.highScoresTitle}>2048 High Scores!</Text> <Text style={styles.scores}>{contents}</Text> </View> ); } } const styles = StyleSheet.create({ container: { flex: 1, justifyContent: 'center', alignItems: 'center', backgroundColor: '#FFFFFF', }, highScoresTitle: { fontSize: 20, textAlign: 'center', margin: 10, }, scores: { textAlign: 'center', color: '#333333', marginBottom: 5, }, }); // 註冊組件,程序入口 // 第一個參數:註冊模塊名稱,這裏親測不和項目名一致也能夠,可是好多資料說名字要和項目名一致 // 第二個參數:函數,此函數返回組件類名,程序啓動就會自動去加載這個組件 AppRegistry.registerComponent('App', () => ScoresView);
進入項目根目錄,安裝cocoapods,
brew install cocoapods
個人mac下會報個錯,在一個文件下沒有權限寫入,而homebrew如今禁止使用sudo執行,根據提示的指令能夠收回那個文件的權限,複製粘貼執行就好。
安裝好後,在根目錄使用pod init,在生成的Podfile中內容改成:
source 'https://github.com/CocoaPods/Specs.git' react_native_path = './ReactNative/node_modules/react-native' platform :ios, ‘9.0’ use_frameworks! target 'ReactNativeDemo' do # 'node_modules'目錄通常位於根目錄中 # 可是若是你的結構不一樣,那你就要根據實際路徑修改下面的`:path` pod 'React', :path => react_native_path, :subspecs => [ 'Core', #'BatchedBridge', # 0.45 版本之後須要添加 'CxxBridge', 'DevSupport', # 若是RN版本 >= 0.43,則須要加入此行才能開啓開發者菜單 'RCTText', 'RCTImage', 'RCTNetwork', 'RCTWebSocket', # 這個模塊是用於調試功能的 # 在這裏繼續添加你所須要的模塊 ] # 若是你的RN版本 >= 0.42.0,則加入下面這行 pod 'yoga', :path => react_native_path + '/ReactCommon/yoga' # Third party deps pod 'DoubleConversion', :podspec => react_native_path + '/third-party-podspecs/DoubleConversion.podspec' pod 'GLog', :podspec => react_native_path + '/third-party-podspecs/GLog.podspec' pod 'Folly', :podspec => react_native_path + '/third-party-podspecs/Folly.podspec' end
這個文件相似npm的package.json,記錄了所需文件的依賴,因此下一步就是
pod install
在總ios項目中修改http的安全策略,在info.plist加上:
<key>NSAppTransportSecurity</key> <dict> <key>NSExceptionDomains</key> <dict> <key>localhost</key> <dict> <key>NSTemporaryExceptionAllowsInsecureHTTPLoads</key> <true/> </dict> </dict> </dict>
用xcode打開項目,在Main.storyboard拖入一個按鈕,在ViewController.m中加入頭文件:
#import <React/RCTRootView.h>
再增長一個按鈕的跳轉方法:
- (IBAction)pushToReactNativeView:(id)sender { NSURL *jsCodeLocation = [NSURL URLWithString:@"http://localhost:8081/index.bundle?platform=ios"]; RCTRootView *rootView = [[RCTRootView alloc] initWithBundleURL: jsCodeLocation moduleName: @"App" initialProperties: @{ @"scores" : @[ @{ @"name" : @"Alex", @"value": @"42" }, @{ @"name" : @"Joel", @"value": @"10" } ] } launchOptions: nil]; UIViewController *vc = [[UIViewController alloc] init]; vc.view = rootView; [self presentViewController:vc animated:YES completion:nil]; }
可能會出現加載出錯,這是由於pod install安裝的文件沒有加載進來,重啓xcode項目,從新打開項目便可。
而後把ViewController.m文件中的#import <fishhook/fishhook.h> 改成 #import "fishhook.h",否則後面運行可能會報錯。
給這個按鈕和這個方法綁定起來,進入keyboard,按住 ctrl,點擊按鈕會出現一個箭頭,指向左上角的ViewContrller,可出現一個框,選擇剛纔寫的pushToReactNativeView方法,會在右下角看到關聯了。
這部可詳見iOS學習之基礎控件添加和事件綁定,推薦一個連接:https://www.jianshu.com/p/6eb302a62956
進入到rn文件夾,npm start 啓動node服務器,這時會進入dev狀態,動態打包。回到xcode,運行項目,點擊按鈕,就會看到跳轉到rn寫的頁面。
在rn項目根目錄中建立release_ios 文件夾,(打包必須建立文件夾)具體能夠本身命名,做爲資源目標的輸出文件目錄。
在根目錄下執行打包命令:
react-native bundle --entry-file index.js --platform ios --dev false --bundle-output release_ios/main.jsbundle --assets-dest release_ios/
會看到release_ios下多出assets文件夾(若是有圖片),和兩個jsbindle文件.
將main.jsbundle和assets拖入Xcode的項目導航面板中,選擇默認導入便可(位置和裏面的文件夾同級)
修改上面的ViewController,m,
將端口動態引入改成本地,讓React Native去使用咱們剛纔導入的jsbundle,這樣以來咱們就擺脫了對本地nodejs服務器的依賴。固然也能夠將jsbundle 放到本身的遠程服務器中,更換遠程的服務器文件就能夠加載jsbundle,爲了提升性能咱們能夠在本地作一次緩存。@後面是本身打包文件的名字不加後綴。
ios app的打包就能夠看官網了:https://developer.apple.com/support/app-store-connect/