├── .babelrc ├── .gitignore ├── CHANGELOG.md ├── README.md ├── appveyor.yml ├── package-lock.json ├── package.json ├── src ├── _template_page │ ├── index.d.ts │ ├── index.json │ ├── index.ts │ ├── index.wxml │ └── index.wxss ├── api │ ├── index.d.ts │ ├── index.ts │ ├── wxfetch.d.ts │ └── wxfetch.ts ├── app.d.ts ├── app.json ├── app.ts ├── app.wxss ├── components │ ├── skeleton-group │ │ ├── index.d.ts │ │ ├── index.json │ │ ├── index.ts │ │ ├── index.wxml │ │ ├── index.wxss │ │ └── readme.md │ ├── skeleton-item │ │ ├── index.d.ts │ │ ├── index.json │ │ ├── index.ts │ │ ├── index.wxml │ │ └── index.wxss │ └── skeleton │ │ ├── index.d.ts │ │ ├── index.json │ │ ├── index.ts │ │ ├── index.wxml │ │ └── index.wxss ├── images │ ├── logo.png │ ├── screenshot.png │ └── screenshot2.png ├── lib │ └── class-component │ │ ├── component.d.ts │ │ ├── component.ts │ │ ├── page.d.ts │ │ └── page.ts ├── sitemap.json ├── style │ ├── common.wxss │ ├── font.less │ ├── main.less │ ├── progress.less │ └── result.less ├── typings │ ├── index.d.ts │ ├── lib.wa.es6.d.ts │ ├── page.d.ts │ ├── page.ts │ └── wx │ │ ├── index.d.ts │ │ ├── lib.wx.api.d.ts │ │ ├── lib.wx.app.d.ts │ │ ├── lib.wx.behavior.d.ts │ │ ├── lib.wx.cloud.d.ts │ │ ├── lib.wx.component.d.ts │ │ ├── lib.wx.event.d.ts │ │ └── lib.wx.page.d.ts └── utils │ └── request │ ├── README.md │ ├── cancel │ ├── cancel.d.ts │ ├── cancel.ts │ ├── cancelToken.d.ts │ ├── cancelToken.ts │ ├── isCancel.d.ts │ └── isCancel.ts │ ├── core.d.ts │ ├── core.ts │ ├── interceptor │ ├── addfix.d.ts │ └── addfix.ts │ ├── middleware │ ├── fetch.d.ts │ ├── fetch.ts │ ├── parseResponse.d.ts │ ├── parseResponse.ts │ ├── simpleGet.d.ts │ ├── simpleGet.ts │ ├── simplePost.d.ts │ └── simplePost.ts │ ├── onion │ ├── compose.d.ts │ ├── compose.ts │ ├── index.d.ts │ └── index.ts │ ├── request.d.ts │ ├── request.ts │ ├── utils.d.ts │ ├── utils.ts │ ├── wxfetch.d.ts │ └── wxfetch.ts ├── tsconfig.json ├── webpack-plugin ├── add-xml-loader.js ├── json-loader.js ├── page-skeleton-loader │ ├── generate.js │ ├── index.js │ ├── parse.js │ ├── readme.md │ ├── transform.js │ └── wx-template-compiler │ │ ├── index.js │ │ └── readme.md └── wxapp-components-plugin │ ├── README.md │ └── index.js └── webpack.config.babel.js /.babelrc: -------------------------------------------------------------------------------- 1 | { 2 | "presets": [ 3 | "es2020", 4 | [ 5 | "es2015", 6 | { 7 | "loose": true 8 | } 9 | ], 10 | "stage-0" 11 | ], 12 | "plugins": [ 13 | [ 14 | "transform-runtime", 15 | { 16 | "helpers": false, 17 | "polyfill": false, 18 | "regenerator": true 19 | } 20 | ] 21 | ] 22 | } 23 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | .mocks/ 2 | node_modules 3 | dist 4 | coverage 5 | .git 6 | .vscode 7 | .DS_Store 8 | /yarn.lock 9 | -------------------------------------------------------------------------------- /CHANGELOG.md: -------------------------------------------------------------------------------- 1 | # Changelog 2 | 3 | ## 2018-07-03 4 | 5 | * [UPGRADE][create-wxapp-page](https://github.com/cantonjs/create-wxapp-page) 更新至 `v2.0.8` 6 | * [UPGRADE][wxapp-webpack-plugin](https://github.com/Cap32/wxapp-webpack-plugin) 更新至 `v0.18.0` 7 | * [UPGRADE][wxml-loader](https://github.com/Cap32/wxml-loader) 更新至 `v0.2.2` 8 | 9 | ## 2018-05-24 10 | 11 | * [NEW] 内置 [copy-webpack-plugin](https://github.com/webpack-contrib/copy-webpack-plugin) 12 | * [FIXED] 修复支付宝小程序兼容问题 (8fafb9c86b9eb2f71bedd8e6b640e26e6c950b3d) 13 | * [REMOVED] 移除 `utils/bomPolyfill.js`,新版微信小程序已经支持 (a53c86e4ce9bfdffeda87328a24ed12ec593e6e3) 14 | * [REMOVED] 移除装逼但不实用的 webpack-dashboard (021da972b22db84e1989df792b15b84a9df758bb) 15 | * [UPGRADE] 更新 [eslint](https://github.com/eslint/eslint) 版本 (dff76f1f36bc5018a3c65e8cdbb9f5a755ba473f) 16 | * [UPGRADE] 更新 [jest](https://github.com/facebook/jest) 至 v21 (0c3a20bfd2e7eb31e66fc7e1a74ab5b80f6d4e21) 17 | 18 | ## 2018-03-06 19 | 20 | * [FIXED] 修复 Windows 下路径问题 ([#21](https://github.com/cantonjs/wxapp-boilerplate/issues/21)) 21 | * [UPGRADE][wxml-loader](https://github.com/Cap32/wxml-loader) 更新至 `v0.2.1` 22 | 23 | ## 2018-03-02 24 | 25 | * [UPGRADE][wxml-loader](https://github.com/Cap32/wxml-loader) 更新至 `v0.2.0` 26 | 27 | ## 2018-02-28 28 | 29 | * [UPGRADE][wxml-loader](https://github.com/Cap32/wxml-loader) 更新至 `v0.1.2` 30 | 31 | ## 2017-12-31 32 | 33 | * [FIXED] 修复打包压缩代码时 `` 的问题 34 | * [UPGRADE][create-wxapp-page](https://github.com/cantonjs/create-wxapp-page) 更新至 `v2.0.2` 35 | * [NEW] 增加 `create-component` script, 支持创建 `Component` 36 | 37 | ## 2017-12-2 38 | 39 | * [NEW] 支持自动打包 `tabbar` 图标,无需 `copy-webpack-plugin` 等额外配置 40 | * [UPGRADE][wxapp-webpack-plugin](https://github.com/Cap32/wxapp-webpack-plugin) 更新至 `v0.17.1` 41 | 42 | ## 2017-11-30 43 | 44 | * [FIXED] 修复 `yarn build` 提示 ['Component' is not defined](https://github.com/cantonjs/wxapp-boilerplate/issues/15) 问题 (@julytian) 45 | 46 | ## 2017-11-18 47 | 48 | * [NEW] 支持微信小程序 [Components](https://mp.weixin.qq.com/debug/wxadoc/dev/framework/custom-component/) 49 | * [UPGRADE][wxapp-webpack-plugin](https://github.com/Cap32/wxapp-webpack-plugin) 更新至 `v0.16.0` 50 | * [UPGRADE][node-sass](https://github.com/sass/node-sass) 更新至 `v4.6.1` 51 | * [UPGRADE][sass-loader](https://github.com/webpack-contrib/sass-loader) 更新至 `v6.0.6` 52 | 53 | ## 2017-10-27 54 | 55 | * [NEW] 增加默认采用 [webpack-dashboard](https://github.com/FormidableLabs/webpack-dashboard) 来展示 webpack 状态 56 | * [UPGRADE] webpack 更新至 `v3.8.1` 57 | * [UPGRADE][create-wxapp-page](https://github.com/cantonjs/create-wxapp-page) 更新至 `v1.2.0` 58 | 59 | ## 2017-10-26 60 | 61 | * [BREAKING] 非 `.js` (如 `.json`, `.wxss`, `.wxml`, `.png` 等等 )文件在编译后将保持原来的文件目录结构 62 | * [BREAKING] 资源文件引用也支持使用相对路径,例如 `pages/index/index.wxml` 里,可以使用相对路径 `../../templates/test.wxml` 来引用,保持小程序原生的开发行为 63 | * [FIXED] 修复最新版微信开发者工具自动检测编译时出现错误 64 | * [FIXED] 修复 `Can not resolve "vertx"` 警告 65 | 66 | ## 2017-09-22 67 | 68 | * [NEW] 支持兼容支付宝小程序 69 | * [FIXED] 修复 stylelint 错误提示 70 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # wx-typescript-cli 2 | 3 | 一个 TypeScript 的小程序脚手架。享受近乎原生的开发体验(少坑/有坑也是微信的锅)。 4 | 5 | ## 📕 TODO Welcome pr 6 | 7 | - [ ] 补充常规组件库 8 | - [ ] 完善文档 9 | - [ ] 发布到 npm 上 10 | - [ ] CI 集成 11 | - [ ] 完善全局组件 12 | - [ ] 支持云开发 13 | - [ ] 增加 git-hook 支持 14 | - [x] 支持自动化生成骨架屏,在骨架屏 loader 的基础上设计骨架屏组件~~ 15 | - [ ] 优化改进骨架屏 16 | 17 | ## 📕 Install 18 | 19 | 暂时没有集成到 npm 上 20 | 21 | ```shell 22 | 23 | git clone https://github.com/rottenpen/wx-typescript-cli.git 24 | cd wx-typescript-cli 25 | npm i //或者 yarn install 26 | 27 | ``` 28 | 29 | 提供 3 种模式 30 | 31 | 1. 开发环境 `npm run dev` 或者 `npm run start` 对应的是 HMR 的实时编译的场景需求,不会对转译的代码进行压缩。 32 | 2. 用于生成预览二维码的开发环境 `npm run build_dev` 对应的是压缩了的开发环境 33 | 3. 生产环境 `npm run build` 对应的是压缩了的生产环境 34 | 35 | 特别注意⚠️ **请在微信开发者工具上,打开 dist 目录**,而不是 src 或者当前目录!!!!! 36 | 37 | ## 🚀 Supported features 38 | 39 | - [x] 引入依赖 40 | - [x] 支持 TypeScript 以及 es-next 语法 41 | - [x] 支持在 wxss 里使用 less 42 | - [x] 支持类 axios 的网络请求开发体验 43 | - [x] 较为完善的 wx/types 44 | - [x] 自动生成骨架屏组件的 loader 45 | - [x] 自动添加全局组件的 loader 46 | - [x] 支持自动化生成骨架屏 47 | 48 | ## 🎆 Class Page 49 | 50 | 为了更好感受 TS 带来的开发体验,对 Page 开发进行魔改。(慎入!) 51 | 52 | - 需要继承 Page 的基类,来获得 type 的支持。 53 | - 需要通过全局的 component 工厂函数装饰 Class。 54 | - 可以在工厂函数中对 Class 进行处理,从而实现 Mixin 的效果。 55 | 56 | ``` TypeScript 57 | // templatePage.ts 58 | import { TmgPage } from "@/page"; 59 | 60 | interface IndexPageData { 61 | list? : any[] 62 | } 63 | 64 | const com = global['__Component'] 65 | @com() 66 | class TemplatePage extends TmgPage{ 67 | public data: IndexPageData = { 68 | list: [] 69 | } 70 | public onLoad(options) { 71 | } 72 | } 73 | ``` 74 | 75 | tips: 76 | 需要工厂函数修饰类,是因为小程序规定 page 不能传入带有构造函数的对象,所以需要对 class 进行预处理。但是这样的同时也带来了一定好处,我们可以在工厂函数对 options 对象进行 Mixin。 77 | 78 | ## 🎆 MiniProgram Types 79 | 80 | 较为齐全的小程序 Types 支持(持续更新中!) 81 | 同步于 https://github.com/wechat-miniprogram/api-typings (如果有缺漏,请pr或者如作者一样手动添加到 `src/types/index.d.ts` 里) 82 | 83 | ## 🎆 request 84 | 85 | 为 TypeScript 的小程序封装了一个类 axios 的库(基于 umi-request) 86 | 87 | ### Supported features 88 | 89 | - url 参数自动序列化 90 | - post 数据提交方式简化 91 | - response 返回处理简化 92 | - api 超时支持 93 | - api 请求缓存支持 94 | - 支持处理 gbk 95 | - 类 axios 的 request 和 response 拦截器(interceptors)支持 96 | - 统一的错误处理方式 97 | - 类 koa 洋葱机制的 use 中间件机制支持 98 | - 类 axios 的取消请求 99 | - 基于 requestTask.Abort() 的取消请求 100 | 101 | ## 👷Skeleton 102 | 103 | - 目前已完成了骨架屏 loader 的制作。 104 | - 它会根据 WXML 里的 skeleton 属性生成一个具有相同属性的 skeleton 组件。具体内容在[readme.md](./webpack-plugin/page-skeleton-loader/readme.md) 105 | - 已初步完成骨架屏组件 106 | 107 | ![关闭骨架屏时](./src/images/screenshot2.png) 108 | ![打开骨架屏时](./src/images/screenshot.png) 109 | 110 | ### template 111 | 112 | ```html 113 | /// 源代码 114 | 115 | var msg = "hello world"; 116 | 117 | module.exports.message = msg; 118 | 119 | 120 | 欢迎使用 wx-typescript-cli 121 | 122 | 123 | 124 | 125 | /// 编译后 126 | 127 | 128 | var msg = "hello world"; 129 | 130 | module.exports.message = msg; 131 | 132 | 133 | 134 | 135 | 136 | 欢迎使用 wx-typescript-cli 137 | 138 | 139 | 140 | 141 | 144 | 145 | 148 | 149 | 150 | 151 | 152 | 153 | 154 | 155 | 156 | 157 | ``` 158 | 159 | ## 💐 Thanks 160 | 161 | - wx-request 灵感来自[umi-request](https://github.com/umijs/umi-request) 162 | - 小程序文件处理 plugin 灵感来自[wxapp-webpack-plugin](https://github.com/Cap32/wxapp-webpack-plugin) 163 | 164 | ## 👷 Code Contributors 165 | 166 | @rottenpen 167 | @XLinzexin 168 | 169 | ## LICENSE 170 | 171 | MIT 172 | -------------------------------------------------------------------------------- /appveyor.yml: -------------------------------------------------------------------------------- 1 | # fix line endings on Windows and checkout all strings with \r\n 2 | init: 3 | - git config --global core.autocrlf true 4 | 5 | # Test against this version of Node.js 6 | environment: 7 | matrix: 8 | # node.js 9 | - nodejs_version: "8" 10 | - nodejs_version: "7" 11 | - nodejs_version: "6" 12 | - nodejs_version: "5" 13 | - nodejs_version: "4" 14 | 15 | platform: 16 | - x86 17 | - x64 18 | 19 | # Install scripts. (runs after repo cloning) 20 | install: 21 | # Get the latest stable version of Node.js or io.js 22 | - ps: Install-Product node $env:nodejs_version 23 | # install modules 24 | - npm i 25 | 26 | 27 | # Post-install test scripts. 28 | test_script: 29 | # Output useful info for debugging 30 | - node --version && npm --version 31 | # run tests 32 | - npm test 33 | 34 | # Don't actually build. 35 | build: off 36 | 37 | matrix: 38 | fast_finish: true 39 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "wx-typescript-cli", 3 | "version": "0.1.0", 4 | "description": "微信小程序 TypeScript 脚手架", 5 | "private": true, 6 | "scripts": { 7 | "start": "webpack --watch --progress --mode development", 8 | "dev": "webpack --watch --progress --mode development", 9 | "build": "NODE_ENV=production webpack --mode production ", 10 | "build_dev": "webpack --mode production ", 11 | "test": "jest", 12 | "version": "webpack -v" 13 | }, 14 | "main": "dist/app.js", 15 | "author": "rottenpen", 16 | "license": "MIT", 17 | "engines": { 18 | "node": ">=4" 19 | }, 20 | "devDependencies": { 21 | "@babel/core": "^7.4.4", 22 | "@babel/preset-env": "^7.4.4", 23 | "@tinajs/wxml-loader": "^0.3.0-fork.0", 24 | "@typescript-eslint/eslint-plugin": "^1.7.0", 25 | "@vue/eslint-config-standard": "^4.0.0", 26 | "@vue/eslint-config-typescript": "^4.0.0", 27 | "babel-core": "^6.26.3", 28 | "babel-eslint": "^10.0.1", 29 | "babel-jest": "21.x", 30 | "babel-loader": "^7.1.5", 31 | "babel-minify-webpack-plugin": "^0.3.1", 32 | "babel-plugin-lodash": "^3.3.4", 33 | "babel-plugin-transform-runtime": "^6.23.0", 34 | "babel-preset-env": "^1.7.0", 35 | "babel-preset-es2015": "^6.24.0", 36 | "babel-preset-es2020": "^1.0.2", 37 | "babel-preset-stage-0": "^6.22.0", 38 | "babel-runtime": "^6.23.0", 39 | "copy-webpack-plugin": "^4.6.0", 40 | "create-wxapp-page": "^2.0.8", 41 | "cross-env": "^5.0.1", 42 | "eslint": "^5.16.0", 43 | "eslint-config-alloy": "^2.0.0-alpha.2", 44 | "eslint-config-cantonjs": "^1.0.0", 45 | "eslint-config-standard": "^11.0.0", 46 | "eslint-import-resolver-webpack": "^0.10.0", 47 | "eslint-loader": "^2.1.2", 48 | "eslint-plugin-import": "^2.16.0", 49 | "eslint-plugin-jest": "^21.15.2", 50 | "eslint-plugin-node": "^6.0.1", 51 | "eslint-plugin-promise": "^3.7.0", 52 | "eslint-plugin-react": "^7.8.2", 53 | "eslint-plugin-standard": "^3.1.0", 54 | "extract-text-webpack-plugin": "^4.0.0-beta.0", 55 | "file-loader": "^1.1.11", 56 | "glob": "^7.1.2", 57 | "jest": "21.x", 58 | "json-loader": "^0.5.7", 59 | "less": "^3.7.1", 60 | "less-loader": "^4.1.0", 61 | "npm-run-all": "^4.1.1", 62 | "prettier-eslint-cli": "^4.7.0", 63 | "resolve-url-loader": "^2.3.2", 64 | "rimraf": "^2.6.1", 65 | "source-map-loader": "^0.2.4", 66 | "stylelint": "^8.0.0", 67 | "stylelint-config-standard": "^17.0.0", 68 | "stylelint-scss": "^1.4.4", 69 | "stylelint-webpack-plugin": "^0.9.0", 70 | "ts-loader": "^5.3.3", 71 | "tslib": "^1.11.1", 72 | "webpack": "^4.30.0", 73 | "webpack-cli": "^3.3.0", 74 | "wxml-loader": "^0.3.0" 75 | }, 76 | "dependencies": { 77 | "@types/node": "^13.13.5", 78 | "@vue/component-compiler-utils": "^3.1.2", 79 | "dayjs": "^1.8.14", 80 | "es6-promise": "^4.1.0", 81 | "fs-extra": "^3.0.1", 82 | "globby": "^6.1.0", 83 | "js-base64": "^2.4.9", 84 | "lodash": "^4.17.15", 85 | "typescript": "^3.9.2", 86 | "vue-template-compiler": "^2.6.11", 87 | "webpack-sources": "^0.2.3" 88 | }, 89 | "jest": { 90 | "modulePathIgnorePatterns": [ 91 | "node_modules", 92 | "lib" 93 | ] 94 | }, 95 | "copyWebpack": [ 96 | "images" 97 | ] 98 | } 99 | -------------------------------------------------------------------------------- /src/_template_page/index.d.ts: -------------------------------------------------------------------------------- 1 | export {}; 2 | -------------------------------------------------------------------------------- /src/_template_page/index.json: -------------------------------------------------------------------------------- 1 | {} -------------------------------------------------------------------------------- /src/_template_page/index.ts: -------------------------------------------------------------------------------- 1 | import { TmgPage } from "@/typings/page"; 2 | import ajax from '@/api/wxfetch' 3 | interface IndexPageData { 4 | list? : any[] 5 | skeletonShow: boolean 6 | } 7 | /** 8 | * 定义 page 类 9 | */ 10 | const com = global['__Component'] 11 | @com() 12 | class TemplatePage extends TmgPage{ 13 | public data: IndexPageData = { 14 | list: ['a'], 15 | skeletonShow: true 16 | } 17 | /** 18 | * onLoad 19 | */ 20 | public onLoad() { 21 | let data = { 22 | name: 'Tom' 23 | } 24 | this.getUser({data}).then(res => { 25 | console.log(res) 26 | }) 27 | } 28 | /** 29 | * getUser 30 | */ 31 | public getUser(options) { 32 | let CancelToken = ajax.CancelToken 33 | let source = CancelToken.source() 34 | options.cancelToken = source.token 35 | let p = ajax.post('/users/', options) 36 | // source.cancel('???') 37 | return p 38 | } 39 | /** 40 | * showToast 41 | */ 42 | public showToast(e: WXEvent): void { 43 | } 44 | public onTapSearchBtn(e: WXEvent): void { 45 | } 46 | /** 47 | * onCancel 48 | */ 49 | public onCancel(e: WXEvent): void { 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /src/_template_page/index.wxml: -------------------------------------------------------------------------------- 1 | 2 | var msg = "hello world"; 3 | 4 | module.exports.message = msg; 5 | 6 | 7 | 欢迎使用 wx-typescript-cli 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /src/_template_page/index.wxss: -------------------------------------------------------------------------------- 1 | .heading { 2 | width: 600rpx; 3 | height: 40rpx; 4 | font-size: 34rpx; 5 | line-height: 40rpx; 6 | } 7 | .confirm { 8 | display: block; 9 | width: 200rpx; 10 | height: 100rpx; 11 | } -------------------------------------------------------------------------------- /src/api/index.d.ts: -------------------------------------------------------------------------------- 1 | export declare function getHotCity(options: any): any; 2 | export declare function postSearch(options: any): any; 3 | -------------------------------------------------------------------------------- /src/api/index.ts: -------------------------------------------------------------------------------- 1 | import ajax from "./wxfetch"; 2 | 3 | export function getHotCity(options) { 4 | const url = '/location/hot_city' 5 | return ajax.get(url, options) 6 | } 7 | 8 | export function postSearch(options) { 9 | const url = '/airshop/search' 10 | return ajax.post(url, options) 11 | } 12 | -------------------------------------------------------------------------------- /src/api/wxfetch.d.ts: -------------------------------------------------------------------------------- 1 | declare let ajax: any; 2 | export default ajax; 3 | -------------------------------------------------------------------------------- /src/api/wxfetch.ts: -------------------------------------------------------------------------------- 1 | import { extend } from '@/utils/request/request'; 2 | const errorHandler = function (error) { 3 | const codeMap = { 4 | '-1': '发生错误啦', 5 | }; 6 | if (error.response) { 7 | console.log(error.response.status); 8 | console.log(error.response.headers); 9 | console.log(error.data); 10 | console.log(error.request); 11 | console.log(codeMap[error.data.status]) 12 | } else { 13 | console.log(error.message); 14 | } 15 | throw error; 16 | } 17 | /** 创建实例 */ 18 | function createRequest(baseUrl) { 19 | const request = extend({ 20 | prefix: baseUrl, 21 | errorHandler 22 | }); 23 | return request; 24 | } 25 | 26 | let ajax:any = createRequest('http://localhost:3000') 27 | /** request拦截器 */ 28 | ajax.interceptors.request.use((url, options) => { 29 | return ( 30 | { 31 | url: `${url}`, 32 | options: { ...options, interceptors: true }, 33 | } 34 | ) 35 | }) 36 | /** response拦截器 */ 37 | ajax.interceptors.response.use((res, req) => { 38 | return res.data 39 | }) 40 | export default ajax -------------------------------------------------------------------------------- /src/app.d.ts: -------------------------------------------------------------------------------- 1 | export {}; 2 | -------------------------------------------------------------------------------- /src/app.json: -------------------------------------------------------------------------------- 1 | { 2 | "pages": [ 3 | "_template_page/index" 4 | ], 5 | "usingComponents": { 6 | "skeleton": "components/skeleton/index", 7 | "skeleton-group": "components/skeleton-group/index", 8 | "skeleton-item": "components/skeleton-item/index" 9 | }, 10 | "subPackages": [], 11 | "tabBar": { 12 | "color": "#C4C4C4", 13 | "selectedColor": "#7AC143", 14 | "backgroundColor": "#fff", 15 | "borderStyle": "black", 16 | "list": [ 17 | { 18 | "pagePath": "_template_page/index", 19 | "text": "主页" 20 | }, 21 | { 22 | "pagePath": "_template_page/index", 23 | "text": "主页" 24 | } 25 | ], 26 | "position": "bottom" 27 | }, 28 | "window": { 29 | "backgroundTextStyle": "light", 30 | "navigationBarBackgroundColor": "#fff", 31 | "navigationBarTextStyle": "black", 32 | "navigationBarTitleText": "" 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /src/app.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * @Author: rotten 3 | * @Date: 2019-07-30 16:53:23 4 | * @Last Modified by: rotten 5 | * @Last Modified time: 2020-06-04 16:59:19 6 | */ 7 | 8 | import { Component, View } from "@/lib/class-component/page"; 9 | Object.assign(global, { __Component: Component }) // 把处理page的工厂函数塞到 global 里,便于全局使用 10 | 11 | App({ 12 | onLaunch (options): void{ 13 | }, 14 | globalData: { 15 | } 16 | }) 17 | -------------------------------------------------------------------------------- /src/app.wxss: -------------------------------------------------------------------------------- 1 | /* 引入该文件,文件被引用才会被webpack编译。但是不编译到当前文件,只是单纯引用 */ 2 | @import (reference, optional, less) "style/common.wxss"; 3 | /* 当做css的import使用 */ 4 | @import (css) "style/common.wxss"; 5 | 6 | page { 7 | background: #ffffff; 8 | width: 100%; 9 | overflow-x: hidden; 10 | min-height: 100vh; 11 | font-family: "Helvetica Neue",Helvetica,Arial, sans-serif,"Microsoft YaHei New", "Microsoft YaHei", "微软雅黑", "宋体", SimSun, STXihei, "华文细黑" 12 | } 13 | page::after { 14 | content: "."; 15 | width: 100%; 16 | height: 1rpx; 17 | background: #ffffff; 18 | position: fixed; 19 | top: 0; 20 | left: 0; 21 | z-index: 99999; 22 | overflow: hidden; 23 | } 24 | view[hidden] { 25 | display: none !important; 26 | } 27 | /* scroll样式 */ 28 | scroll-view ::-webkit-scrollbar { 29 | width: 0; 30 | height: 0; 31 | color: transparent; 32 | } 33 | 34 | /* 默认样式 */ 35 | page { 36 | font-size: 24rpx; 37 | } 38 | image { 39 | position: relative; 40 | z-index: 0; 41 | display: block; 42 | width: 100%; 43 | height: 100%; 44 | } 45 | page, 46 | view, 47 | block, 48 | image, 49 | navigator, 50 | swiper, 51 | swiper-item, 52 | scroll-view { 53 | box-sizing: border-box; 54 | -moz-box-sizing: border-box; 55 | -webkit-box-sizing: border-box; 56 | } 57 | view.hide { 58 | display: none !important; 59 | } 60 | /* flex布局相关 */ 61 | .flex { 62 | display: flex; 63 | flex-direction: column; 64 | align-items: center; 65 | justify-content: center; 66 | } 67 | -------------------------------------------------------------------------------- /src/components/skeleton-group/index.d.ts: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/components/skeleton-group/index.d.ts -------------------------------------------------------------------------------- /src/components/skeleton-group/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "component": true, 3 | "usingComponents": {} 4 | } -------------------------------------------------------------------------------- /src/components/skeleton-group/index.ts: -------------------------------------------------------------------------------- 1 | Component({ 2 | properties: { 3 | }, 4 | data: { 5 | }, 6 | pageLifetimes: { 7 | // 组件所在页面的生命周期函数 8 | show: function () { }, 9 | hide: function () { }, 10 | resize: function () { }, 11 | }, 12 | methods: { 13 | } 14 | }) -------------------------------------------------------------------------------- /src/components/skeleton-group/index.wxml: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /src/components/skeleton-group/index.wxss: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/components/skeleton-group/index.wxss -------------------------------------------------------------------------------- /src/components/skeleton-group/readme.md: -------------------------------------------------------------------------------- 1 | # skeleton-group 2 | 3 | 理论上 skeleton-group 只是一个用来复刻样式的组件,不带任何样式 4 | -------------------------------------------------------------------------------- /src/components/skeleton-item/index.d.ts: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/components/skeleton-item/index.d.ts -------------------------------------------------------------------------------- /src/components/skeleton-item/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "component": true, 3 | "usingComponents": {} 4 | } -------------------------------------------------------------------------------- /src/components/skeleton-item/index.ts: -------------------------------------------------------------------------------- 1 | Component({ 2 | properties: { 3 | }, 4 | data: { 5 | }, 6 | pageLifetimes: { 7 | // 组件所在页面的生命周期函数 8 | show: function () { }, 9 | hide: function () { }, 10 | resize: function () { }, 11 | }, 12 | methods: { 13 | } 14 | }) -------------------------------------------------------------------------------- /src/components/skeleton-item/index.wxml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /src/components/skeleton-item/index.wxss: -------------------------------------------------------------------------------- 1 | .skeleton-item { 2 | width: 100%; 3 | height: 100%; 4 | background-color: rgb(194, 207, 214)!important; 5 | box-sizing: border-box; 6 | border: 5rpx solid #ffffff; 7 | } -------------------------------------------------------------------------------- /src/components/skeleton/index.d.ts: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/components/skeleton/index.d.ts -------------------------------------------------------------------------------- /src/components/skeleton/index.json: -------------------------------------------------------------------------------- 1 | { 2 | "component": true, 3 | "usingComponents": {} 4 | } -------------------------------------------------------------------------------- /src/components/skeleton/index.ts: -------------------------------------------------------------------------------- 1 | Component({ 2 | properties: { 3 | }, 4 | data: { 5 | }, 6 | pageLifetimes: { 7 | // 组件所在页面的生命周期函数 8 | show: function () { }, 9 | hide: function () { }, 10 | resize: function () { }, 11 | }, 12 | methods: { 13 | } 14 | }) -------------------------------------------------------------------------------- /src/components/skeleton/index.wxml: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /src/components/skeleton/index.wxss: -------------------------------------------------------------------------------- 1 | .skeleton { 2 | position: fixed; 3 | z-index: 9999; 4 | display: flex; 5 | flex-direction: column; 6 | align-items: center; 7 | width: 100vw!important; 8 | height: 100vh!important; 9 | bottom: 0!important; 10 | left: 0!important; 11 | background-color: #ffffff!important; 12 | } -------------------------------------------------------------------------------- /src/images/logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/images/logo.png -------------------------------------------------------------------------------- /src/images/screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/images/screenshot.png -------------------------------------------------------------------------------- /src/images/screenshot2.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/rottenpen/wx-typescript-cli/dde87b1689e6aee1100d7af2ab5871454e771b7e/src/images/screenshot2.png -------------------------------------------------------------------------------- /src/lib/class-component/component.d.ts: -------------------------------------------------------------------------------- 1 | import { View } from "./page"; 2 | export declare type ViewClass = typeof View; 3 | export declare const $internalHooks: string[]; 4 | declare function Component(options?: any): any; 5 | export default Component; 6 | -------------------------------------------------------------------------------- /src/lib/class-component/component.ts: -------------------------------------------------------------------------------- 1 | 2 | import { View } from "./page"; 3 | export type ViewClass = typeof View; 4 | 5 | export const $internalHooks = [ 6 | "data", 7 | "onLoad", 8 | "onReady", 9 | "onShow", 10 | "onHide", 11 | "onUnload", 12 | "onPullDownRefresh", 13 | "onReachBottom", 14 | "onShareAppMessage", 15 | "onPageScroll", 16 | "onTabItemTap", 17 | ]; 18 | 19 | function componentFactory( 20 | Cm: ViewClass, 21 | options: any 22 | ): ViewClass { 23 | 24 | const proto = Cm.prototype; 25 | 26 | Object.getOwnPropertyNames(proto).forEach((key): void => { 27 | if (key === "constructor") { 28 | return; 29 | } 30 | 31 | options[key] = proto[key]; 32 | }); 33 | 34 | const data = new Cm().data; 35 | if (data) { 36 | 37 | const plainData = options.data || {}; 38 | Object.keys(data).forEach((key): void => { 39 | if (data[key] !== undefined) { 40 | plainData[key] = data[key]; 41 | } 42 | }); 43 | options.data = plainData as S; 44 | } 45 | 46 | !options.onShareAppMessage && (options.onShareAppMessage = function (): any { 47 | return { 48 | title: '嘉盛真实账户申请', 49 | imageUrl: '/images/sharelogo.jpg', 50 | path: 'pages/main/home/index' 51 | } 52 | }) 53 | Page(options); 54 | return Cm; 55 | } 56 | 57 | function Component(options: any = {}): any { 58 | // console.log(options) 59 | if (typeof options === "function") { 60 | return componentFactory(options, undefined); 61 | } 62 | return (Cm: ViewClass): any => { 63 | return componentFactory(Cm, options); 64 | }; 65 | } 66 | 67 | export default Component; -------------------------------------------------------------------------------- /src/lib/class-component/page.d.ts: -------------------------------------------------------------------------------- 1 | export declare class View { 2 | data: S; 3 | onLoad?(options: any): void; 4 | onReady?(): void; 5 | onShow?(): void; 6 | onHide?(): void; 7 | onUnload?(): void; 8 | onPullDownRefresh?(): void; 9 | onReachBottom?(): void; 10 | onShareAppMessage?(): void; 11 | onPageScroll?(): void; 12 | onTabItemTap?(item: any): void; 13 | } 14 | export { default as Component } from "./component"; 15 | -------------------------------------------------------------------------------- /src/lib/class-component/page.ts: -------------------------------------------------------------------------------- 1 | export class View { 2 | public data: S; 3 | public onLoad?(options: any): void; 4 | public onReady?(): void; 5 | public onShow?(): void; 6 | public onHide?(): void; 7 | public onUnload?(): void; 8 | public onPullDownRefresh?(): void; 9 | public onReachBottom?(): void; 10 | public onShareAppMessage?(): void; 11 | public onPageScroll?(): void; 12 | public onTabItemTap?(item: any): void; 13 | } 14 | 15 | export { default as Component } from "./component"; -------------------------------------------------------------------------------- /src/sitemap.json: -------------------------------------------------------------------------------- 1 | { 2 | "rules":[{ 3 | "action": "allow", 4 | "page": "*" 5 | }] 6 | } -------------------------------------------------------------------------------- /src/style/common.wxss: -------------------------------------------------------------------------------- 1 | @import "./main.less"; 2 | @import "./font.less"; 3 | .scroll-H { 4 | white-space: nowrap; 5 | } 6 | .scroll-H .scroll-item { 7 | display: inline-block; 8 | } 9 | /* 字体大小及行高 */ 10 | .fs38 { 11 | font-size: 38rpx !important; 12 | line-height: 54rpx; 13 | height: 54rpx; 14 | } 15 | .lh38 { 16 | line-height: 38rpx !important; 17 | } 18 | .fs32 { 19 | font-size: 32rpx !important; 20 | line-height: 46rpx; 21 | height: 46rpx; 22 | } 23 | .lh32 { 24 | line-height: 32rpx !important; 25 | } 26 | .fs28 { 27 | font-size: 28rpx !important; 28 | line-height: 40rpx; 29 | height: 40rpx; 30 | } 31 | .lh28 { 32 | line-height: 28rpx !important; 33 | } 34 | .fs26 { 35 | font-size: 26rpx !important; 36 | line-height: 36rpx; 37 | height: 36rpx; 38 | } 39 | .lh26 { 40 | line-height: 26rpx !important; 41 | } 42 | .fs24 { 43 | font-size: 24rpx !important; 44 | line-height: 32rpx; 45 | height: 32rpx; 46 | } 47 | .lh24 { 48 | line-height: 24rpx !important; 49 | } 50 | .fs22 { 51 | font-size: 22rpx !important; 52 | line-height: 30rpx; 53 | height: 30rpx; 54 | } 55 | .lh22 { 56 | line-height: 22rpx !important; 57 | } 58 | .fcmain1 { 59 | color: @primary-color!important; 60 | } 61 | .fcmain2 { 62 | color: @primary-color!important; 63 | } 64 | // .fcmain2 { 65 | // color: @secondary-color!important; 66 | // } 67 | .fcerror { 68 | color: @error-color!important; 69 | } 70 | .fclight { 71 | color: @error-color!important; 72 | } 73 | .fcwarn { 74 | color: @warn-color!important; 75 | } 76 | .fc44 { 77 | color: #444 !important; 78 | } 79 | .fc88 { 80 | color: #888 !important; 81 | } 82 | .fccc { 83 | color: #ccc !important; 84 | } 85 | /* 圆角 */ 86 | @radius8: 8rpx; 87 | @radius4: 4rpx; 88 | //弹窗的圆角 89 | .popup-radius { 90 | border-radius: @radius8; 91 | } 92 | //普通容器的圆角 93 | .box-radius { 94 | border-radius: @radius4; 95 | } 96 | .clear { 97 | &::after { 98 | content: "."; 99 | color: transparent; 100 | height: 0; 101 | overflow: hidden; 102 | clear: both; 103 | } 104 | } 105 | -------------------------------------------------------------------------------- /src/style/main.less: -------------------------------------------------------------------------------- 1 | /* 颜色 */ 2 | // @primary-color: #c1916c; 3 | @primary-color: #3a84ff; 4 | @secondary-color: #4ba7f9; 5 | @error-color :#E73333; 6 | @light-color: #ff501f; 7 | @warn-color: #fcba3b; 8 | 9 | @bg-text-primary: #444444; 10 | @bg-text-regular: #888888; 11 | @bg-text-secondary : #cccccc; 12 | 13 | /* 主图色 */ 14 | @background-color: #f9f9f9; 15 | -------------------------------------------------------------------------------- /src/style/progress.less: -------------------------------------------------------------------------------- 1 | .page{ 2 | .header{ 3 | width: 100vw; 4 | image { 5 | width: 100vw; 6 | } 7 | } 8 | } -------------------------------------------------------------------------------- /src/style/result.less: -------------------------------------------------------------------------------- 1 | .page { 2 | width: 100vw; 3 | height: calc(100vh - 240rpx); 4 | position: relative; 5 | display: flex; 6 | justify-content: space-between; 7 | flex-direction: column; 8 | align-items: center; 9 | .icon { 10 | width: 140rpx; 11 | height: 140rpx; 12 | margin-top: 80rpx; 13 | margin-bottom: 58rpx; 14 | } 15 | .btblock { 16 | // position: absolute; 17 | // bottom: 30rpx; 18 | display: flex; 19 | align-items: center; 20 | flex-direction: row; 21 | justify-content: center; 22 | // align-items: flex-end; 23 | border-radius: 6rpx; 24 | background-color: #0ab45b; 25 | width: 690rpx; 26 | height: 92rpx; 27 | } 28 | .btinfo { 29 | max-width: 666rpx; 30 | overflow: hidden; 31 | text-align: center; 32 | text-overflow: ellipsis; 33 | line-height: 40rpx; 34 | white-space: pre; 35 | color: #ffffff; 36 | font-size: 28rpx; 37 | font-weight: 400; 38 | } 39 | .item { 40 | display:flex; 41 | width:100vw; 42 | justify-content:flex-end; 43 | flex-direction:column; 44 | align-items:center; 45 | margin-bottom: 80rpx; 46 | } 47 | .copyright { 48 | color: rgb(153, 153, 153); 49 | font-size: 20rpx; 50 | line-height: 28rpx; 51 | margin-bottom: 40rpx; 52 | } 53 | } -------------------------------------------------------------------------------- /src/typings/index.d.ts: -------------------------------------------------------------------------------- 1 | /*! ***************************************************************************** 2 | Copyright (c) 2018 Tencent, Inc. All rights reserved. 3 | 4 | Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: 5 | 6 | The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. 7 | 8 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 9 | ***************************************************************************** */ 10 | 11 | /// 12 | /// 13 | 14 | // declare class TmgPage { 15 | // public setData: (obj: any, cb?: () => void) => void 16 | // public readonly __proto__: any 17 | // } 18 | interface WXTarget { 19 | id: string; 20 | dataset: any; 21 | offsetLeft: number; 22 | offsetTop: number; 23 | } 24 | 25 | /** 微信绑定事件的回调 */ 26 | interface WXEvent { 27 | /** 点击事件 详情 */ 28 | detail: any; 29 | currentTarget: WXTarget; 30 | target: WXTarget; 31 | type?: string; 32 | timeStamp?: number; 33 | touches?: any[]; 34 | } 35 | // eslint-disable-next-line 36 | interface global { 37 | /** 实际上并不存在 URLSearchParams */ 38 | URLSearchParams? :any, 39 | __Component: (options?: any) => any; 40 | } 41 | // eslint-disable-next-line 42 | interface window { 43 | /** 实际上并不存在 URLSearchParams */ 44 | URLSearchParams? :any, 45 | } 46 | declare const window: window; 47 | declare const global: global; 48 | // export = TmgPage; 49 | // eslint-disable-next-line @typescript-eslint/class-name-casing 50 | interface __wxConfig { 51 | page: any; 52 | } 53 | 54 | declare const __wxConfig; -------------------------------------------------------------------------------- /src/typings/page.d.ts: -------------------------------------------------------------------------------- 1 | declare type Record = { 2 | [P in K]: T; 3 | }; 4 | declare type IAnyObject = Record; 5 | interface IPageScrollOption { 6 | /** 页面在垂直方向已滚动的距离(单位px) */ 7 | scrollTop: number; 8 | } 9 | interface ICustomShareContent { 10 | /** 转发标题。默认值:当前小程序名称 */ 11 | title?: string; 12 | /** 转发路径,必须是以 / 开头的完整路径。默认值:当前页面 path */ 13 | path?: string; 14 | /** 自定义图片路径,可以是本地文件路径、代码包文件路径或者网络图片路径。支持PNG及JPG。显示图片长宽比是 5:4,最低基础库: `1.5.0`。默认值:使用默认截图 */ 15 | imageUrl?: string; 16 | } 17 | interface IShareAppMessageOption { 18 | /** 转发事件来源。 19 | * 20 | * 可选值: 21 | * - `button`:页面内转发按钮; 22 | * - `menu`:右上角转发菜单。 23 | * 24 | * 最低基础库: `1.2.4` 25 | */ 26 | from: 'button' | 'menu' | string; 27 | /** 如果 `from` 值是 `button`,则 `target` 是触发这次转发事件的 `button`,否则为 `undefined` 28 | * 29 | * 最低基础库: `1.2.4` */ 30 | target: any; 31 | /** 页面中包含``组件时,返回当前``的url 32 | * 33 | * 最低基础库: `1.6.4` 34 | */ 35 | webViewUrl?: string; 36 | } 37 | interface ITabItemTapOption { 38 | /** 被点击tabItem的序号,从0开始,最低基础库: `1.9.0` */ 39 | index: string; 40 | /** 被点击tabItem的页面路径,最低基础库: `1.9.0` */ 41 | pagePath: string; 42 | /** 被点击tabItem的按钮文字,最低基础库: `1.9.0` */ 43 | text: string; 44 | } 45 | /** 页面状态 */ 46 | /** 47 | * Page 基类 48 | */ 49 | export declare class TmgPage { 50 | /** 页面的初始数据 51 | * 52 | * `data` 是页面第一次渲染使用的**初始数据**。 53 | * 54 | * 页面加载时,`data` 将会以`JSON`字符串的形式由逻辑层传至渲染层,因此`data`中的数据必须是可以转成`JSON`的类型:字符串,数字,布尔值,对象,数组。 55 | * 56 | * 渲染层可以通过 `WXML` 对数据进行绑定。 57 | */ 58 | data?: D; 59 | /** `setData` 函数用于将数据从逻辑层发送到视图层(异步),同时改变对应的 `this.data` 的值(同步)。 60 | * 61 | * **注意:** 62 | * 63 | * 1. **直接修改 this.data 而不调用 this.setData 是无法改变页面的状态的,还会造成数据不一致**。 64 | * 1. 仅支持设置可 JSON 化的数据。 65 | * 1. 单次设置的数据不能超过1024kB,请尽量避免一次设置过多的数据。 66 | * 1. 请不要把 data 中任何一项的 value 设为 `undefined` ,否则这一项将不被设置并可能遗留一些潜在问题。 67 | */ 68 | /** 69 | * setData 70 | */ 71 | setData?( 72 | /** 这次要改变的数据 73 | * 74 | * 以 `key: value` 的形式表示,将 `this.data` 中的 `key` 对应的值改变成 `value`。 75 | * 76 | * 其中 `key` 可以以数据路径的形式给出,支持改变数组中的某一项或对象的某个属性,如 `array[2].message`,`a.b.c.d`,并且不需要在 this.data 中预先定义。 77 | */ 78 | data: D | Pick | IAnyObject, 79 | /** setData引起的界面更新渲染完毕后的回调函数,最低基础库: `1.5.0` */ 80 | callback?: () => void): void; 81 | /** 到当前页面的路径,类型为`String`。最低基础库: `1.2.0` */ 82 | route?: string; 83 | readonly __proto__: any; 84 | /** 生命周期回调—监听页面加载 85 | * 86 | * 页面加载时触发。一个页面只会调用一次,可以在 onLoad 的参数中获取打开当前页面路径中的参数。 87 | */ 88 | onLoad?( 89 | /** 打开当前页面路径中的参数 */ 90 | query?: { 91 | [queryKey: string]: string; 92 | }): void; 93 | /** 生命周期回调—监听页面显示 94 | * 95 | * 页面显示/切入前台时触发。 96 | */ 97 | onShow?(): void; 98 | /** 生命周期回调—监听页面初次渲染完成 99 | * 100 | * 页面初次渲染完成时触发。一个页面只会调用一次,代表页面已经准备妥当,可以和视图层进行交互。 101 | * 102 | 103 | * 注意:对界面内容进行设置的 API 如`wx.setNavigationBarTitle`,请在`onReady`之后进行。 104 | */ 105 | onReady?(): void; 106 | /** 生命周期回调—监听页面隐藏 107 | * 108 | * 页面隐藏/切入后台时触发。 如 `navigateTo` 或底部 `tab` 切换到其他页面,小程序切入后台等。 109 | */ 110 | onHide?(): void; 111 | /** 生命周期回调—监听页面卸载 112 | * 113 | * 页面卸载时触发。如`redirectTo`或`navigateBack`到其他页面时。 114 | */ 115 | onUnload?(): void; 116 | /** 监听用户下拉动作 117 | * 118 | * 监听用户下拉刷新事件。 119 | * - 需要在`app.json`的`window`选项中或页面配置中开启`enablePullDownRefresh`。 120 | * - 可以通过`wx.startPullDownRefresh`触发下拉刷新,调用后触发下拉刷新动画,效果与用户手动下拉刷新一致。 121 | * - 当处理完数据刷新后,`wx.stopPullDownRefresh`可以停止当前页面的下拉刷新。 122 | */ 123 | onPullDownRefresh?(): void; 124 | /** 页面上拉触底事件的处理函数 125 | * 126 | * 监听用户上拉触底事件。 127 | * - 可以在`app.json`的`window`选项中或页面配置中设置触发距离`onReachBottomDistance`。 128 | * - 在触发距离内滑动期间,本事件只会被触发一次。 129 | */ 130 | onReachBottom?(): void; 131 | /** 用户点击右上角转发 132 | * 133 | * 监听用户点击页面内转发按钮(`