iOS混合開發(fā)-Native&H5模式

Hybrid目前開發(fā)現(xiàn)狀

??目前主要有以下幾種方式的混合開發(fā):

  • Native&H5:
    ??這種模式就是在原生頁面加入H5的頁面,將項(xiàng)目中重復(fù)使用又比較耗時(shí)的部分用H5頁面實(shí)現(xiàn)涌哲,在iOS始衅、Android和H5以及微信公眾號(hào)都可以使用推沸。
    ??優(yōu)點(diǎn):方便快捷,入侵性小,幾乎不改變?cè)鶤PP的框架使用成本較低卦停,容易上手向胡。
    ??缺點(diǎn):效果不如原生流暢,體驗(yàn)比較差沫浆;如果遇到多級(jí)的H5頁面在Native加載,那么實(shí)現(xiàn)的效果往往不如預(yù)期专执。
    ??Native和H5職責(zé)劃分:總的原則是H5提供內(nèi)容,Native提供容器本股。
    ??使用Native的場(chǎng)景——轉(zhuǎn)場(chǎng)動(dòng)畫攀痊、多線程操作(密集型任務(wù))、IO的調(diào)用拄显,當(dāng)然一些安全性比較高的界面苟径,比如:注冊(cè)躬审、登錄界面、支付界面承边。當(dāng)然,有些要考慮到終端性能的問題博助,有些動(dòng)畫H5雖然能夠?qū)崿F(xiàn),但是在低端機(jī)器上效果很差蛔糯,這個(gè)時(shí)候就要考慮用原生實(shí)現(xiàn)了拯腮。
    ??使用H5的場(chǎng)景——基本信息的展示蚁飒,簡(jiǎn)單圖表的展示。一句話總結(jié):H5負(fù)責(zé)需要快速迭代又不使用系統(tǒng)IO交互內(nèi)容的展示狼电。
  • React Native
    ??RN 是什么:就是使用 JS 和 React 來構(gòu)建原生 APP弦蹂。而 RN 并不能算作是 Hybrid,它是通過 JS 來直接調(diào)用原生組件達(dá)到高性能的一種解決方案凸椿。
    ??RN 的優(yōu)點(diǎn):組件化、虛擬DOM脑漫、開發(fā)效率高,性能無限接近原生APP吨拍,當(dāng)然還包括死掉的 HotFix(手動(dòng)捂臉)网杆。
    ??RN 的缺點(diǎn):三方 SDK 開放的 RN 比較少 ,需要自己橋接碳却。如果想要開發(fā)高性能的應(yīng)用队秩,必須了解 Native 開發(fā)昼浦。
  • Cordova
    ??Cordova 是一個(gè)開源的移動(dòng)開發(fā)框架。允許你使用標(biāo)準(zhǔn)的 web 技術(shù)HTML5鸟蟹、CSS3 和 JavaScript 做跨平臺(tái)開發(fā)使兔。應(yīng)用在每個(gè)平臺(tái)的具體執(zhí)行被封裝了起來建钥,并依靠復(fù)合標(biāo)準(zhǔn)的 API 綁定去訪問每個(gè)設(shè)備的功能火诸,比如說:傳感器荠察、數(shù)據(jù)奈搜、網(wǎng)絡(luò)狀態(tài)等。
    ??Cordova 優(yōu)點(diǎn):降低開發(fā)成本馋吗,一次開發(fā)多平臺(tái)套用秋秤,版本更新可動(dòng)態(tài)更新。
    ??Cordova 缺點(diǎn):Cordova的原理就是在原生 APP 上加了一個(gè) WebView灼卢,并提供一套 JS 與原生代碼交互的類庫。交互效果一般鞋真,并且訪問原生控件時(shí)受限。
  • Weex
    ??Weex 是一套簡(jiǎn)單易用的跨平臺(tái)開發(fā)方案海诲,能以 web 的開發(fā)體驗(yàn)構(gòu)建高性能檩互、可擴(kuò)展的 Native 應(yīng)用。Weex 使用 Vue 作為上層框架闸昨,并遵循 W3C 標(biāo)準(zhǔn)實(shí)現(xiàn)了統(tǒng)一的 JSEngine 和 DOM API。
    ??Weex 優(yōu)點(diǎn):輕量級(jí)溉跃,簡(jiǎn)單的 DSL 語言易于上手;擴(kuò)展性好撰茎,可以對(duì)網(wǎng)絡(luò)打洼、圖片、存儲(chǔ)募疮、UT、組件他嚷、接口等根據(jù)自身 APP 和業(yè)務(wù)需求進(jìn)行擴(kuò)展;組件化筋蓖,Weex 本身編寫的界面就天然的支持組件化,同事支持大部分組件蚣抗;開發(fā)成本較低瓮下。
    ??Weex 的缺點(diǎn):Bug 很多,作為新推出的解決方案讽坏,Weex 還有很多需要改進(jìn);社區(qū)的規(guī)模較小路呜,知名度也相對(duì)較低。

Native&H5使用實(shí)例

  • WKWebViewJavascriptBridge 關(guān)聯(lián) WKWebView
    ??我們使用了 WKWebViewJavascriptBridge 這個(gè)優(yōu)秀的第三方庫來橋接 WKWebView 和 H5党涕。
lazy var webView: WKWebView = {
    let temp = WKWebView()
    temp.isOpaque = false
    temp.uiDelegate = self
    temp.navigationDelegate = self
    temp.addObserver(self, forKeyPath: "estimatedProgress", options: NSKeyValueObservingOptions.new, context: nil)
    return temp
}()

lazy var webViewBridge: WKWebViewJavascriptBridge = {
    let temp = WKWebViewJavascriptBridge.init(for: webView)
    
    temp?.setWebViewDelegate(self)
    return temp!
}()
  • registerHandler
    ??我們通過 webViewBridge 注冊(cè) handle 綁定相應(yīng)的事件巡社,這樣 H5 可以通過這個(gè)事件告訴 APP 進(jìn)行相應(yīng)的操作和傳遞數(shù)據(jù)。以此實(shí)現(xiàn) H5 與 APP 的交互肥荔。
//注冊(cè)一個(gè)如果Token過期朝群,H5通過注冊(cè)的事件告訴Native
func registTokenHandle() {
    webViewBridge.registerHandler("tokenDisabled") { (data, responseCallBack) in

    //這里是登錄失效的代碼
        
    }
}
  • WKWebView-UserAgent設(shè)置
    ??要區(qū)分打開的 H5 是本地 APP 還是在手機(jī)的瀏覽器,就要修改默認(rèn)的 UserAgent
func setupUserAgent() {
    let webView = UIWebView()
    if var newUserAgent = webView.stringByEvaluatingJavaScript(from: "navigator.userAgent"){
        newUserAgent.append(" XXX-iOS")
        let dic = ["UserAgent": newUserAgent]
        UserDefaults.standard.register(defaults: dic)
    }
}
  • 進(jìn)度條和title
    ??通過 WKWebView可以很方便的使用 addObserver 來 設(shè)置進(jìn)度條和 捕獲 H5 的title給 Native 的頁面誉帅。
    ??進(jìn)度條:
//1 設(shè)置 observer
temp.addObserver(self, forKeyPath: "estimatedProgress", options: NSKeyValueObservingOptions.new, context: nil)
//2 設(shè)置代理
class YourWebViewController: WKUIDelegate,WKNavigationDelegate{}
//3 實(shí)現(xiàn)代理方法
override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
    if keyPath == "estimatedProgress",
        (object as? WKWebView) == webView{
        let progress = Float(self.webView.estimatedProgress)
        progressView.setProgress(progress, animated: true)
        if progress >= 1.0 {
            UIView.animate(withDuration: 0.3, delay: 0.1, options: .curveEaseOut, animations: {
                self.progressView.alpha = 0
            }, completion: { (finish) in
                self.progressView.setProgress(0.0, animated: false)
            })
        }else{
            self.progressView.alpha = 1
        }
    }
}
//4 記得 removeObserver
deinit {
    self.webView.removeObserver(self, forKeyPath: "estimatedProgress")
}

??捕獲H5 的 Title:

//1 設(shè)置 observer
wkWebView.addObserver(self, forKeyPath: "title", options: NSKeyValueObservingOptions.new, context: nil)
//2 設(shè)置代理
class YourWebViewController: WKUIDelegate,WKNavigationDelegate{}
//3 實(shí)現(xiàn)代理方法
override func observeValue(forKeyPath keyPath: String?, of object: Any?, change: [NSKeyValueChangeKey : Any]?, context: UnsafeMutableRawPointer?) {
    if keyPath == "title",(object as? WKWebView) == webView{
        webViewTitle = self.webView.title
    }else{
        super.observeValue(forKeyPath: keyPath, of: object, change: change, context: context)
    }
}
//4 記得 removeObserver
deinit {
    self.webView.removeObserver(self, forKeyPath: "estimatedProgress")
}
  • 代碼重構(gòu)
    ??一兩個(gè) WebView 的頁面可以隨意些蚜锨,但是如果項(xiàng)目中很多頁面都通過 H5 實(shí)現(xiàn)慢蜓,那么我們就要統(tǒng)一規(guī)范配置需要跳轉(zhuǎn)的 URL亚再。
class YourJSBridge: NSObject {
    
    static let baseUrl = YourAppManager.baseH5URL
    
    var baseUrl: String{
        return YourJSBridge.baseUrl
    }
    
    struct Event {
        static let successButtonClick = "successButtonClick"
    }
    
    struct Path {
        static let yourUrlPath = "yourUrlPath"
    }
    
    struct Url {
        static func successMethod(parame successStr: String) -> String{
            return baseUrl.your_appendingPathComponent(Path.yourUrlPath).token.parameter(key: "successStr", value: successStr)
        }
    }
}

fileprivate extension String{
    var token: String{
        let token = YourManager.shared.token?.token ?? "---"
        return self+"?token=\(token)"
    }
    
    func parameter(key: String,value: Any) -> String{
        return self+"&\(key)=\(value)"
    }
    
    func your_appendingPathComponent(_ path: String) -> String{
        return self+"/"+path
    }
}

參考鏈接:

Hybrid APP架構(gòu)設(shè)計(jì)思路
iOS原生混合RN開發(fā)最佳實(shí)踐
weex&ReactNative對(duì)比
RN 系列之--什么是 ReactNative
Weex在達(dá)人店的一年實(shí)踐
淺談一款移動(dòng)端開發(fā)框架Weex

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末则剃,一起剝皮案震驚了整個(gè)濱河市如捅,隨后出現(xiàn)的幾起案子棍现,更是在濱河造成了極大的恐慌伪朽,老刑警劉巖汛蝙,帶你破解...
    沈念sama閱讀 207,248評(píng)論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異坚洽,居然都是意外死亡西土,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,681評(píng)論 2 381
  • 文/潘曉璐 我一進(jìn)店門跳昼,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人鹅颊,你說我怎么就攤上這事墓造。” “怎么了觅闽?”我有些...
    開封第一講書人閱讀 153,443評(píng)論 0 344
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)尸闸。 經(jīng)常有香客問我孕锄,道長(zhǎng),這世上最難降的妖魔是什么硫惕? 我笑而不...
    開封第一講書人閱讀 55,475評(píng)論 1 279
  • 正文 為了忘掉前任,我火速辦了婚禮踪旷,結(jié)果婚禮上,老公的妹妹穿的比我還像新娘令野。我一直安慰自己,他們只是感情好气破,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,458評(píng)論 5 374
  • 文/花漫 我一把揭開白布现使。 她就那樣靜靜地躺著低匙,像睡著了一般碳锈。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上强重,一...
    開封第一講書人閱讀 49,185評(píng)論 1 284
  • 那天贸人,我揣著相機(jī)與錄音,去河邊找鬼艺智。 笑死,一個(gè)胖子當(dāng)著我的面吹牛力惯,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播哮缺,決...
    沈念sama閱讀 38,451評(píng)論 3 401
  • 文/蒼蘭香墨 我猛地睜開眼甲喝,長(zhǎng)吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來了埠胖?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 37,112評(píng)論 0 261
  • 序言:老撾萬榮一對(duì)情侶失蹤非竿,失蹤者是張志新(化名)和其女友劉穎谋竖,沒想到半個(gè)月后承匣,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體锤悄,經(jīng)...
    沈念sama閱讀 43,609評(píng)論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 36,083評(píng)論 2 325
  • 正文 我和宋清朗相戀三年袍暴,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片政模。...
    茶點(diǎn)故事閱讀 38,163評(píng)論 1 334
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡沿腰,死狀恐怖狈定,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情纽什,我是刑警寧澤,帶...
    沈念sama閱讀 33,803評(píng)論 4 323
  • 正文 年R本政府宣布企巢,位于F島的核電站让蕾,受9級(jí)特大地震影響浪规,放射性物質(zhì)發(fā)生泄漏探孝。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,357評(píng)論 3 307
  • 文/蒙蒙 一缸濒、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧庇配,春花似錦绍些、人聲如沸捞慌。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,357評(píng)論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽锻霎。三九已至,卻和暖如春旋恼,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背冰更。 一陣腳步聲響...
    開封第一講書人閱讀 31,590評(píng)論 1 261
  • 我被黑心中介騙來泰國(guó)打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留蜀细,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 45,636評(píng)論 2 355
  • 正文 我出身青樓谆刨,卻偏偏與公主長(zhǎng)得像归斤,于是被迫代替她去往敵國(guó)和親痊夭。 傳聞我的和親對(duì)象是個(gè)殘疾皇子脏里,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,925評(píng)論 2 344