project.config.json
:项目配置文件, 比如项目名称、appid等 ; 配置详情sitemap.json
:小程序搜索相关的;配置详情app.json:
全局配置page.json
:页面配置;app.js
可共享全局属性值pages:
页面路径列表
window:
全局的默认窗口展示
tabBar:
顶部tab栏的展示{
"pages": [
"pages/home/home"
],
"window": {
"backgroundTextStyle": "dark",
"navigationBarBackgroundColor": "#f6f866",
"navigationBarTitleText": "Weixin",
"navigationBarTextStyle": "black"
},
"tabBar": {
"color": "#777",
"selectedColor": "#1cb9ce",
"list": [{
"pagePath": "pages/home/home",
"text": "主页面”},
{
"pagePath": "pages/day02/day02",
"text": "home"
}
]
},
"style": "v2",
"sitemapLocation": "sitemap.json"
}
同时每一个小程序页面也可以使用 .json
文件来对本页面的窗口表现进行配置。
app.json 的 window
中相同的配置项{
"usingComponents": {},
"navigationBarTitleText": "主页面",
"backgroundTextStyle": "dark", 背景文字颜色
"enablePullDownRefresh": true, 允许下拉刷新
"backgroundColor":"#f70", 背景颜色
"onReachBottomDistance": 100 距离底部多少触发事件
}
// 下拉刷新, 获取最新的数据
onPullDownRefresh() {
console.log('监听下拉刷新');
// 停止下拉刷新
setTimeout(() => {
// 异步请求
wx.stopPullDownRefresh({
success: (res) => {
console.log('停止', res)
},
})
}, 1000)
},
// 监听页面滚动到底部
onReachBottom() {
console.log('滚动到底部多少距离时加载更多~~ 100px');
this.setData({
listCounter: this.data.listCounter + 30
})
}
作用一:
scene
值作用二:定义全局App的数据
app.js
// app实例可以共享全局数据
globalData: {
userInfo: null,
token: 'Afjwt-12mandak-45'
}
home.js
onLoad() {
const {
globalData
} = getApp() // 全局的app实例
console.log(globalData.token);
// 拿到token发送网络请求-页面初始化
this.setData({
globalData
})
},
作用三:生命周期函数
{
"pages": [
"pages/hone/hone",
"pages/Profile/Profile",
"pages/experience/experience",
"pages/skill/skill",
"pages/index/index",
"pages/logs/logs"
],
"tabBar":{
"color": "#777",
"selectedColor": "#1cb9ce",
"list":[
{"pagePath": "pages/hone/hone","text":"简历信息","iconPath": "/pages/img/icon08.png","selectedIconPath": "/pages/img/icon08.png"},
{"pagePath": "pages/skill/skill","text":"个人技能","iconPath": "/pages/img/icon04.png","selectedIconPath": "/pages/img/icon04.png"},
{"pagePath": "pages/experience/experience","text":"项目经历","iconPath": "/pages/img/icon02.png","selectedIconPath": "/pages/img/icon02.png"},
{"pagePath": "pages/Profile/Profile","text":"自我评价","iconPath": "/pages/img/icon06.png","selectedIconPath": "/pages/img/icon06.png"}
]
},
"window": {
"backgroundTextStyle": "light",
"navigationBarBackgroundColor": "#fff",
"navigationBarTitleText": "Weixin",
"navigationBarTextStyle": "black"
},
"style": "v2",
"sitemapLocation": "sitemap.json"
}
参考官网基本语法解释
{{ msg}}可以执行简单的js表达式
{{2+3}}
{{msg.length}}
wx:if=""
wx:elif=""
wx:else
hidden // true 隐藏
wx:key="*this"
wx:key="字符串"
表示对象唯一属性// 默认item就是数据 ,index是下标
wx:for="{{list}}"
wx:key="index"
{{item}}
{{index}}
定义item与index的名称
wx:for="{{list}}}"
wx:for-item="myitem"
wx:for-index="myidx"
{{myidx}}
{{myitem}}
格式:<元素 bind事件名= “回调”>
外传
,capture 是事件捕获里传
。capture-bind只能用冒号形式。catch来绑定事件
。如catchtap,capture-catch:tap。bindInput 表单输入时
bindconfirm 表单输入确认
bindtap 点击时候
事件传参
表单绑定
<input value="{{s1}}" bindinput="inputHd">
// js.js
inputHd(e){
this.setData({s1:e.detail.value}) // 表单的值获取:e.detail.value
}
属性 | 类型 | 说明 |
---|---|---|
type | String | 事件类型 |
timeStamp | Integer | 页面打开到触发事件所经过的毫秒数 |
target | Object | 触发事件的组件的一些属性值集合 |
currentTarget | Object | 当前组件的一些属性值集合 |
detail | Object | 额外的信息 |
touches | Array | 触摸事件,当前停留在屏幕中的触摸点信息的数组 |
changedTouches | Array | 触摸事件,当前变化的触摸点信息的数组 |
属性 | 类型 | 说明 |
---|---|---|
id | String | 当前组件的id |
dataset | Object | 当前组件上由data-开头的自定义属性组成的集合 |
taget
点击inter不能拿到dataset数据currentTarget
可以拿到
this.setData
同react一样open-type
属性
<button type="primary" bindgetuserinfo="getUserInfo" size="mini" open-type="getUserInfo">getUserInfo</button>
getUserInfo(e) {
// 不推荐使用getUserInfo获取用户信息,预计自2021年4月13日起,getUserInfo将不再弹出弹窗,并直接返回匿名的用户个人信息
this.setData({
userInfo: e.detail.userInfo,
hasUserInfo: true
})
},
<button bindtap="getUserProfile"> 获取头像昵称 </button>
getUserProfile(e) {
// 推荐使用wx.getUserProfile获取用户信息,开发者每次通过该接口获取用户个人信息均需用户确认
// 开发者妥善保管用户快速填写的头像昵称,避免重复弹窗
wx.getUserProfile({
desc: '用于完善会员资料', // 声明获取用户个人信息后的用途,后续会展示在弹窗中,请谨慎填写
success: (res) => {
this.setData({
userInfo: res.userInfo,
hasUserInfo: true
})
}
})
},
模式 | 值 | 说明 |
---|---|---|
缩放 | scaleToFill | 不保持纵横比缩放图片,使图片的宽高完全拉伸至填满 image 元素 |
缩放 | aspectFit | 保持纵横比缩放图片,直到图片某一边碰到边界。 |
缩放 | aspectFill | 保持纵横比缩放图片,直到图片完全铺满边界。 |
缩放 | widthFix | 宽度不变,高度自动变化,保持原图宽高比不变 |
<button bindtap="hyImageUpload">选择图片上传</button>
<!-- 选择本地图片 -->
<image src="{{imageUrl}}"></image>
hyImageUpload(){
wx.chooseMedia({
camera: 'image',
}).then(res=>{
this.setData({
imageUrl:res.tempFiles[0].tempFilePath
})
})
}
<input type="text" model:value=" {{message}}"/>
属性名 | 类型 | 描述 | 注解 |
---|---|---|---|
id | String | 组件的唯一标示 | 保持整个页面唯一 |
class | String | 组件的样式类 | 在对应的 WXSS 中定义的样式类 |
style | String | 组件的内联样式 | 可以动态设置的内联样式 |
hidden | Boolean | 组件是否显示 | 所有组件默认显示 |
data-* | Any | 自定义属性 | 组件上触发的事件时,会发送给事件处理函数 |
bind* / catch* | EventHandler | 组件的事件 | 详见事件 |
Page/Component中定义的函数
的.//
<wxs module="format">
function joinTgether(num) {
return '¥' + num
}
// 必须模块化导出
module.exports={
joinTgether:joinTgether
}
</wxs>
<block wx:for="{{wxs}}" wx:key="*this">
<button size="mini" type="warn">{{item}}-{{format.joinTgether(item)}}</button>
</block>
utils
必须放在.wxs结尾的文件<button>模块抽离wxs</button>
<wxs module="format" src="/utils_wxs/format.wxs"></wxs>
<block wx:for="{{wxs}}" wx:key="*this">
<button size="mini" type="warn">{{item}}-{{format.joinTgether(item)}}</button>
</block>
module.exports
实现;.json
文件中进行自定义组件声明(将component 字段设为 true 可这一组文件设为自定义组件):xx.json
文件中导入{
"usingComponents": {
"sel-info": "/components/selection-info/sel-info"
}
}
以“wx-”为
前缀,否则会报错。app.json的usingComponents
声明某个组件,那么所有页面和组件可以直接使用该组件组件内的样式 对 外部样式 的影响
外部样式 对 组件内样式 的影响
如何让class可以相互影响
Component对象
中,可以传入一个options
属性,其中options属性中有一个styleIsolation
(隔离)属性。isolated
表示启用样式隔离,在自定义组件内外,使用 class 指定的样式将不会相互影响(默认取值);apply-shared
表示页面 wxss 样式将影响到自定义组件,但自定义组件 wxss 中指定的样式不会影响页面;shared
表示页面 wxss 样式将影响到自定义组件,自定义组件 wxss 中指定的样式也会影响页面和其他设置 了 options: {
// styleIsolation:"isolated" // 默认值
styleIsolation: "apply-shared"
},
<view style="width: 100%;height:80px;background-color: blueviolet;">
<button>{{title}}</button>
<view style="background-color: brown;margin-top: 10px; color: cornsilk;"> {{content}}</view>
</view>
properties: {
title: {
type: String,
value: '默认标题'
},content:{
type:String,
value:'默认内容'
}
},
<props-data />
<view class="styl">
<props-data title="通信" content='组件通信-传递参数-动态数据' />
</view>
<props-data title="z组件传参" content='组件通信-传递参数-动态数据' />
组件传递样式 -externalClasses
externalClasses
属性入对应的class
,并且给这个class设置样式组件的插槽也是为了让我们封装的组件更加具有扩展性
注意slot 不支持默认值
可以利用兄弟选中器解决<view class="myslot">
<view class="header">header</view>
<!-- 小程序插槽不支持默认值 -->
<view class="content">
<slot></slot>
</view>
<view class="default">兄弟选择器解决默认值</view>
<view class="footer">footer</view>
</view>
<my-slot>
<button>按钮</button>
</my-slot>
<my-slot>
<button size="mini" type="primary">default样式</button>
</my-slot>
<my-slot>
</my-slot>
.default{
display: none;
}
.content:empty + .default{
display: block;
}
<view class="slot">
<view class="t">
<text >上插槽</text> :
<slot name="t"></slot>
</view>
<view class="c">
<text>中间插槽</text> :
<slot name="c"></slot>
</view>
<view class="b">
<text>下插槽</text> :
<slot name="b"></slot>
</view>
</view>
Component({
// 允许定义多个插槽
options: {
multipleSlots: true
},
})
<more-slot>
<text slot="t">上插入</text>
<text slot="c">中间插入</text>
<text slot="b">下插入</text>
</more-slot>
类似于Vue中的 “mixins”
。
引用多个 behavior ,behavior 也可以引用其它 behavior
;export const counterMinxin = Behavior({
data: {
counter: 100
},
methods: {
add() {
// 加一修改 ,不应该使用++,这会导致counter在修改this..data.counter也在修改
this.setData({
counter: this.data.counter + 1
})
}
}
})
import { counterMinxin } from "../../behaviors/counter"
Component({
behaviors: [counterMinxin],
})
lifetimes
字段内进行声明Component({
behaviors: [counterMinxin],
lifetimes:{
created(){
console.log('组件被创建');
},
attached(){
console.log('组件添加到dom树中');
},
detached(){
console.log('组件被删除');
}
}
})
文档参考链接
应用生命周期钩子函数
属性 | 说明 |
---|---|
onLaunch | 生命周期回调——监听小程序初始化。 |
onShow | 生命周期回调——监听小程序启动或切前台。 |
onHide | 生命周期回调——监听小程序切后台。 |
onError | 错误监听函数。 |
属性 | 说明 |
---|---|
onLoad | 生命周期回调—监听页面加载 |
onShow | 生命周期回调—监听页面显示 |
onReady | 生命周期回调—监听页面初次渲染完成 |
onHide | 生命周期回调—监听页面隐藏 |
onUnload | 生命周期回调—监听页面卸载 |
onPullDownRefresh | 监听用户下拉动作 |
onReachBottom | 页面上拉触底事件的处理函数 |
onShareAppMessage | 用户点击右上角转发 |
onShareTimeline | 用户点击右上角转发到朋友圈 |
onAddToFavorites | 用户点击右上角收藏 |
onPageScroll | 页面滚动触发事件的处理函数 |
onResize | 页面尺寸改变时触发,详见 响应显示区域变化 |
// 1. 页面路径
pages/index/index?id=10086&name='admin'
// 2. onLoad 获取参数
onLoad(query){}
属性 | 说明 |
---|---|
created | 组件生命周期函数 - 在组件实例刚刚被创建时执行,注意此时不能调用 setData ) |
attached | 组件生命周期函数 - 在组件实例进入页面节点树时执行) |
ready | 组件生命周期函数 - 在组件布局完成后执行) |
moved | 组件生命周期函数 - 在组件实例被移动到节点树另一个位置时执行) |
detached | 组件生命周期函数 - 在组件实例被从页面节点树移除时执行) |
wx.request(Object object)
wx.request({
url: "api",
data: {
page: 1
},
success: res => {
console.log(res);
},
fail: err => {}
})
//0. 封装成函数
export function hyRequest(options) {
return new Promise((resolve, reject) => {
wx.request({
...options,
success: res => {
resolve(res.data)
},
fail: reject
})
})
}
//0. 类的方法封装
class hyService {
request(options) {
return new Promise((resolve, reject) => {
wx.request({
...options,
success: res => {
resolve(res.data)
},
fail: reject
})
})
}
get(options) {
return this.request({ ...options, method: 'GET'})
}
post(options) {
return this.request({
...options,
method: 'POST'
})
}
}
export const serviceResponse = new hyService()
// 1. 导入
import {hyRequest} from '../../service/request'
// 2. 使用封装调用api
hyRequest({url:"http://123.207.32.32:1888/api/city/all"}).then(res=>{
console.log(res);
})
wx.getSystemInfo(Object object)
wx.getLocation(Object object)
reqInfo() {
// 获取设备信息
// 我们需要经常获取当前设备的信息,用于手机信息或者进行一些适配工作
wx.getSystemInfo({
success: arr => {
console.log(arr);
}
}),
wx.getLocation({
success:err=>{
console.log(err);
}
})
}
注意获取位置信息需要相关权限
"permission": {
"scope.userLocation": {
"desc": "位置信息将用于小程序位置接口的效果展示"
}
}
navigateTo() {
// 跳转的页面是tarBar内的页面,需要使用wx.switchTab({})
wx.navigateTo({
// url: '/navPage/navigateTo/index',
// 传参
url: '/navPage/navigateTo/index?name=admin',
})
}
Page({
// options接受路径参数
onLoad(options) {
console.log(options);
},
})
Page({
navigateTo() {
// 方式二
wx.navigateTo({
url: '/navPage/navigateTo/index?name=admin',
events: {
backEvent(data) {
console.log('接受跳转的参数', data);
}
}
})
}
})
Page({
up() {
wx.navigateBack()
// // 传递数据给上一级
// const pages = getCurrentPages()
// //读取最后一个页面,的实例
// const prePage = pages[pages.length - 2]
// // 设置上一个页面的数据
// prePage.setData({
// message: 'admin'
// })
// console.log(pages);
const eventChannel = this.getOpenerEventChannel()
eventChannel.emit('backEvent', {
name: 'admin',
pad: 'password'
})
},
// 回退过多可以直接在onLoad里面设置
onUnload() {
const pages = getCurrentPages()
const prePage = pages[pages.length - 2]
prePage.setData({
message: 'admin',
username: 'password'
})
},
})
// app.js
App({
onLaunch() {
// 展示本地存储能力
const logs = wx.getStorageSync('logs') || []
logs.unshift(Date.now())
wx.setStorageSync('logs', logs)
// 登录
wx.login({
success: res => {
// 发送 res.code 到后台换取 openId, sessionKey, unionId
const code = res.code
wx.request({
url: 'url',
data: {
code
},
method: 'POST',
success: res => {
const token = res.data.token
wx.setStorageSync('token', token)
}
})
}
})
},
})