小程序开发总结
小程序的核心是一个响应式的数据绑定系统,逻辑上分为视图层和逻辑层。这两层始终保持同步,只要在逻辑层修改数据,视图层就会相应的更新。
小程序遵守Convention Over Configuration
的原则,没有留给开发者自由选择的余地。
支付宝小程序和微信小程序的开发框架几乎一模一样,以下代码以微信小程序为例。
包管理
微信小程序使用bower
做模块管理,支付宝小程序使用npm
。
bower.json
1 | { |
运行代码之前需要先把通过包管理工具把远程依赖拉取到本地。
1 | bower init |
APP
调用构造函数——App
可以生成一个APP实例,它除了管理所有的页面和全局数据,还提供生命周期回调函数。
APP入口一般包含三个文件:
- app.js
- app.json
- app.wxss(支付宝是app.acss)
三个文件的作用域是全局,可以在Page中直接访问。
一个APP有且只能有一个
app.js
文件。
页面
调用构造函数——Page
可以生成一个页面实例,页面通过wxml(支付宝是axml)展示数据或提供交互, 数据保存在Page
的data
属性中。
1 | const app = getApp(); // 获取app实例 |
所有的页面位于pages
目录,一个页面对应一个子目录。
页面 address 的目录结构如下所示:
1 | ├── pages |
- js封装了业务逻辑
- json配置了页面属性
- wxml展示页面元素
数据绑定
数据绑定使用Mustache语法(双大括号)将Page
的data
变量包起来绑定(双向)到wxml
元素。
1 | <view> {{ phoneNumber }} </view> |
通过Page#setData
可以自动触发界面数据更新:
1 | onPhoneNumberCleared(e) { |
直接修改
this.data
无效,无法改变页面的状态,还会造成数据不一致
组件
组件是一个可复用的单元,它可以对外提供js、wxml、wxss
wxml格式如下:
1 | <template name="zan_account"> |
在Page中使用组件时,需要分别引入对应的文件。
js@page
1 | const ZanAccount = require('../../../components/zan_account/index') |
require
要使用相对路径
wxml@page
1 | <import src="/components/zan_account/index.wxml" /> |
wxss@page
1 | @import "/components/zan_account/index.wxss"; |
最佳实践
wxss
和wxml
通过import
最终会和page
页面合为一个整体。
template
会被导入到page
的wxml
中,所以它用到的变量只会与page
的data
进行绑定(例如上例中的phoneNumber
)。
为了把组件封装得比较完整,我们需要在组件的js文件中定义好data
以及event
,然后导入到page
的js文件中。
先封装一个合并对象数据的工具函数——extend
:
extend.js
1 | var extend = function(obj) { |
通过extend
函数就可以把多个对象合并成一个Page
对象:
1 | var ZanAccount = require('../../../components/zan_account/index') |
那么组件应该如何定义呢?
因为组件的数据和方法会被合并到Page对象中,因此我们可以把组件分为三个部分:
- data - 数据
- handle - 事件回调
- method - 其他方法
1 | let data = { |
利用Object.assign
函数把属性合并之后导出:
1 | module.exports = Object.assign({}, handle, method); |
CSS
CSS命名规范使用B
lock E
lement M
odifier。
BEM — Block Element Modifier is a methodology that helps you to create reusable components and code sharing in front-end development
对比Android
App
=>Application
Page
=>Activity
getApp
=>getApplication
in activity- 数据绑定 => Data Binding