赞
踩
小程序有许多的内置组件,比如之前学习过的 view
、image
、scroll-view
、swiper
等,除此之外小程序也允许开发者自定义组件。
自定义组件的结构与页面是一致的,即也包含有4个部分,分别为:
.wxml
组件的布局结构
.js
组件的处理逻辑
.json
组件的配置文件
.wxss
组件的布局样式
通常习惯将组件放到独立的目录
components
当中,这个目录需要我们手动进行创建。
创建一个叫 authorization
的组件来学习组件创建的步骤,在 components
目录中新建 authorization
目录,然后在右键在菜单中找到【新建 Component】,输入组件名称后会自动创建组件。
组件和页面的结构是一致的,但也是有区别的,先简单有个了解:
组件的配置文件中配置项 component: true
组件的 .js
文件中调用 Component
函数
如果报 什么什么忽略 的错就在project.private.config.json文件夹的setting里面加上以下代码
报错原因,建了应用,没有使用
- "setting": {
- "ignoreDevUnusedFiles": false,
- "ignoreUploadUnusedFiles":false
- },
组件的注册分为页面注册和全局注册两种情况:
页面注册是在使用组件的页面配置中通过 usingComponents
进行注册,只能在当前页面中使用注册的组件,如下代码所示:
- {
- "usingComponents": {
- "authorization": "/components/authorization/index"
- }
- }
- <!-- pages/index/index.wxml -->
- <!-- 双标签用法 -->
- <authorization></authorization>
- <!-- 单标签用法(一定要闭合) -->
- <authorization />
全局注册是在 app.json
文件中通过 usingComponents
对自定义组件进行注册,注册的组件可以任意页面中使用全局注册的组件,如下代码所示:
- {
- "pages": [...],
- "window": {...},
- + "usingComponents": {
- + "authorization": "/components/authorization/index"
- + },
- "sitemapLocation": "sitemap.json"
- }
一些需要注意的细节:
因为 WXML 节点标签名只能是小写字母、中划线和下划线的组合,所以自定义组件的标签名也只能包含这些字符。
自定义组件也是可以引用自定义组件的,引用方法类似于页面引用自定义组件的方式(使用 usingComponents
字段)。
自定义组件和页面所在项目根目录名不能以“wx-”为前缀,否则会报错。
本节来学习如何处理组件的逻辑。
了解数据变量、方法定义和使用
data
组件本身内部定义的数据
methods
中定义组件的方法
- // components/authorization/index
- Component({
- // 初始组件内部数据
- data: {
- message: '组件中初始的数据'
- },
- methods: {
- // 定义事件回调函数
- handlerClick() {
- console.log('clicked')
- },
- },
- })
自定义组件有自已的作用域,然而在实际开发中,父子组件之间的数据传递是不可避免的。
父传子
父组件通过属性赋值为子组件传递数组
- <!-- pages/index/index.wxml -->
- <view class="box">
- <!-- 应用自定义组件 -->
- <header isLogin="{{true}}" tips="{{msg}}" />
- </view>
子组件通过properties
接收父组件数据
- Component({
- // 接收父组件数据
- properties: {
- isLogin: Boolean,
- tips: {
- // 属性的数据类型
- type: String,
- // 属性的默认值
- value: 'hello'
- }
- },
- })
查看或调试传入组件的数据与页面数据的查看方式不同,具体查看如下图所示: 说明❓:选中要查看的组件,通过右侧component data面板查看
注意:可以直接修改父组件传递的数据(父组件不受影响)
子传父
父组件在子组件上绑定自定义事件,提供自定义事件回调方法
在自定义事件回调方法中,通过默认形参event.detail
获取数据
- <!-- pages/index/index.wxml -->
- <view class="box">
- <!-- 应用自定义组件 -->
- <header isLogin="{{true}}" tips="{{msg}}"
- bind:自定义的事件名="mycallback" />
- </view>
-
- // pages/index/index.js
- Page({
- // 父组件中的数据
- data: {
- },
- // 自定义事件的回调
- mycallback: function (e) {
- console.log('我是父组件中的回调函数...',e);
- }
- })
![](https://csdnimg.cn/release/blogv2/dist/pc/img/newCodeMoreWhite.png)
子组件触发父组件自定义事件
通过this.triggerEvent('自定义事件名称',data)
触发和传递数据
- Component({
- // ...
- // 组件方法,可用于事件监听回调函数
- methods: {
- sayHi: function () {
- // 并且将 {name: '小明', age: 18} 做为参数,传给父组件自定义事件的回调函数
- this.triggerEvent('事件名', {name: '小明', age: 18});
- }
- }
- })
前面我们分别学习了应用级别和页面级别的生命周期,组件也有生命周期函数,通过
lifetimes
来定义,主要的生命周期函数有:
attached
在组件实例进入页面节点树时执行
detached
在组件实例被从页面节点树移除时执行
- Component({
- // ...
- // 组件生命周期
- lifetimes: {
- attached: function() {
- // 在组件实例进入页面节点树时执行
- },
- detached: function() {
- // 在组件实例被从页面节点树移除时执行
- },
- },
- });
小程序的组件模板其实就是插槽功能,通过
<slot>
在组件内部定义插槽位置,以authorization
组件为例其用法如下所示:
在组件内定定义 slot
插槽,插槽其实就是个占位符号
- <view class="container">
- <slot></slot>
- </view>
在首页面应用组件并在组件开始和结束位置中间插入内容,被插入的内容就会被渲染到插槽的位置上:
- <authorization is-login="{{true}}" tips="用户未登录">
- <view>默认slot 插槽</view>
- <view>默认slot 插槽</view>
- </authorization>
默认情况小程序在一个组件中只能支持一个插槽,如果需要多个插槽需要启用多
slot
支持,启用方式如下所示:
启用多插槽支持
- Component({
- options: {
- // 启用多插槽支持
- multipleSlots: true
- }
- })
启用了多插槽支持后通过 name
为插槽命名:
- <view class="container">
- <slot name="content"></slot>
- </view>
- <view class="layout">
- <slot name="number"></slot>
- </view>
在应用组件时通过 slot
属性指定将内容放入哪个插槽的位置:
- <authorization is-login="{{true}}" tips="用户未登录">
- <view slot="content">
- <view>具名slot 插槽的位置</view>
- <view>具名slot 插槽的位置</view>
- </view>
- <text slot="number">1000</text>
- </authorization>
Vant 提供了微信小程序版本的组件库,它本质上就是自定义的小程序组件,我们来学习如何在小程序中引入 Vant 组件库。
第 1 步:安装 vant 组件库
npm i @vant/weapp -S --production
第 2 步:如下图所示构建 Vant 组件库,构建时会去检查 package.json
中记录的依赖,因此一定要有 package.json
文件的存在。
第 3 步:以按钮组件为例,演示使用 Vant 组件的使用方法,推荐全局注册组件 Vant 组件
- {
- "usingComponents": {
- "van-button": "@vant/weapp/button/index"
- }
- }
注意:将 app.json 中的 "style": "v2"
去除,小程序的新版基础组件强行加上了许多样式,难以覆盖,不关闭将造成部分组件样式混乱。
介绍常用组件使用方法
首先要在 app.json
中全局注册组件:
- {
- "usingComponents": {
- "van-cell": "@vant/weapp/cell/index",
- "van-cell-group": "@vant/weapp/cell-group/index"
- }
- }
van-cell
组件可以独立使用,也可以配置 van-cell-group
一起使用:
- <van-cell-group custom-class="cell-group" inset>
- <van-cell size="large" title="北京富力家园">
- <text class="tags fail">审核失败</text>
- </van-cell>
- <van-cell title="房间号" value="1号楼1单元101室" border="{{ false }}" />
- <van-cell title="业主" value="内容" border="{{ false }}" />
- </van-cell-group>
同样的先在 app.json
中全局注册组件:
- {
- "usingComponents": {
- "van-swipe-cell": "@vant/weapp/swipe-cell/index"
- },
- }
然后将需要侧向滑动的盒子用 van-swipe-cell
组件包裹起来即可:
- <van-swipe-cell right-width="{{ 65 }}">
- <van-cell-group>
- <van-cell size="large" title="北京富力家园">
- <text class="tags fail">审核失败</text>
- </van-cell>
- <van-cell title="房间号" value="1号楼1单元101室" border="{{ false }}" />
- <van-cell title="业主" value="内容" border="{{ false }}" />
- </van-cell-group>
- - <!-- 右侧滑动显示的按钮 -->
- + <view slot="right">删除</view>
- </van-swipe-cell>
Vant 组件中的组件提供了非常整齐美观的样式,但是开发中在所难免需要对原有样式进行个修改
简单粗暴,通过调试工具查找要修改样式的盒子,找到已定义的类名,然后强制覆盖原有的样式
- .van-swipe-cell__right {
- display: flex;
- align-items: center;
- justify-content: center;
- width: 65px !important;
- margin-left: -20px;
- text-align: center;
- color: #fff;
- background-color: #eb5757;
- }
::: tip 提示: 在进行样式覆盖时优先不够的情况下使用 !important :::
使用样式变量
新版本的 css 支持定义变量,其语法样式为:
--变量名: 值
,定义的变量通过var
关键字来使用:
局部变量
举例说明:
- .box {
- --my-cusotm-color: pink;
- backgound-color: var(--my-cusotm-color);
- }
上述代码中定义的变量只能用在 .box
盒子及后代元素上
全局变量
如果希望整个页面都能使用这个变量,可以这样定义:
- page {
- --my-cusotm-color: pink;
- }
-
- .box {
- backgound-color: var(--my-cusotm-color);
- }
- .navs {
- backgound-color: var(--my-cusotm-color);
- }
了解了 css 变量的基本用法后,咱们修改 vant 中 css 变量覆盖原来样式:
说明❓:通过调式面板,查看组件元素中用到的css变量进行覆盖
- page {
- --cell-large-title-font-size: 30rpx;
- --cell-text-color: #c3c3c5;
- --cell-value-color: #686868;
- }
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。