• WEIXIN day_04(8.19)小程序的事件处理、传参、常用API、生命周期、网络通信


    小程序的事件处理

    <swiper  bindchange="当轮播图切换页面时触发该事件">swiper> 
    <scroll-view bindscrolltoupper="滚到顶触发" 
                 bindscrolltolower="滚到底触发">scroll-view>
    <input bindinput="" />
    <image bindtap="">image>
    <picker bindchange="">picker>
    .................
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    很多事件类型匹配相应的组件。

    小程序的事件类型主要分为2类:

    1. 冒泡事件 组件触发该事件后,该事件将会向父节点传递。
    2. 非冒泡事件 组件触发该事件后,该事件不会向父节点传递。

    WXML的冒泡事件列表:

    类型触发条件
    touchstart手指触摸动作开始
    touchmove手指触摸后移动
    touchcancel手指触摸动作被打断,如来电提醒,弹窗
    touchend手指触摸动作结束
    tap手指触摸后马上离开
    longpress手指触摸后,超过350ms再离开,如果指定了事件回调函数并触发了这个事件,tap事件将不被触发

    注:除上表之外的其他组件自定义事件如无特殊声明都是非冒泡事件,如 form 的submit事件,input 的input事件,scroll-view 的scroll事件,(详见各个组件)

    案例:pages/event/event

    为组件绑定事件的方式
    <view bindtap="tapview">view>
    <view bind:tap="tapview">view>
    <view catchtap="tapview">view>
    
    • 1
    • 2
    • 3

    使用bind事件类名方式或catch事件类名方式都可以为组件绑定事件,不一样的是catch方式将会自动阻止事件冒泡

    bind:事件类名也可以为组件绑定事件,所不同的是,bind可以为所有组件绑定事件,而bind:方式不能用于部分原生组件

    原生组件:

    原生组件指的是由android、ios操作系统直接控制的组件,而不是小程序自定义设计的组件。原生组件与操作系统底层直接打交道,不会被小程序过多干预。

    比如:video组件、camera组件、input组件等。

    小程序中事件触发后的传参方案
    <image bindtap="tapImage">image>
    
    • 1

    点击图片,触发tap事件,执行tapImage方法。

    注意:绑定tap事件时,事件处理函数名:tapImage严禁出现小括号。 这样就会出现一个问题,小程序触发tap事件后,如何给tapImage方法传递自定义参数?

    需求:

    <view>
    	臭豆腐   2    5.0  <button bindtap="del" data-i="0">删除button>
    view>
    <view>
    	螺蛳粉   2    5.0  <button bindtap="del" data-i="1">删除button>
    view>
    <view>
    	臭鳜鱼   2    5.0  <button bindtap="del" data-i="2" data-a=''>删除button>
    view>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    del(event){
        let i = event.target.dataset.i
        console.log(i)   // 获取点击的按钮上绑定的data-i属性值
    }
    
    • 1
    • 2
    • 3
    • 4

    对于非冒泡事件,一般都是小程序官方自定义事件,这种事件触发后所涉及到的参数一般都被组件封装到了detail属性中,所以直接使用 event.detail就可以访问到:

    <input bindinput="handleInput" />
    <switch bindchange="handleChange">switch>
    <scroll-view bindscroll="handleScroll">scroll-view>
    <swiper bindchange="changeSwiper">swiper>
    
    handleInput(event){
    	event.detail.value
    }
    handleChange(event){
    	event.detail.value
    }
    handleScroll(event){
    	event.detail
    }
    changeSwiper(event){
    	event.detail
    }
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17

    案例:吃饭睡觉打豆豆。

    小程序常用API

    小程序界面交互类API
    小程序路由跳转类API(编程式跳转)
    • wx.switchTab 跳转到tabbar页面,这样将会销毁所有非tabbar页面。
    • wx.reLaunch 重新启动小程序,打开某一个页面。
    • wx.redirectTo 销毁当前页,跳转到目标非tabbar页面。
    • wx.navigateTo 保留跳转,保留当前页,跳转到非tabbar页面。
    • [wx.navigateBack](https://developers.weixin.qq.com/miniprogram/dev/api/route/ wx.navigateBack.html) 销毁当前页从而回到上一页、上n页。

    小程序两个页面跳转过程中的参数传递方案

    小程序页面设计中,从页面A跳转到页面B的过程中将涉及到相关的参数传递。参数传递场景有两类:

    1. 正向传参

      A页面跳转到B页面,顺便带点参数给B页面,在B页面接收。

      A页面中传参:

      wx.navigateTo({
          url:'/pages/b/b?name=张三&pwd=1234&age=15'
      })
      
      • 1
      • 2
      • 3

      B页面中接收:

      //在B页面的js文件中:
      Page({
          onLoad(option){
              // 小程序传递的option对象封装了上一个页面传过来的参数
              option.name    option.pwd   option.age
          }
      })
      
      • 1
      • 2
      • 3
      • 4
      • 5
      • 6
      • 7
    2. 反向传参

      A页面跳转到B页面,在B页面中操作时,将一些数据回传给A。

      A页面在跳转的过程中,通过events声明一个函数,接收B回传的数据:

      wx.navigateTo({
          url: 'b',
          events: {
              acceptData: (data)=>{
                  // 当B回传数据后,执行该方法,data就是回传回来的数据
              }
          }
      })
      
      • 1
      • 2
      • 3
      • 4
      • 5
      • 6
      • 7
      • 8

      B页面中,找准合适的时机,当需要会出参数给A页面时,需要如下代码:

      let ec = this.getOpenerEventChannel() // 事件通道,用于与A通信
      ec.emit('acceptData', '参数信息')  // 通过A页面,执行acceptData,传参
      
      • 1
      • 2

    实现选择城市业务。

    小程序的生命周期

    搞清楚每一个组件生命周期的过程。

    搞清楚每一个生命周期钩子方法执行的时机。

    搞清楚每一个生命周期钩子方法执行的先后顺序与执行次数。

    未来使用时,找准生命周期方法,在合适的位置写代码就行了。

    小程序页面的生命周期

    定义了小程序中一个普通页面,从生到死所经过的生命周期钩子方法。

      /** 生命周期函数--监听页面加载  执行一次 */
      onLoad(options) { 
      },
    
      /**  生命周期函数--监听页面初次渲染完成  执行一次  */
      onReady() { 
      },
    
      /** 生命周期函数--监听页面显示  执行多次  */
      onShow() { 
      },
    
      /** 生命周期函数--监听页面隐藏  执行多次  */
      onHide() { 
      },
    
      /** 生命周期函数--监听页面卸载  执行一次  */
      onUnload() { 
      },
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    小程序应用的生命周期

    整个微信小程序,从应用启动到应用关停也会涉及到应用全局的生命周期,其中有关的生命周期钩子方法在app.js中进行声明:

    // app.js
    // 当前文件将会在小程序初次启动时加载,仅加载一次
    // 在该js文件中可以定义应用全局的生命周期
    App({
        /** 生命周期回调—监听小程序初始化
          小程序初始化完成时触发,全局只触发一次。 */
        onLaunch(){
            console.log('App onLaunch...')
        },
    
        /** 生命周期回调—监听小程序显示
          小程序启动,或从后台进入前台显示时 */
        onShow(){ 
            let t = new Date().getTime()
            console.log('App onShow...'+t)
            let delta = t - this.globalData.time
            if(this.globalData.time!=0 && delta > 5000) {
                console.log('您已经离开了5秒钟,请重新登录...')
            } 
        }, 
    
        /** 生命周期回调—监听小程序隐藏  
       *  小程序从前台进入后台时 */
        onHide(){
            let t = new Date().getTime()
            console.log('App onHide...' + t)
            // 将隐藏app时的时间戳存入globalData.time
            this.globalData.time = t
        },
    
        /** 在App.js中声明globalData用于存储全局共享的数据 */
        globalData : {
            time : 0,
    
            cityname: '北京',
            username: '张三',
        }
    })
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38

    app.js中推荐声明一个globalData属性用于存储全局共享数据,由于小程序全局app.js仅加载一次,所以App对象也属于全局单例。所有页面都可以通过一些API拿到App对象从而共享globalData中的数据。例如:

    // app.js
    App({
        globalData: {
            name: 'zhangsan',
            ......
        }
    })
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    在页面中如果希望访问该globalData数据,如下:

    //a.js
    Page({
        onLoad(){
            // getApp()方法将会返回全局唯一的App对象
            let name = getApp().globalData.name
        }
    })
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    基于生命周期与App.globalData实现反向传参
    1. 从A页面跳转到B页面。
    2. 在B页面中,将数据存入App.globalData,返回A页面。
    3. 在A页面中,重写onShow方法,从App.globalData中获取存储的数据从而完成反向传参。

    小程序中的网络通信

    测试连接: https://api.tedu.cn/index.php?cid=1

    修改DNS为:114.114.114.114

    1. 电脑右下角,右键网络,打开网络设置。
    2. 更改适配器选项。
    3. 右键当前正在使用的网络:选择属性。
    4. 双击列表中:Internet 协议版本4.
    5. 修改DNS服务器地址:114.114.114.114
    6. 确定。
    小程序中的网络通信相关API
    wx.request({
        url: '请求地址',
        method: '请求方式  GET|POST等',
        header: {},   // 设置请求消息头
        data: {},     // 传递请求参数
        success: (res)=>{....}, 
        fail: (err)=>{....},
        complete: (res)=>{....}
    })
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9

    案例:发请求,访问接口。pages/req/req

    https://api.tedu.cn 不在以下 request 合法域名列表中,请参考文档:https://developers.weixin.qq.com/miniprogram/dev/framework/ability/network.html

    小程序开发者工具只允许向合法的域名发送https请求。合法的域名需要在小程序后台管理网站 — 开发 — 开发管理 — 开发设置 — 服务器域名的位置 来进行域名配置。

    https://wx.mp.qq.com扫码登录即可。

    当合法域名配置完毕后,打开开发工具,点击右上角:详情、项目配置,刷新合法域名列表即可看到配置的域名信息。(如果依然不在合法域名列表中,重启开发工具即可)

    在小程序/小游戏中使用网络相关的 API 时,需要注意下列问题,请开发者提前了解。
    1. 服务器域名配置

    每个微信小程序需要事先设置通讯域名,小程序只可以跟指定的域名进行网络通信。包括普通 HTTPS 请求(wx.request)、上传文件(wx.uploadFile)、下载文件(wx.downloadFile) 和 WebSocket 通信(wx.connectSocket)。

    2. 配置流程

    服务器域名请在 「小程序后台 - 开发 - 开发设置 - 服务器域名」 中进行配置,配置时需要注意:

    • 域名只支持 https (wx.requestwx.uploadFilewx.downloadFile) 和 wss (wx.connectSocket) 协议;
    • 域名不能使用 IP 地址(小程序的局域网 IP 除外)或 localhost;
    • 可以配置端口,如 https://myserver.com:8080,但是配置后只能向 https://myserver.com:8080 发起请求。如果向 https://myserver.com、https://myserver.com:9091 等 URL 请求则会失败。
    • 如果不配置端口。如 https://myserver.com,那么请求的 URL 中也不能包含端口,甚至是默认的 443 端口也不可以。如果向 https://myserver.com:443 请求则会失败。
    • 域名必须经过 ICP 备案;
    • 出于安全考虑,api.weixin.qq.com 不能被配置为服务器域名,相关 API 也不能在小程序内调用。 开发者应将 AppSecret 保存到后台服务器中,通过服务器使用 getAccessToken 接口获取 access_token,并调用相关 API;
    • 不支持配置父域名,使用子域名。
  • 相关阅读:
    Mysql JDBC反序列化漏洞
    浏览器localStorage和sessionStorage详解、特点、区别、StorageEvent事件以及注意事项
    Mybatis中表之间的关联关系
    浏览器的缓存机制 优点 缺点 协商缓存和强缓存 浏览器缓存过程 如何判断强缓存是否过期
    周总结
    Linux网络相关命令
    QT 知:qmake 手册
    浏览器中修改视频播放速度
    2022 Java零基础必备 简单易学 Eclipse免费下载安装+JDK环境搭建一站式捆绑服务到底的教程 足够全、足够详细、足够劲爆
    SSRF漏洞JAVA解决方案
  • 原文地址:https://blog.csdn.net/m0_70328115/article/details/126817744