微信小程序
- 开发事项
- 页面的展示;
- 页面上的用户交互事件;
- 页面间的切换逻辑;
- 数据存储与网络调用;
- 前端架构
- service:业务逻辑层,按业务类型整合相关的方法,向上暴露接口,降低表现层对业务逻辑的关注;
- pages:表现层,一个页面一个文件夹,放置这个页面涉及的资源;
- common:放置一些和项目相关的公共代码,如转码,工具包,公共样式设置等;
- lib:放置一些最底层、第三方的库;
- widgets:一些通用的带UI的小组件,独立闭环的交互;
- 项目目录
- 全局
- app.js:小程序的全局脚本文件,用来监听并处理小程序的生命周期函数,声明全局变量,调用API等;
- App({
- onLaunch: function( ){ }, //启动时的初始化操作
- onShow: function( ){ }, //从后台进入前台的操作;
- onHide: function( ){ }, //从前台进入后台的操作
- globalConf: {
- indexDate: ‘’,
- matchDate: ‘’
- }
- globalData: ‘’
- )}
- App({
- app.json:小程序的全局配置文件,会被页面继承;当页面有设置自己的配件文件时,则以页面自己的为准;
- app.wxss:全局样式文件;
- app.js:小程序的全局脚本文件,用来监听并处理小程序的生命周期函数,声明全局变量,调用API等;
- 页面
- pages
- page1
- page1.js
- Page({
- data: {}, //页面数据
- onLoad: function( ){ }, //页面加载时的初始化操作;
- onReady: function( ){ }, //加载就绪后的操作;
- onShow: function( ){ }, //页面打开时的操作;
- onHide: function( ){ }, //页面隐藏时的操作;
- onUnLoad: function( ){ }, //页面关闭时的操作;
- viewTap: function( ){ //页面元素事件触发的操作;
- this.setData({
- test: ‘set some data for updating now’
- })
- }
- this.setData({
- Page({
- page1.json
- page1.wxss
- page1.js
- page2
- …(略)
- page1
- pages
- 全局
- 两个开发步骤
- 创建实例:即编写3个 app 前缀的文件,定义、配置及页面执行关联;
- 创建页面:编写页面结构与事务处理逻辑;
- MIMA架构示意图
1. - 结构
- 页面层
- 逻辑层
- 数据层
- 页面临时数据或缓存:在 Page( ) 中,使用 setData 函数,将数据从逻辑层发往视图层;
- 文件存储(本地存储),使用以下3个API:
- wx.getStorage:获取本地数据缓存;
- wx.setStorage:设置本地数据缓存;
- wx.clearStorage:清除本地数据缓存;
- 网络存储和调用
- wx.request:发起网络请求;
- wx.uploadFile:上传文件
- wx.downloadFile:下载文件;
- wx.navigateTo:新窗口打开新页面;
- wx.redirectTo:原窗口打开新页面;
- 开发流程
- 配置
- 全局配置:app.json
- 页面配置:page.json
- 逻辑层
- 注册程序:app( ) 方法
- 注册页面:page( ) 方法
- 模块化
- 将一些公共的代码抽离一个或多个单独的 js 文件,作为一个模块;
- 模块通过 module.exports 对外暴露接口以供其他 js 文件引入使用,示例如下:
- // common.js
- function sayHello(name) {
- console.log(‘Hello ‘ + name + ‘!’)
- }
- module.exports = {
- sayHello: sayHello
- }
- function sayHello(name) {
- // call.js 引用的文件
- var common = require(‘common.js’)
- Page({
- helloMIMA: function( ){
- common.sayHello(‘MIMA’) //使用的场景;
- }
- helloMIMA: function( ){
- // common.js
- 微信的原生 API
- 八大类:网络、媒体、文件、数据缓存、位置、设备、界面、微信开放接口;
- API 的名字如果以 on 开头,例如 wx.onSocketOpen,表示监听某个事件发生,它接受一个回调函数为参数,当事件触发时,会调用这个回调函数;
- 其他 API 接口接受一个 Object 对象做为参数,这个对象可以指定 success、fail、complete 三个参数,参数值为函数,分别代表接口调用成功、失败、完成后要执行的回调函数;
- 视图层
- WXML
- 数据绑定
- 简单绑定
- 运算:
三元运算{{ flag? true : false }}、算数运算{{ a + b }}、逻辑判断{{ length > 5 }}、字符串运算{{ "hello" + name }}、数据路径运算{{ object.key }}, {{ array[0] }}
; - 组合:在花括号内组合元素,组成新的数组或对象、支持扩展运算符展开对象
1
{{[ zero, 1, 2, 3 ], Data: { zero: 0 }}};
- 条件语句
- wx: if 和 wx: else
- 可以通过 block 加条件,一次判断多个标签;
- 列表语句
- wx: for,数组当前项的下标变量名默认为 index,变量名默认为 item;
- 使用 wx: for-item 和 wx: for-index 可以用来指定元素和下标的变量名,例如: wx: for-item = “itemName” wx: for-index = “indexName”
- wx: for 支持嵌套;
- 同样可以通过 block 来渲染一个包含多个节点的块;
- 可以使用 wx: key 来指定项目的唯一标识符,并进行需要的操作,例如固定位置的排序
- 方法示例:给对象增加一个 unique 属性,然后每个 item 这个属性的值不同,然后在标签中设置 wx: key = unique;由于每个 key 的值不同,这样就可以通过 unique 的值来唯一标识每个标签,对其进行操作;
- 模板
可以通过定义模板 <template name = "templName">,在模板内放代码段,然后通过 <template is="templName" data = "{{... item}}"> 来引用模板
;- 模板有自己的作用域,只能使用 data 属性传入的数据;
is 属性可以通过花括号放入语句来做一些运算,例如动态判断采用哪个模板名字,以渲染哪个模板,例如 is="{{ value? even : odd }}
“
- 引用
- import
- 通过 import 可以在当前文件中使用目标文件定义的 template;
- import 有作用域的限制,只能一层,不能嵌套,即 A 引用 B ,B 引用 C,则 A 可以使用在 B 中定义的模板,但不能使用 C 中定义的模板;
- include
- include 可以将目标文件除模板代码块()的所有代码引入,相当于拷贝到 include 的位置;
- import
- 事件绑定
- 与用户交互一般通过事件来进行,在组件上面绑定事件名称,被触发时,到该页面对应的 Page 实例中寻找对应的事件处理函数,参数是 event;
- 事件类型
- 冒泡事件:触发后,会向父级节点传递;共有6个,分别为
- touchstart:触摸
- touchmove:触摸后移动
- touchcancel:触摸中断
- touchend:触摸结束
- tap:点击
- longtap:长点击
- 非冒泡事件:触发后,不会向父级节点传递;除了以上6个冒泡事件外,其他事件都是非冒泡事件;
- 冒泡的意思是,如果它被点击了,则它会触发它的父级节点上的事件,直到被阻止,或者到达根节点;
- 冒泡事件:触发后,会向父级节点传递;共有6个,分别为
- 事件写法:
- key:以 bind 或 catch 开头,然后加上事件的类型,例如 bindtap, catchtouchstart;注:bind 不会阻止冒泡, catch 会阻止冒泡;
- value:一个字符串,对应 Page 中定义的同名函数;
- 事件对象的属性
- type:字符串,事件类型
- timeStamp:整数,当前页面打开,到事件触发,经过的毫秒数;
- target:对象,事件触发的源组件
- currentTarget:对象,事件触发的当前组件(如果是冒泡事件,父级组件的事件的 currentTarget 即是父级组件,而非源组件)
- touches:数组,触摸点信息的数组
- changeTouches:数组,变化的解摸点信息的数组;
- detail:对象,其他额外的信息;
- 数据绑定
- WXML
- 配置
- 错误集
- 页面间传递数据的方法
- 在 app.js 中定义全局变量,由各个页面按需要赋值和获取;
- 在缓存中定义属性值存储,由 setStorage 和 getStorage 方法进行赋值和读取;
- 通过事件的 id 和 dataset 属性传递值到 js 逻辑层,然后在 navigate 或 redirectTo 的 url 中赋值参数,最后通过新页面的 onLoad 初始化的 options 参数获取值;
- 通过
组件中的 url 属性中赋值参数;
- 如果想要在子元素中使用 width: 100% 或 height: 100%,则首先需要在其父级以上的元素中定义相应的宽度值,因为这个 100% 是相对父元素而言的,它的表现取决于父元素的实际宽度是多少;
- 更新 data 某个对象的属性值
- var prop = ‘obj.key’
- this.setData({
- })
- scroll-view 有一个BUG,当内部元素的样式不完全一致时,不会对齐,需要在 scroll-view 内部嵌套一层 view 用来放置各元素,才可以控制;
- R.map 如何解决需要传入两个参数的问题?
- 页面间传递数据的方法
微信小程序
https://ccw1078.github.io/2018/01/04/微信小程序/