内容大部分来自微信小程序官方文档,主要是对微信小程序一个系统的认识和总结
一、指南
2) 介绍小程序代码构成 app.json 、 app.js 和 app.wxss , 2-1) 介绍小程序页面构成 page.js 、 page.wxml 、 page.json 、 page.wxss 、page.wxs,3) 为 project.config.json 项目配置信息,4) 为 sitemap.json 小程序索引配置
1).小程序与普通网页开发的区别
小程序的主要开发语言是 JavaScript。
网页开发渲染线程和脚本线程是互斥的,长时间的脚本运行可能会导致页面失去响应,而在小程序中,二者是分开的,分别运行在不同的线程中。
网页开发者可以使用到各种浏览器暴露出来的 DOM API,进行 DOM 选中和操作。而如上文所述,小程序的逻辑层和渲染层是分开的,逻辑层运行在 JSCore 中,并没有一个完整浏览器对象,因而缺少相关的DOM API和BOM API。这一区别导致了前端开发非常熟悉的一些库,例如 jQuery、 Zepto 等,在小程序中是无法运行的。同时 JSCore 的环境同 NodeJS 环境也是不尽相同,所以一些 NPM 的包在小程序中也是无法运行的。
网页开发者需要面对的环境是各式各样的浏览器,PC 端需要面对 IE、Chrome、QQ浏览器等,在移动端需要面对Safari、Chrome以及 iOS、Android 系统中的各式 WebView 。而小程序开发过程中需要面对的是两大操作系统 iOS 和 Android 的微信客户端,以及用于辅助开发的小程序开发者工具,小程序中三大运行环境也是有所区别的
运行环境 |
逻辑层 |
渲染层 |
iOS |
JavaScriptCore |
WKWebView |
安卓 |
V8 |
chromium定制内核 |
小程序开发者工具 |
NWJS |
Chrome WebView |
2).小程序代码构成
小程序包含一个描述整体程序的app和多个描述各自页面的page。
一个小程序主体部分由三个文件组成,必须放在项目的根目录,如下:
文件 | 必需 | 作用 |
---|---|---|
app.js | 是 | 小程序逻辑 |
app.json | 是 | 小程序公共配置 |
app.wxss | 否 | 小程序公共样式表(注1) |
注1:
作用于全局的样式表,同CSS用法一样,若在任意Page页写了同名Class则覆盖此处的样式。
行内样式 > Page.css > app.css
小程序全局配置 app.json
app.json是当前小程序的全局配置,包括了小程序的所有页面路径、界面表现、网络超时时间、底部 tab 等
// 小程序配置app.json
// JSON 配置 // JSON 是一种数据格式,并不是编程语言,在小程序中,JSON扮演的静态配置的角色 /* JSON 语法 注意事项: JSON文件都是被包裹在一个大括号中 {},通过key-value的方式来表达数据。JSON的Key必须包裹在一个双引号中,在实践中,编写 JSON 的时候,忘了给 Key 值加双引号或者是把双引号写成单引号是常见错误。 JSON的值只能是以下几种数据格式,其他任何格式都会触发报错,例如 JavaScript 中的 undefined。 数字,包含浮点数和整数 字符串,需要包裹在双引号中 Bool值,true 或者 false 数组,需要包裹在方括号中 [] 对象,需要包裹在大括号中 {} Null 还需要注意的是 JSON 文件中无法使用注释,试图添加注释将会引发报错。 */ { //pages用于指定小程序由哪些页面组成,每一项都对应一个页面路径(文件名) 信息。文件名不需要写文件后缀,框架会自动去寻找对于位置的 .json, .js, .wxml, .wxss 四个文件进行处理。数组的第一项代表小程序的初始页面(首页)。小程序中新增/减少页面,都需要对 pages 数组进行修改。 "pages": [ "pages/index/index", "pages/logs/logs" ], //window对象。设置小程序全局的状态栏、导航条、标题、窗口背景色。 "window": { //导航栏背景颜色,十六进制颜色 "navigationBarBackgroundColor": "#ffffff", //导航栏标题颜色 仅包含black (黑色)/ white(白色) "navigationBarTextStyle": "black", //导航栏标题文字内容 "navigationBarTitleText": "听风吟", //导航栏样式 仅包含default(默认)/custom(清空之前的所有样式设置) "navigationStyle": "default", //窗口的背景色 (未发现明显改变) "backgroundColor": "#eeeeee", //下拉 loading 的样式 仅支持 dark(刷新时改为三个 ·) / light(无特殊属性)需开启enablePullDownRefresh下拉刷新 "backgroundTextStyle": "light", //开启/关闭全局下拉刷新 仅true/false "enablePullDownRefresh": true, //页面上拉触底事件触发时距页面底部距离,单位为 px。 "onReachBottomDistance": 30, // 响应显示区域变化 //屏幕旋转设置,支持 auto (自动)/ portrait(竖屏) / landscape (2.5.0支持固定横屏显示) "pageOrientation": "portrait", // iPad 上启用屏幕旋转支持 "resizable": true }, //tabBar如果小程序是一个多 tab 应用(客户端窗口的底部或顶部有 tab 栏可以切换页面),可以通过 tabBar 配置项指定 tab 栏的表现,以及 tab 切换时显示的对应页面(指定页面栏目最少2个最多5个并配置样式) "tabBar": { //tab 上的文字默认颜色,仅支持十六进制颜色 "color": "#ffffff", //tab 上的文字选中时的颜色,仅支持十六进制颜色 "selectedColor": "#00ffff", //tab 的背景色,仅支持十六进制颜色 "backgroundColor": "#000000", //tabbar 上边框的颜色, 仅支持 black / white "borderStyle": "black", //tab的列表项接受一个数组,配置最少 2 个、最多 5 个 tab "list": [ { //页面路径,必须在 pages 中先定义 "pagePath": "pages/index/index", //tab 上按钮文字 "text": "首页", //图片路径,icon 大小限制为 40kb,建议尺寸为 81px * 81px,不支持网络图片。当 position 为 top 时,不显示 icon。 "iconPath": "../images/xxx.ico", //选中时的图片路径,限制同上 "selectedIconPath": "../images/xxx2.ico" }, { "pagePath": "pages/logs/logs", "text": "日志", "iconPath": "../images/xxx.ico", "selectedIconPath": "../images/xxx2.ico" } ], // tabBar 的位置,仅支持 bottom / top "position":"bottom", //自定义 tabBar 用自定义组件的方式编写即可,该自定义组件完全接管 tabBar 的渲染。另外,自定义组件新增 getTabBar 接口,可获取当前页面下的自定义 tabBar 组件实例 //添加自定义目录custom-tab-bar "custom":true }, //networkTimeout各类网络请求的超时时间,单位均为毫秒。 //默认均为60s "networkTimeout": { //wx.request 的超时时间,单位:毫秒。 "request": 10000, //wx.downloadFile 的超时时间,单位:毫秒。 "downloadFile": 10000, //wx.connectSocket 的超时时间,单位:毫秒。 "connectSocket": 10000, //wx.uploadFile 的超时时间,单位:毫秒。 "uploadFile": 10000 }, //debug在开发者工具中开启 debug 模式,在开发者工具的控制台面板,调试信息以 info 的形式给出,其信息有 Page 的注册,页面路由,数据更新,事件触发等。 "debug": false, //要在插件中调用插件功能页,需要先激活插件所有者小程序的功能页 "functionalPages": { "independent": true }, //subpackages申明项目分包结构 /**某些情况下,开发者需要将小程序划分成不同的子包,在构建时打包成不同的分包,用户在使用时按需进行加载。 在构建小程序分包项目时,构建会输出一个或多个分包。每个使用分包小程序必定含有一个主包。所谓的主包,即放置默认启动页面/TabBar 页面,以及一些所有分包都需用到公共资源/JS 脚本;而分包则是根据开发者的配置进行划分。 在小程序启动时,默认会下载主包并启动主包内页面,当用户进入分包内某个页面时,客户端会把对应分包下载下来,下载完成后再进行展示。 目前小程序分包大小有以下限制: 整个小程序所有分包大小不超过 8M 单个分包/主包大小不能超过 2M 对小程序进行分包,可以优化小程序首次启动的下载时间,以及在多团队共同开发时可以更好的解耦协作。*/ /** 打包原则 声明 subpackages 后,将按 subpackages 配置路径进行打包,subpackages 配置路径外的目录将被打包到 app(主包) 中 app(主包)也可以有自己的 pages(即最外层的 pages 字段) subpackage 的根目录不能是另外一个 subpackage 内的子目录 tabBar 页面必须在 app(主包)内 */ /* 引用原则 packageA 无法 require packageB JS 文件,但可以 require app、自己 package 内的 JS 文件 packageA 无法 import packageB 的 template,但可以 require app、自己 package 内的 template packageA 无法使用 packageB 的资源,但可以使用 app、自己 package 内的资源*/ /* 低版本兼容 由微信后台编译来处理旧版本客户端的兼容,后台会编译两份代码包,一份是分包后代码,另外一份是整包的兼容代码。 新客户端用分包,老客户端还是用的整包,完整包会把各个 subpackage 里面的路径放到 pages 中。 */ "subpackages": [ { //分包跟目录 "root": "packageA", //分包别名,分包预加载时可用 "name": "pack1", //分包页面路径,相对于分包跟目录,使用同pages一样 "pages": [ "pages/test/test" ], //是否为独立分包 /* 独立分包 微信客户端 6.7.2,基础库 2.3.0 及以上版本开始支持。开发者工具请使用 1.02.1808300 及以上版本,可点此下载。 独立分包是小程序中一种特殊类型的分包,可以独立于主包和其他分包运行。从独立分包中页面进入小程序时,不需要下载主包。当用户进入普通分包或主包内页面时,主包才会被下载。 开发者可以按需将某些具有一定功能独立性的页面配置到独立分包中。当小程序从普通的分包页面启动时,需要首先下载主包;而独立分包不依赖主包即可运行,可以很大程度上提升分包页面的启动速度。 一个小程序中可以有多个独立分包 */ /* 限制 独立分包属于分包的一种。普通分包的所有限制都对独立分包有效。独立分包中插件、自定义组件的处理方式同普通分包。 此外,使用独立分包时要注意: 1、独立分包中不能依赖主包和其他分包中的内容,包括js文件、template、wxss、自定义组件、插件等。主包中的app.wxss对独立分包无效,应避免在独立分包页面中使用 app.wxss 中的样式; 2、App 只能在主包内定义,独立分包中不能定义 App,会造成无法预期的行为; 3、独立分包中暂时不支持使用插件 */ /* 关于 getApp() 与普通分包不同,独立分包运行时,App 并不一定被注册,因此 getApp() 也不一定可以获得 App 对象: 当用户从独立分包页面启动小程序时,主包不存在,App也不存在,此时调用 getApp() 获取到的是 undefined。 当用户进入普通分包或主包内页面时,主包才会被下载,App 才会被注册。 当用户是从普通分包或主包内页面跳转到独立分包页面时,主包已经存在,此时调用 getApp() 可以获取到真正的 App。 由于这一限制,开发者无法通过 App 对象实现独立分包和小程序其他部分的全局变量共享。 为了在独立分包中满足这一需求,基础库 2.2.4 版本开始 getApp支持 [allowDefault ]参数,在 App 未定义时返回一个默认实现。当主包加载,App 被注册时,默认实现中定义的属性会被覆盖合并到真正的 App 中 定义方法: const app = getApp({allowDefault: true}) */ /* 关于 App 生命周期 当从独立分包启动小程序时,主包中 App 的 onLaunch 和首次 onShow 会在从独立分包页面首次进入主包或其他普通分包页面时调用。 由于独立分包中无法定义 App,小程序生命周期的监听可以使用 wx.onAppShow,wx.onAppHide 完成。App 上的其他事件可以使用 wx.onError,wx.onPageNotFound 监听 */ "independent":false }, { "root": "packageB", "name": "pack2", "pages": [ "pages/demo/demo" ], "independent": false } ], //preloadRule分包预下载 /* 进入小程序某个页面时,由框架自动预下载可能需要的分包,提升进入后续分包页面时的启动速度。对于独立分包,也可以预下载主包 预下载分包行为在进入某个页面时触发,通过在 app.json 增加 preloadRule 配置来控制。 */ "preloadRule": { //页面路径 "pages/index/index": { //预下载配置 //在指定网络下预下载,可选值为:all: 不限网络 wifi: 仅wifi下预下载 "network": "all", //进入页面后预下载分包的 root 或 name。__APP__ 表示主包 "packages": [ "packageA" ] }, "pages/logs/logs": { "network": "wifi", "packages": [ "__APP__", "packageA", "packageB" ] } }, //多线程workers /* 一些异步处理的任务,可以放置于 Worker 中运行,待运行结束后,再把结果返回到小程序主线程。Worker 运行于一个单独的全局上下文与线程中,不能直接调用主线程的方法。 Worker 与主线程之间的数据传输,双方使用 Worker.postMessage() 来发送数据,Worker.onMessage() 来接收数据,传输的数据并不是直接共享,而是被复制的 */ "workers": "workers", /*在app.js中创建worker实例,只能创建一个 Worker wx.createWorker(string scriptPath) 监听主线程/Worker 线程向当前线程发送的消息的事件 worker.onMessage(function (res) {console.log(res)}) 向主线程/Worker 线程发送的消息 worker.postMessage({msg: 'hello worker'}) 需要发送的消息,必须是一个可序列化的 JavaScript key-value 形式的对象(JSON格式) Worker.terminate() 结束当前 Worker 线程。仅限在主线程 worker 对象上调用 */ //requiredBackgroundModes申明需要后台运行的能力,类型为数组。目前支持以下项目:audio: 后台音乐播放 location: 后台定位 //在此处申明了后台运行的接口,开发版和体验版上可以直接生效,正式版还需通过审核。 "requiredBackgroundModes": [ "audio", "location" ], // 使用插件 /* plugins 定义段中可以包含多个插件声明,每个插件声明以一个使用者自定义的插件引用名作为标识,并指明插件的 appid 和需要使用的版本号。其中,引用名(如上例中的 myPlugin)由使用者自定义,无需和插件开发者保持一致或与开发者协调。在后续的插件使用中,该引用名将被用于表示该插件 */ "plugins": { "myPlugin": { "version": "1.0.0", "provider": "wxidxxxxxxxxxxxxxxxx" } }, // 当小程序需要使用 wx.navigateToMiniProgram 接口跳转到其他小程序时,需要先在配置文件中声明需要跳转的小程序 appId 列表,最多允许填写 10 个。 "navigateToMiniProgramAppIdList":[ "wxcbe110fu2xaxedfu", "wxfb1ff0f3u0abe913", "wxc1b5d81exdad1efe", "wxu8caa30cd32c1fb9", "wx52axxb89fx3xe23c" ], // usingComponents // 在此处声明的自定义组件视为全局自定义组件,在小程序内的页面或自定义组件中可以直接使用而无需再声明 // 授权permission // 部分接口需要经过用户授权同意才能调用。我们把这些接口按使用范围分成多个 scope ,用户选择对 scope 来进行授权,当授权给一个 scope 之后,其对应的所有接口都可以直接使用。 // 获取用户授权设置 // wx.getSetting // 打开设置界面 // wx.openSetting // 提前发起授权请求 // wx.authorize /* scope 列表 scope.userInfo wx.getUserInfo 用户信息 scope.userLocation wx.getLocation, wx.chooseLocation 地理位置 scope.userLocationBackground wx.userLocationBackground 后台定位 scope.address wx.chooseAddress 通讯地址 scope.invoiceTitle wx.chooseInvoiceTitle 发票抬头 scope.invoice wx.chooseInvoice 获取发票 scope.werun wx.getWeRunData 微信运动步数 scope.record wx.startRecord 录音功能 scope.writePhotosAlbum wx.saveImageToPhotosAlbum, wx.saveVideoToPhotosAlbum 保存到相册 scope.camera camera 组件 摄像头 */ "permission": { "scope.userLocation": { "desc": "你的位置信息将用于小程序位置接口的效果展示" // 高速公路行驶持续后台定位 } }, // 配置微信小程序内索引 /* sitemap.json 用于配置小程序及其页面是否允许被微信索引,文件内容为一个 JSON 对象,如果没有 sitemap.json ,则默认为所有页面都允许被索引; */ "sitemapLocation": "sitemap.json", // 微信客户端 7.0 开始,UI 界面进行了大改版。小程序也进行了基础组件的样式升级。app.json 中配置 "style": "v2"可表明启用新版的组件样式。本次改动涉及的组件有 button icon radio checkbox switch slider。 "style": "v2" }
小程序app.js
每个小程序都需要在app.js中调用 App方法注册小程序示例,绑定生命周期回调函数、错误监听和页面不存在监听函数等
//注册小程序app.js /** * * App() 必须在 app.js 中调用,必须调用且只能调用一次 * * 整个小程序只有一个 App 实例,是全部页面共享的。开发者可以通过 getApp 方法获取到全局唯一的 App 示例,获取App上的数据或调用开发者注册在 App 上的函数。 */ App({ // 生命周期回调——监听小程序初始化。 /** * 小程序初始化完成时触发,全局只触发一次。回调参数也可以使用 wx.getLaunchOptionsSync 获取 * 返回参数 * Object 属性 类型 说明 path string 启动小程序的路径 scene number 启动小程序的场景值(具体场景值参考:场景值列表) query Object 启动小程序的 query 参数 shareTicket string shareTicket,获取转发信息(详见:注1) referrerInfo Object 来源信息。从另一个小程序、公众号或 App 进入小程序时返回。否则返回 {}。(详见:注2) */ /** * 注1 * 获取更多转发信息 * 通常开发者希望转发出去的小程序被二次打开的时候能够获取到一些信息,例如群的标识。现在通过调用 wx.showShareMenu 并且设置 withShareTicket 为 true ,当用户将小程序转发到任一群聊之后,此转发卡片在群聊中被其他用户打开时,可以在 App.onLaunch 或 App.onShow 获取到一个 shareTicket。通过调用 wx.getShareInfo 接口传入此 shareTicket 可以获取到转发信息 * * 说人话系列: * 即可以通过设置转发withShareTicket为true在另一个页面中通过shareTicket获取wx.getShareInfo 接口回调以取得更多转发信息 * 如:A用户在将Test小程序转发至C微信群,此时B用户通过点击C微信群中的小程序卡片进入小程序,此时开发者可通过App.onLaunch或wx.getLaunchOptionsSync获取shareTicket, * 然后将shareTicket传入wx.getShareInfo获取回调,回调中的敏感数据为加密的需后台校验解密开放数据(解密详见:服务端获取开放数据) */ /** * 注2 * referrerInfo 结构 属性 类型 说明 appId string 来源小程序、公众号或 App 的 appId extraData Object 来源小程序传过来的数据,scene=1037或1038时支持 注意: 部分版本在无referrerInfo的时候会返回 undefined,建议使用 options.referrerInfo && options.referrerInfo.appId 进行判断 */ onLaunch: function(options) { //小程序初始化完后,打印回调参数,同wx.getLaunchOptionsSync函数一样 console.log(options) // 展示本地存储能力 var logs = wx.getStorageSync('logs') || [] logs.unshift(Date.now()) wx.setStorageSync('logs', logs) // 登录 wx.login({ success: res => { // 发送 res.code 到后台换取 openId, sessionKey, unionId } }) // 获取用户信息 wx.getSetting({ success: res => { if (res.authSetting['scope.userInfo']) { // 已经授权,可以直接调用 getUserInfo 获取头像昵称,不会弹框 wx.getUserInfo({ success: res => { // 可以将 res 发送给后台解码出 unionId this.globalData.userInfo = res.userInfo // 由于 getUserInfo 是网络请求,可能会在 Page.onLoad 之后才返回 // 所以此处加入 callback 以防止这种情况 if (this.userInfoReadyCallback) { this.userInfoReadyCallback(res) } } }) } } }) }, // 生命周期回调——监听小程序启动或切前台。 /** * 小程序启动,或从后台进入前台显示时触发。也可以使用 wx.onAppShow 绑定监听 * 回调参数同onLaunch或wx.getLaunchOptionsSync一样,区别在于 onLaunch 全局只生效一次,而onShow每次进入小程序前台或启动都会触发 */ onShow: function(options) { console.log("Look Me") }, // 生命周期回调——监听小程序切后台 /** * 小程序从前台进入后台时触发。也可以使用 wx.onAppHide 绑定监听 */ onHide: function() { console.log("awsl") }, // 错误监听函数。 /** * 小程序发生脚本错误或 API 调用报错时触发。也可以使用 wx.onError 绑定监听 */ onError(msg) { console.log(msg) }, // 页面不存在监听函数 /** * 小程序要打开的页面不存在时触发。也可以使用 wx.onPageNotFound 绑定监听 * 返回参数 * 属性 类型 说明 path string 不存在页面的路径 query Object 打开不存在页面的 query 参数 isEntryPage boolean 是否本次启动的首个页面(例如从分享等入口进来,首个页面是开发者配置的分享页面) 注意: 开发者可以在回调中进行页面重定向,但必须在回调中同步处理,异步处理(例如 setTimeout 异步执行)无效。 若开发者没有调用 wx.onPageNotFound 绑定监听,也没有声明 App.onPageNotFound,当跳转页面不存在时,将推入微信客户端原生的页面不存在提示页面。 如果回调中又重定向到另一个不存在的页面,将推入微信客户端原生的页面不存在提示页面,并且不再第二次回调 (通常可以在此处配置自己的不存在页面) */ onPageNotFound(res) { wx.redirectTo({ url: 'pages/...' }) // 如果是 tabbar 页面,请使用 wx.switchTab }, // 其他 类型:any 非必填 可以添加任意的函数或数据变量到 Object 参数中,用 this(即app实例) 可以访问 /** * 可添加全局函数,获取app应用实例后即可使用 * * 如下: * const app = getApp(); * * app.test(23333) * * 控制台将打印"23333" */ test: function(e) { console.log(e) }, //全局变量,全局可用,一般用于保存用户信息 globalData: { userInfo: null } })
小程序全局样式app.wxss
WXSS (WeiXin Style Sheets)是一套样式语言,用于描述 WXML 的组件样式。
/* app.wxss */ /* WXSS 用来决定 WXML 的组件应该怎么显示。WXSS 具有 CSS 大部分特性。同时为了更适合开发微信小程序,WXSS 对 CSS 进行了扩充以及修改。 与 CSS 相比,WXSS 扩展的特性有: 尺寸单位 样式导入 尺寸单位 rpx(responsive pixel): 可以根据屏幕宽度进行自适应。规定屏幕宽为750rpx。如在 iPhone6 上,屏幕宽度为375px,共有750个物理像素,则750rpx = 375px = 750物理像素,1rpx = 0.5px = 1物理像素。 设备 rpx换算px (屏幕宽度/750) px换算rpx (750/屏幕宽度) iPhone5 1rpx = 0.42px 1px = 2.34rpx iPhone6 1rpx = 0.5px 1px = 2rpx iPhone6 Plus 1rpx = 0.552px 1px = 1.81rpx 样式导入 使用@import语句可以导入外联样式表,@import后跟需要导入的外联样式表的相对路径,用;表示语句结束。 */ /* 建议: 开发微信小程序时设计师可以用 iPhone6 作为视觉稿的标准。 */ /* 内联样式 框架组件上支持使用 style、class 属性来控制组件的样式。 style:静态的样式统一写到 class 中。style 接收动态的样式,在运行时会进行解析,请尽量避免将静态的样式写进 style 中,以免影响渲染速度。class:用于指定样式规则,其属性值是样式规则中类选择器名(样式类名)的集合,样式类名不需要带上.,样式类名之间用空格分隔。 */ /* 选择器 目前支持的选择器有: 选择器 样例 样例描述 .class .intro 选择所有拥有 class="intro" 的组件 #id #firstname 选择拥有 id="firstname" 的组件 element view 选择所有 view 组件 element, element view, checkbox 选择所有文档的 view 组件和所有的 checkbox 组件 ::after view::after 在 view 组件后边插入内容 ::before view::before 在 view 组件前边插入内容 */ /* 全局样式与局部样式 定义在 app.wxss 中的样式为全局样式,作用于每一个页面。在 page 的 wxss 文件中定义的样式为局部样式,只作用在对应的页面,并会覆盖 app.wxss 中相同的选择器。 */ .container { height: 100%; display: flex; flex-direction: column; align-items: center; justify-content: space-between; padding: 200rpx 0; box-sizing: border-box; }
2-1).小程序页面构成
文件类型 | 必需 | 作用 |
---|---|---|
js | 是 | 页面逻辑 |
wxml | 是 | 页面结构 |
json | 否 | 页面配置 |
wxss | 否 | 页面样式表 |
Page.wxml
WXML(WeiXin Markup Language)是框架设计的一套标签语言,结合基础组件、事件系统,可以构建出页面的结构
<view class='page'> <view class="container"> <view class="userinfo"> <button wx:if="{{!hasUserInfo && canIUse}}" open-type="getUserInfo" bindgetuserinfo="getUserInfo"> 获取头像昵称 button> <block wx:else> <image bindtap="bindViewTap" class="userinfo-avatar" src="{{userInfo.avatarUrl}}" mode="cover">image> <text class="userinfo-nickname">{{userInfo.nickName}}text> block> view> <view class="usermotto"> <text class="user-motto">{{motto}}text> view> view> view>
page.json
每一个小程序页面也可以使用 .json 文件来对本页面的窗口表现进行配置。页面中配置项在当前页面会覆盖 app.json 的 window 中相同的配置项。文件内容为一个 JSON 对象
// 页面配置page.json // 每一个小程序页面都可以使用 .json 文件来对本页面的窗口表现进行配置。页面中配置项在当前页面会覆盖 app.json 的 window 中相同的配置项。文件内容为一个 JSON 对象,有以下属性 { // 导航栏背景颜色 颜色都以十六进制显示,否则在不同设备中可能显示错误 "navigationBarBackgroundColor": "#13c106", // 导航栏标题颜色,仅支持 black / white (黑/白) "navigationBarTextStyle": "black", // 导航栏标题文字内容 "navigationBarTitleText": "聽風吟", // 导航栏样式,仅支持以下值:default 默认样式 、 custom 自定义导航栏,只保留右上角胶囊按钮 "navigationStyle": "default", // 窗口的背景色 "backgroundColor": "#13c106", // 下拉 loading 的样式,仅支持 dark (三个点)/ light (无特殊展示) "backgroundTextStyle": "dark", // 顶部窗口的背景色,仅 iOS 支持 "backgroundColorTop": "#13c106", // 底部窗口的背景色,仅 iOS 支持 "backgroundColorBottom": "#13c106", // 控制当前页下拉刷新 "enablePullDownRefresh": false, // 控制当前页上拉刷新 "onReachBottomDistance": false, // 控制当前页屏幕旋转 支持 auto (自动)/ portrait(竖屏) / landscape (2.5.0支持固定横屏显示) "pageOrientation": "portrait", // 设置为 true 则页面整体不能上下滚动。只在页面配置中有效,无法在 app.json 中设置 "disableScroll": true, // 页面自定义组件配置 /* 自定义组件 从小程序基础库版本 1.6.3 开始,小程序支持简洁的组件化编程。所有自定义组件相关特性都需要基础库版本 1.6.3 或更高。 开发者可以将页面内的功能模块抽象成自定义组件,以便在不同的页面中重复使用;也可以将复杂的页面拆分成多个低耦合的模块,有助于代码维护。自定义组件在使用时与基础组件非常相似 */ /* // custom-comp 创建自定义组件 类似于页面,一个自定义组件由 json wxml wxss js 4个文件组成。要编写一个自定义组件,首先需要在 json 文件中进行自定义组件声明(将 component 字段设为 true 可以将这一组文件设为自定义组件) // custom-comp.json { "component": true } 在 wxml 文件中编写组件模板,在 wxss 文件中加入组件样式,它们的写法与页面的写法类似。 // custom-comp.wxml{{innerText}} // custom-comp.wxss .inner { color: red; } // 注意:在组件wxss中不应使用ID选择器、属性选择器和标签名选择器。 在自定义组件的 js 文件中,需要使用 Component() 来注册组件,并提供组件的属性定义、内部数据和自定义方法。 组件的属性值和内部数据将被用于组件 wxml 的渲染,其中,属性值是可由组件外部传入的 // custom-comp.js Component({ properties: { // 这里定义了innerText属性,属性值可以在组件使用时指定 innerText: { type: String, value: 'default value', } }, data: { // 这里是一些组件内部数据 someData: {} }, methods: { // 这里是一个自定义方法 customMethod: function(){} } }) */ // 使用自定义组件,使用已注册的自定义组件前,首先要在页面的 json 文件中进行引用声明。此时需要提供每个自定义组件的标签名和对应的自定义组件文件路径: "usingComponents": { "custom-comp": "./custom-comp" } /* */ // 在页面的 wxml 中就可以像使用基础组件一样使用自定义组件。节点名即自定义组件的标签名,节点属性即传递给组件的属性值 // 自定义组件的 wxml 节点结构在与数据结合之后,将被插入到引用位置内 /* 细节注意事项: 因为 WXML 节点标签名只能是小写字母、中划线和下划线的组合,所以自定义组件的标签名也只能包含这些字符。 自定义组件也是可以引用自定义组件的,引用方法类似于页面引用自定义组件的方式(使用 usingComponents 字段)。 自定义组件和页面所在项目根目录名不能以“wx-”为前缀,否则会报错。 注意,是否在页面文件中使用 usingComponents 会使得页面的 this 对象的原型稍有差异,包括: 使用 usingComponents 页面的原型与不使用时不一致,即 Object.getPrototypeOf(this) 结果不同。 使用 usingComponents 时会多一些方法,如 selectComponent 。 出于性能考虑,使用 usingComponents 时, setData 内容不会被直接深复制,即 this.setData({ field: obj}) 后 this.data.field === obj 。(深复制会在这个值被组件间传递时发生。) */ }
3).项目配置 project.config.json
//工具配置project.config.json //官方提供的配置非常残缺。。。 /* 如配置值为""则为Sring类型,根据相应路径或提示更改即可 如配置值为true则当前配置为Boolean类型 如配置值为Object固定选项则会有相应提示 */ { //指定小程序源码的目录(需为相对路径)-- "miniprogramRoot": "", //指定腾讯云项目的目录(需为相对路径)-- "qcloudRoot": "", //指定插件项目的目录(需为相对路径)-- "pluginRoot": "", //编译类型 /* 仅包含miniprogram (普通小程序项目)plugin(小程序插件项目) */ "compileType": "miniprogram", //项目设置 "setting": { //是否启用 es6 转 es5 "es6": true, //上传代码时样式是否自动补全 "postcss": true, //上传代码时是否自动压缩 "minified": true, //是否检查安全域名和 TLS 版本 "urlCheck": false, //是否进行代码保护-- "uglifyFileName": true, //是否打开SiteMap索引提示((默认为true) /* 微信现已开放小程序内搜索,开发者可以通过 sitemap.json 配置,或者管理后台页面收录开关来配置其小程序页面是否允许微信索引。当开发者允许微信索引时,微信会通过爬虫的形式,为小程序的页面内容建立索引。当用户的搜索词条触发该索引时,小程序的页面将可能展示在搜索结果中。 爬虫访问小程序内页面时,会携带特定的 user-agent:mpcrawler 及场景值:1129。需要注意的是,若小程序爬虫发现的页面数据和真实用户的呈现不一致,那么该页面将不会进入索引中。 */ /* 说人话系列: 微信小程序2019/03/29号推出 sitemap 功能,默认收录所有小程序页面功能,用于微信场景搜索,之后可以根据内容来搜索小程序,而不仅止于小程序名称和简介 此功能并非关闭索引,而是关闭索引的提示 关闭索引请查看 sitemap.json */ "checkSiteMap": true, //是否使用工具渲染 CoverView-- "coverView": true, //是否打开增强编译-- "enhance": true, //增强编译下Babel的配置项-- "babelSetting": { //配置需要跳过Babel编译(包括代码压缩)处理的文件或目录 "ignore": [], //暂无官方说明 "disablePlugins": [], //Babel 辅助函数的输出目录,默认为 @babel/runtime "outputPath": "" }, //上传时是否带上 sourcemap(默认为true) "uploadWithSourceMap": true, //暂无官方说明 "newFeature": true, "autoAudits": false, "checkInvalidKey": true, }, //基础库版本 "libVersion": "2.8.0", //当前项目appid,只在新建项目时读取 "appid": "wx03f53a71c3f1c05c", //当前项目名字,只在新建项目时读取 "projectname": "XJTest", //打包配置项(此项设置需重启开发者工具才可生效) /* packOptions 用以配置项目在打包过程中的选项。打包是预览、上传时对项目进行的必须步骤。 目前可以指定 packOptions.ignore 字段,用以配置打包时对符合指定规则的文件或文件夹进行忽略,以跳过打包的过程,这些文件或文件夹将不会出现在预览或上传的结果内。 packOptions.ignore 为一对象数组,对象元素类型如下: 字段名 类型 说明 value string 路径1或取值 type string 类型 */ /* type 可以取的值为 folder(文件夹) file(文件) suffix(后缀) prefix(前缀) regexp2(正则表达式) glob2(Glob 规则) 所有规则值都会自动忽略大小写。 注 1: value 字段的值若表示文件或文件夹路径,以小程序目录 (miniprogramRoot) 为根目录。 注 2: regexp、glob 仅 1.02.1809260 及以上版本工具支持。 */ //示例 "packOptions": { "ignore": [ { "type": "file", "value": "test/test.js" }, { "type": "folder", "value": "test" }, { "type": "suffix", "value": ".webp" }, { "type": "prefix", "value": "test-" }, { "type": "glob", "value": "test/**/*.js" }, { "type": "regexp", "value": "\\.jsx$" } ] }, //调试配置项 /* debugOptions 用以配置在对项目代码进行调试时的选项。 目前可以指定 debugOptions.hidedInDevtools 字段,用以配置调试时于调试器 Sources 面板隐藏源代码的文件。 hidedInDevtools 的配置规则和 packOptions.ignore 是一致的。 当某个 js 文件符合此规则时,调试器 Sources 面板中此文件源代码正文内容将被隐藏,显示为: // xxx.js has been hided by project.config.json 注:配置此规则后,可能需要关闭并重新打开项目才能看到效果。 */ "debugOptions": { "hidedInDevtools": [ { "type": "file", "value": "test/test.js" }, { "type": "folder", "value": "test" }, { "type": "suffix", "value": ".webp" }, { "type": "prefix", "value": "test-" }, { "type": "glob", "value": "test/**/*.js" }, { "type": "regexp", "value": "\\.jsx$" } ] }, //自定义预处理 "scripts": { //官方仅以下说明 /* scripts 中指定自定义预处理的命令 名字 说明 beforeCompile 编译前预处理命令 beforePreview 预览前预处理命令 beforeUpload 上传前预处理命令 */ }, //当前文件描述 "description": "项目配置文件", //是否为游客 "isGameTourist": false, //工具类型 "simulatorType": "wechat", //开发者工具插件库版本 "simulatorPluginLibVersion": {}, //暂无官方说明 "condition": { "search": { "current": -1, "list": [] }, "conversation": { "current": -1, "list": [] }, "game": { "currentL": -1, "list": [] }, "miniprogram": { "current": -1, "list": [] } } }
4).小程序索引配置sitemap.json
//小程序索引配置sitemap.json /* 微信现已开放小程序内搜索,开发者可以通过 sitemap.json 配置,或者管理后台页面收录开关来配置其小程序页面是否允许微信索引。当开发者允许微信索引时,微信会通过爬虫的形式,为小程序的页面内容建立索引。当用户的搜索词条触发该索引时,小程序的页面将可能展示在搜索结果中。 爬虫访问小程序内页面时,会携带特定的 user-agent:mpcrawler 及场景值:1129。需要注意的是,若小程序爬虫发现的页面数据和真实用户的呈现不一致,那么该页面将不会进入索引中。 */ /* 注:如果没有 sitemap.json ,则默认为所有页面都允许被索引 注:{"action": "allow","page": "*"} 是优先级最低的默认规则,未显式指明 "disallow" 的都默认被索引 */ { //文件描述 "desc": "关于本文件的更多信息,请参考文档 https://developers.weixin.qq.com/miniprogram/dev/framework/sitemap.html", // 小程序索引配置 "rules": [ { // "allow"(允许)、"disallow"(不允许) 命中该规则的页面是否能被索引 "action": "allow", // "*" 所有页面/页面的路径 "page": "path/to/page", // 当 page 字段指定的页面在被本规则匹配时可能使用的页面参数名称的列表(不含参数值) "params": [ "a", "b" ], // 当 page 字段指定的页面在被本规则匹配时,此参数说明 params 匹配方式 /* exact 当小程序页面的参数列表等于 params 时,规则命中 inclusive 当小程序页面的参数列表包含 params 时,规则命中 exclusive 当小程序页面的参数列表与 params 交集为空时,规则命中 partial 当小程序页面的参数列表与 params 交集不为空时,规则命中 */ "matching": "exact" }, { "action": "disallow", "page": "path/to/page" } ] /* path/to/page?a=1&b=2 => 优先索引 path/to/page => 不被索引 path/to/page?a=1 => 不被索引 path/to/page?a=1&b=2&c=3 => 不被索引 其他页面都会被索引 */ }
二、框架
三、组件
四、API
require和import的区别
import和require都是被模块化所使用。
1-遵循规范
require 是 AMD规范引入方式
import是ES6的一个语法标准,如果要兼容浏览器的话必须转化成ES5的语法
2-调用时间
require是运行时调用,所以require理论上可以运用在代码的任何地方
import是编译时调用,所以必须放在文件开头
3-本质
require是赋值过程,其实require的结果就是对象、数字、字符串、函数等,再把require的结果赋值给某个变量
import是解构过程,但是目前所有的引擎都还没有实现import,我们在node中使用babel支持ES6,也仅仅是将ES6转码为ES5再执行,import语法会被转码为require
变量声明(var、let、const)
var:声明全局变量。换句话理解就是,声明在for循环中的变量,跳出for循环同样可以使用。
let:声明块级变量。即局部变量。(只在let命令所在的代码块内有效)
const:声明一个只读常量。具有块级作用域。(一旦声明即不可更改,声明时必须赋值)
不存在变量提升
var命令会发生”变量提升“现象,即变量可以在声明之前使用,值为undefined。这种现象多多少少是有些奇怪的,按照一般的逻辑,变量应该在声明语句之后才可以使用。
为了纠正这种现象,let命令改变了语法行为,它所声明的变量一定要在声明后使用,否则报错。
暂时性死区
只要块级作用域内存在let命令,它所声明的变量就“绑定”(binding)这个区域,不再受外部的影响。
var tmp = 123;
if (true) {
tmp = 'abc'; // ReferenceError
let tmp;
}
上面代码中,存在全局变量tmp,但是块级作用域内let又声明了一个局部变量tmp,导致后者绑定这个块级作用域,所以在let声明变量前,对tmp赋值会报错。
ES6明确规定,如果区块中存在let和const命令,这个区块对这些命令声明的变量,从一开始就形成了封闭作用域。凡是在声明之前就使用这些变量,就会报错。
总之,在代码块内,使用let命令声明变量之前,该变量都是不可用的。这在语法上,称为“暂时性死区”(temporal dead zone,简称 TDZ)。
不允许重复声明
let不允许在相同作用域内,重复声明同一个变量
const本质
const实际上保证的,并不是变量的值不得改动,而是变量指向的那个内存地址不得改动。对于简单类型的数据(数值、字符串、布尔值),值就保存在变量指向的那个内存地址,因此等同于常量。但对于复合类型的数据(主要是对象和数组),变量指向的内存地址,保存的只是一个指针,const只能保证这个指针是固定的,它指向的数据结构是可变的。
JSON
是一种取代XML的一种轻量级的数据交换格式
它独立于语言的文本格式的的同时还采用了类似于C语言家族的习惯(包括C, C++, C#, Java, JavaScript, Perl, Python等)和xml相比,它更小巧、易于人阅读和编写,并且描述能力也不差,同时也易于机器解析和生成。
这些特性使JSON成为理想的数据交换语言,利于网络传输数据且节省流量而起到加快速度的作用。
书写格式是:以“{”开始,“}”结束。是一个无序的“‘名称/值’对”集合。名称写在前面(在双引号中),值对写在后面(同样在双引号中),中间用冒号隔开。
[如果是字符串,那不管是键或值最好都用双引号引起来]
-------------------函数记录-------------------
获取当前系统信息
wx.getSystemInfo({
success: function (res) {
console.log(res)
}
})
包含信息:
DKVersion:"2.7.7" -SDK版本
batteryLevel:100 -电池水平
brand:"devtools" -品牌
errMsg:"getSystemInfo:ok" -errMsg
fontSizeSetting:16 -字体大小设置
language:"zh" -语言
model:"iPhone 7 Plus" -模型
pixelRatio:3 -像素比
platform:"devtools" -平台
screenHeight:736 -屏幕高度
screenWidth:414 -屏幕宽度
statusBarHeight:20 -状态栏高度
system:"iOS 10.0.1" -系统
version:"6.6.3" -版本
windowHeight:672 -窗口高度
windowWidth:414 -窗口宽度