动态

详情 返回 返回

Hybrid APP開發實戰(三):uni-app中的nvue - 动态 详情

關注公眾號前端小白菜,更多前端小乾貨等着你喔!公眾號會不定期分享前端技術,每天進步一點點,與大家相伴成長

uni-app App端內置了一個基於weex的原生渲染引擎,提供了原生的渲染能力。

想用JavaScript開發中原生的組件能力,前端有兩種選擇weex和react-native,兩個框架分別依託於vue與react。weex依託於vue,與uni-app的設計理念一致,故而也是uni-app性能優化上的最優選擇。

uni-app與本weex的區別在於uni-app本質上還是運行在webview之上的,説到底還是網頁,而weex提供的是原生的渲染能力,weex實現原理簡單點來説就是將weex組件映射到原生組件上,你寫的是view,實際上渲染的安卓或者IOS的容器組件,故而能擁有近乎原生的渲染能力。

weex原理

放一張比較簡單的weex的架構圖。


圖片來源網絡

看圖説話,不難理解。

1、WEEX通過前端構建能力將vue文件轉換為打包JSBundle文件

2、通過網絡或者是內置的方式加載

3、客户端提供js執行引擎,執行JSBundle文件,生成虛擬DOM

4、WEEX渲染引擎針對不同平台轉換為對應的原生組件。

以上只是淺顯的理解,但大致描述了WEEX能提供原生渲染能力的原因。

NVUE正是借用了WEEX的能力來提升uni-app的渲染能力。雖然NVUE可以提供不錯的原生的能力,但是同時也有不少限制。

NVUE/WEEX的使用場景

純NVUE項目,要想獲得更好的性能,自然是全部使用NVUE最好,uni-app也提供了純NVUE的編譯模式,內部只提供WEEX渲染引擎,打包出來的APP性能更好,安裝包也更小。

提升APP打開速度,混用模式下,推薦首頁使用NVUE開發,uni-app提供fast編譯模式,可以提升APP的加載以及打開速度。

覆蓋原生組件,APP端的導航欄、tabbar、以及一些原生組件(比如VIDEO)無法被覆蓋,頁面內想要覆蓋這些組件就需要用到NVUE。uni-app提供了SUBNVUE功能,SUBNVUE是一個NVUE頁面,具有更高的層級,可以覆蓋所有組件。

使用原生能力,uni-app雖然提供了眾多組件,但是部分組件的部分能力只能在NVUE中使用,比如Input的 confirm-type功能,如果想要定製鍵盤右下角按鈕為“發送”文案,則只能使用NVUE,這個需求在IM即時通訊中最為常見。

NVUE/WEEX的限制

WEEX開發有很多限制,主要表現在CSS的限制上,畢竟不是所有的CSS效果都能映射到原生組件上的。比如:

1、只支持flex佈局,同時uni-app中默認flex排版方向縱向:flex-direction: column;  開發時需要稍加註意,也可以在 manifest.json 中配置 app-plus.nvue.flex-direction: row 來修改。

2、css只支持類選擇器,且不支持嵌套,這意味着你不能寫 #app,也不能寫.app .main 以及其他更多寫法。

3、背景圖無法使用。

4、邊框陰影支持度不足。

5、不能使用typescript,vue本身對ts的支持就比較弱,但現在已經是ts的天下,原生js的書寫的代碼簡直無法維護,自己寫的代碼,過一個月自己都看不懂,ts絕對是前端開發者心目中的白月光。

6、無法訪問Vue.prototype,一個常見的做法是,將vuex示例全局掛載在Vue.prototype上,這樣各個組件中都可以很好的使用vuex。

// main.js
import store from "./store";
Vue.prototype.$store = store;
​
// App.vue
{
  methods: {
    update() {
      this.$store.dispatch('user/update');
    }
  }
}

7、無法訪問全局掛載的組件,類似於Vue.prototype,NVUE中也無法使用全局組件,其原因在於nvue與vue本質上就不一樣,甚至是編譯環境都不一樣,兩者直接無法直接通訊,需要藉助uni-app提供的通訊機制進行通訊。

NVUE的性能提升?

本人NVUE用的不多,性能數據沒有實際測試過,純眼睛測試 ~ 貌似看不出太多的不一樣。但是上面提到的組件覆蓋功能,以及原生組件能力還是需要使用NVUE來實現。 ~~

NVUE開發過程中其實坑不少,除了某些必須使用NVUE來實現的能力外,如果沒有嚴格的性能追求,不太建議使用NVUE,為了那麼點的性能,付出的開發成本可能會更多,此外現在的手機性能都有不錯的性能,差距不大的話根本體驗不出來。

首頁使用NVUE是個不錯的選擇,畢竟是原生渲染,而首頁的渲染速度又關乎着APP的打開速度,APP的打開速度是一個APP的重要衡量標準。原生渲染能力與WEBVIEW的渲染能力越是在性能較差的機器上表現越是明顯。

NVUE全局掛在VUEX?

有同學就要問了,如果我非要在NVUE裏面讀取全局掛在VUEX實例該怎麼辦呢?別急還是有辦法的。

uni-app參考小程序實現了globalData能力,這是一種比較簡單的全局能力,在NVUE中也可以使用,通過這個全局能力,咱們就可以實現NVUE讀取全局VUEX了。

// main.js
import store from "./store";
Vue.prototype.$store = store;
​
// App.vue
export default {
  globalData: {  
    $store: null,  
  },
  async onLaunch() {
    // 坑逼,getApp() 微信報錯,this.$scope h5報錯
    const _app = this.$scope || getApp();
    _app.globalData.$store = this.$store;
  }   
}
// chat.nvue
export default {
  methods: {
    send() {
      const { $store } = getApp().globalData || this;
      $store.dispatch('user/login');
    }
  }
}

想要掛載其他API能力,可以參考以上寫法。如果您有任何想法或疑問可以在下方留言評論探討。

歷史文章閲讀

Hybrid APP開發實戰(一)

Hybrid APP開發實戰(二)

本文首發於本人公眾號,前端小白菜,分享與關注前端技術,歡迎關注~~

前端小白菜

Add a new 评论

Some HTML is okay.