為什么要講這個主題?
- 實際上是本人1年來多來對小程序技術棧的學習分享(基礎之一)。
- 小程序及其開發模式的持續熱度。
- 作為一個前端或技術人員對新技術的關注。
- 了解一下開發模式,可以類比到我們公司現在及未來的項目。
一、首先你要知道什么是小程序
2017年1月9日,張小龍在2017微信公開課Pro上發布的小程序正式上線。簡單來說,小程序就是一個不需要下載和安裝的應用。只要在“小程序”入口中搜索自己需要的小程序,或者通過掃描小程序碼就能使用它。幾乎任何人和企業、組織都可以擁有屬于自己的小程序。
小程序瞄準的是“輕量級服務”,所以小程序能做到的是“滿足用戶大部分的基礎需求”,因此很多服務類的大企業基本都有屬于自己的小程序,如肯德基、星巴克、農業銀行、摩拜單車等。
小程序主要的優點:
- 不需要下載(不占手機內存)
- 沒有廣告、沒有游戲,用戶可直接體驗等同于APP的功能
- 使用起來比較流暢,不會出現卡頓
- 為很多中小型公司或者節省了開發APP的成本
- 可以捆綁在公眾號上,讓關注公眾號的粉絲體驗。
參考數據:
https://mp.weixin.qq.com/s/t-odsKSbfLkUvANj6AueAA
https://mp.weixin.qq.com/s/hTMzlcjFaEVX_km0sxDrYg
小程序主要的缺點:
- 小程序在微信沒有集中入口。
- 微信不會推出小程序商店,也不會向用戶推薦小程序。
- 小程序沒有訂閱關系,沒有粉絲,只有訪問量。
- 小程序不能推送消息。
- 小程序不能做游戲。
- 用戶均為微信用戶,可以說這些小程序是沒有自己的用戶的。
- 目前只有安卓系統的手機可以添加圖標到桌面
二、HelloWorld
一個完整的小程序頁面包含了以下不同類型的文件:
.json 后綴的 JSON 配置文件
.wxml 后綴的 WXML 模板文件
.wxss 后綴的 WXSS 樣式文件
.js 后綴的 JS 腳本邏輯文件
官方文檔: https://developers.weixin.qq.com/miniprogram/dev/
資料集合: https://mp.weixin.qq.com/s/t-odsKSbfLkUvANj6AueAA
三、開發模式拆解
找一個視角去拆解,即 MVC(Model-View-Controller)。
1. 數據如何獲取
- 通過 HTTPS 請求去服務端獲取數據。
支持 HTTPS 是最基本的,小程序對 HTTPS 有限制,除了要求通信協議是 HTTPS,出現的域名必須提前預設之外,還將應用層協議限定到了 JSON 格式下。這一點,可能比任何一個已有客戶端平臺都更為嚴苛。
- 可以在本地文件系統上存取數據。
小程序提供了豐富的 API 供開發者在手機系統上存取文件。可用本地文件來做緩存、狀態記憶等,為開發提供了便利。
- 可以讀寫設備中的一部分信息。
小程序開放了一些 API,幫助開發者獲得設備上的基本信息,比如手機型號、屏幕尺寸、網絡狀態等。較為有價值的是可以選擇獲取手機上的圖片等多媒體文件,這給做圖像應用提供了可能;并且,它還提供了羅盤、重力感應器、地理位置等信息,對開發者理解用戶所處的環境大有裨益。
官方文檔: https://developers.weixin.qq.com/miniprogram/dev/api/
舉個例子
// 先調用登錄接口,獲得請求碼
wx.login({
success: function (res) {
// 獲取到請求碼,繼續請求用戶的基本信息
var code = res.code
wx.getUserInfo({
success: function (res) {
// 獲取到了加密的用戶信息,去服務端解密并存儲
var userData = res.encryptedData
var iv = res.iv
wx.request({
url: 'https://my_account/...',
data: {
code: code,
user_data: userData,
iv: iv
},
success: function(res) {
// 在服務器上,解析并生成自己的賬號驗證信息
var user = res.data.user
var token = res.data.token
// 并且還可以存在本地存儲上,供下次打開使用
wx.setStorage({
key: 'my_token',
data: token
})
}
})
}
})
}
});
2. 界面如何呈現
在小程序中,和 HTML 對應的是 WXML,保留下來的只有 HTML 的概念,而傳統的<div>、<a>標簽都完全被拋棄了。和 Facebook 的 React 類似,小程序引入了自己的 HTML 標簽,它和 <article〉、<section> 這樣的語義標簽不同,小程序中的標簽更像是傳統客戶端開發中的組件(或者叫控件),每個組件都有自己背后的職能和使用方式。
ReactNative Api: https://reactnative.cn/docs/button/
和 HTML 相比,小程序的 WXSS 算是比較完整地保留了 CSS 的特征。WXSS 在語義上最大的不同,一是在于它支持了相對尺寸單位 rpx(responsive pixel),每 750rpx 等價于當前設備的屏幕寬度,它的引入,把那種繁復的屏幕尺寸適配變得簡單了不少。
小程序中雖然支持 ES6 標準的 JavaScript,但窗口級的 JavaScript 卻完全被廢棄掉了,開發者無法用 JavaScript 去調用 window、document 對象來修改界面元素完成邏輯。
小程序中的 JavaScript 其實直接對應 Node.js 的用法,用來完成后臺業務邏輯,而不是直接控制交互。小程序的這個設計,使其可以用到 Virtual Dom 的方式來渲染界面,讓界面數據更新時的性能優化成為可能,但付出的代價就是少了窗口級 JavaScript 的那層膠水黏合,使得很多功能的開發變得極其呆板和繁復。
官方文檔: https://developers.weixin.qq.com/miniprogram/dev/component/
3. 交互如何傳導
舉個實際的例子,假設開發者需要做一個滑動切換頁面的效果,在小程序中該如何實現?首先,是將變量數據引入渲染頁面:
<view
class="page"
id="current-page"
style="left:{{distance}}rpx;"
bindtouchstart="movePage"
bindtouchcancel="movePage"
bindtouchmove="movePage"
bindtouchend="movePage">
</view>
可以看到,distance 是一個模版參數,它初始值為 0,表示移動的距離。通過 bindtouchstart 等函數綁定上 JavaScript 的方法,將事件回傳。
movePage: function(event) {
var status = {
needUpdate: false,
distance: 0
}
// 處理各種事件,計算是否需要刷新,和移動方向
if ("touchstart" === event.type) {
// 開始計算移動
...
} else if ("touchend" === event.type) {
// 判定移動的距離是否足夠.
...
} else if ("touchcancel" === event.type) {
// 被打斷就算了.
...
} else if ("touchmove" === event.type) {
// 計算移動距離
...
}
// 根據移動的距離,來更新界面
if (status.needUpdate) {
this.setData({
distance: status.distance
})
}
}
而在 JavaScript 一端,則捕獲事件、計算偏移量,然后將新的偏移量送到前端界面。
類似Vue: https://cn.vuejs.org/v2/guide/class-and-style.html#%E7%BB%91%E5%AE%9A-HTML-Class
小結
整體來看,小程序是借了 HTML5 的技術棧,行了傳統客戶端開發的模式,這一點和 React 等平臺會比較相近,可以視為 HTML5 的一個新分支。
從設計思路看,小程序做了大量的“限制”,最大的限制是開發者其實無法通過 JavaScript 這樣的編程語言直接對界面進行控制,而是通過數據驅動來間接實現。這對于缺少開發經驗的人而言,是有益的事情,因為降低了理解的門檻,但對于復雜的應用來說,這個模式開發起來比較呆板,往往是一個變化多處修改,增加了理解代碼的成本。
四、介紹兩款小程序組件化開發框架
Wepy: https://tencent.github.io/wepy/index.html
Mpvue: http://mpvue.com
為什么要選擇框架?
痛點太多
- 頻繁調用
setData
及setData
過程中頁面跳閃- 組件化支持能力太弱(幾乎沒有)
- 不能使用
less、jade
等- 無法使用
NPM
包及ES
高級語法request
并發次數限制- 一個頁面對應4個文件,看的眼花繚亂
......
對比
五、延伸閱讀
WeUI
https://weui.io/
Min小程序UI組件庫
https://github.com/meili/min-cli
在微信小程序里實現圖片預加載組件
https://aotu.io/notes/2017/01/06/wxapp-img-loader/
Weex
http://weex.apache.org/cn/
支付寶小程序的開放能力
https://docs.alipay.com/mini/introduce/auth
百度新發布的智能小程序是什么
https://mp.weixin.qq.com/s/RxBnfplK1kVQ6tcAK7Ablg