宝哥软件园

基于组件的微信小程序快速实现可用模态窗口

编辑:宝哥软件园 来源:互联网 时间:2021-12-11

微信小程序组件化 快速实现可用模态窗(图1)

在整个现代前端框架中(不考虑ng react vue),基于组件的声明性呈现路由状态管理适用于基本的四节车厢。另一方面,小程序开发环境缺乏很多特性。好在11月初,微信团队发布了正式的组件方案,我们基本可以告别现有的黑客方法实现组件了。

hack方式

使用模板实现https://zhuanlan.zhihu.com/p/.组件化使用包含组件化简单地说就是包含组件wxml和样式文件到页面。然后,导入组件的js文件通过合并将组件数据方法合并到页面中。对于数据,首先调用组件事件,然后调用父页面事件。

上述方案核心:将组件中定义的数据和方法组合到页面中,实现组件化。本质上,没有组件范围的隔离,将不可避免地出现命名冲突覆盖。

实现一个组件

方便快捷的理解。在这里,我们使用官方组件方案来实现一个模态弹出窗口easyModal。

请看看https://gitee.com/sherlock221的源代码。

阅读前请阅读https://mp.weixin.qq.com/debu官方定制组件文档。

组件分析

分为两个小组件来实现这个模态弹出窗口:基本模态弹出窗口和增强模态弹出窗口。

microsoft="" pingfang="" sans="" wenquanyi="">基本模态弹窗 具备

微信小程序组件化 快速实现可用模态窗(图2)

1.显示/隐藏2.backdrop3.过度动画4.自定义头尾这几部分基础功能

增强型模态弹窗 具备

微信小程序组件化 快速实现可用模态窗(图3)

1.基础模态弹窗功能2.自定义内容区域3.title自定义4.确定取消按钮自定义

基本模态窗

微信小程序组件化 快速实现可用模态窗(图4)

首先在base文件夹下直接右键创建component -> baseModal在baseModal.js中创建组件所需要props 这些属性来自父组件或 外层page 中的数据,

Component({      options : {    multipleSlots: true   },  /**   * 组件的属性列表   */  properties: {    backdrop: {      type: Boolean,      value: true    },    animated : {      type: Boolean,      value: true    },        modalSize : {      type: String,      value: "md"    },      animationOption : {      type : Object,      value  : {        duration : 300       }    }     },}

下来创建 data,isShow控制 弹窗显示和隐藏 animation则是弹窗动画函数.

/**   * 组件的初始数据   */  data: {    isShow : false,    animation : ''  },

在生命周期函数 ready中初始化animation

ready: function () {        this.animation = wx.createAnimation({       duration: this.data.animationOption.duration,      timingFunction: "linear",      delay: 0    });   },

组件有2个public方法 show hide 方法, private 有执行动画 和 切换显隐的方法

methods: {      hideModal : function(e){          if(e){          let type = e.currentTarget.dataset.type;          if (type == 'mask' && !this.data.backdrop) {            return;          }           }                        if (this.data.isShow) this._toggleModal();      },      showModal : function(){        if (!this.data.isShow) {          this._toggleModal();                 }      },      _toggleModal : function(){              if(!this.data.animated){            this.setData({              isShow: !this.data.isShow            })        }        else{          let isShow = !this.data.isShow;          this._executeAnimation(isShow);        }              },      _executeAnimation: function (isShow) {        ......      }  }

可以通过animated属性来判断 组件是否需要调用_executeAnimation 来执行动画显示

页面结构

<view  animation="{{animationData}}"  hidden="{{!isShow}}"  class='modal'>     <view  data-type="mask"  catchtap='hideModal' class='modal-mask' >view>        <view  class='modal-layer  modal-layer-radius {{modalSize == "sm" ? " modal-layer-sm" : " modal-layer-md" }} ' >                  <view class='modal-header'>                      <slot name="header">slot>                       view>                    <view class='modal-body'>                        <slot name="body">slot>                                    view>          <view class='modal-footer'>               <slot name="footer">slot>                               view>      view>  view>

slot 节点,用于承载组件使用者提供的wxml结构。默认情况下,一个组件的wxml中只能有一个slot。需要使用多slot时,记得开启配置

options : {    multipleSlots: true   },

下来创建样式wxss具体可以看github 文件这就不贴

/** 模态 **/.modal{  position: fixed;  top: 0rpx;  left: 0rpx;  right: 0rpx;  bottom: 0rpx;  width: 100%;  height: 100%;   z-index: 100;}..............

需要注意 组件wxss文件 具备隔离性的你在page 中定义的class , 在app.wxss 中定义的class 都无法再组件中使用,如果真有一些需要复用到的样式 可以抽取成一个wxss 通过import 导入 组件的wxss

@import"../../style/font.wxss";

这样会增加组件和业务的耦合度 公共组件不建议使用

接下来可以在业务界面中去使用

<base-modal id="thridModal">  <view slot="header" class='modal-header'>        头部    view>     <view slot="body" class='modal-body'>        中间    view>     <view slot="footer" class='modal-footer'>         尾部          view>base-modal>

别忘了在业务页面的json中引入组件

{     "usingComponents": {           "base-modal": "/component/easyModal/base/baseModal"    }  }

还记得我们上面baseModal 有两个public方法 怎么样去调用呢 这里介绍下

Component 的一个实例方法 selectComponent通过它 可以找到子组件实例 这个有点像是 jq 选择器 通过selector去寻找dom(但是不是dom是js对象) 不过它更像是 react 或 vue ref this.$refs.xxx 获得组件实例.

我们给这个组件创建一个id 通过id选择器就可以找到base-modal的实例 在ready中找到modal实例

onReady: function () {         this.thridModal = this.selectComponent("#thridModal");  },

然后就可以调用实例的public的方法.

this.thridModal.showModal();this.thridModal.hideModal();
增强模态窗

增强模态窗是基于baseModal的.

{  "component": true,  "usingComponents": {    "base-modal" : "../base/baseModal"  }}

注意 增强模态窗口 需要包含 基本模态窗口 json中引用才能使用

<base-modal id="baseModal"   modalSize="{{modalSize}}"  animated="{{animated}}"  backdrop="{{backdrop}}">    <view slot="header" class='modal-header'>        <text>{{title}}text>    view>     <view slot="body" class='modal-body'>        <slot>slot>    view>     <view slot="footer" class='modal-footer'>         <text catchtap='_cancelModal' class='btn btn-default'>{{cancelText}}text>         <text catchtap='_confirmModal'  class='btn btn-primary'>{{confirmText}}text>          view>base-modal>

说下event部分 确定 取消按钮是需要 向外部page 发送事件通知的其进行业务操作的

 //cancel    _cancelModal : function(){            this.hide();           this.triggerEvent("cancelEvent");    },    //success    _confirmModal : function(){           this.triggerEvent("confirmEvent");    }

通过triggerEvent触发事件 这点和官网文档没有区别.

业务Page界面:

<easy-modal        id="easyModal"       title="这个是标题 01"         bind:cancelEvent="_cancelEvent"        bind:confirmEvent="_confirmEventFirst"        >  <view class='modal-content'>             <text> 这是内容部分 01 text>                  <text> 这是内容部分 01 text>                  <text> 这是内容部分 01 text>                            
更多资讯
游戏推荐
更多+