微信小程序中自定义组件的使用
微信小程序没有select下拉框的标签,我们可以自己写一个component组件来实现下拉框的功能。
先介绍下,微信小程序中组件的使用和传参。在微信小程序中要使用自己自定义的组件需要在组件的json文件中设置component=true.
select.json:
{
"component": true,
"usingComponents": {}
}
然后在需要调用组件的页面json文件中设置绑定调用组件的地址:
{
"usingComponents": {
"select":"../../components/select/select"
}
}
然后就可以在页面中使用组件的标签来直接使用组件了。
select组件
子页面代码示例:
select.js:
Component({
properties: {
options: {
type: Array,
value: []
},
defaultOption: {
type: Object,
value: {
id: '000',
name: '下拉框'
}
},
key: {
type: String,
value: 'id'
},
text: {
type: String,
value: 'name'
}
},
data: {
isShow: false,
current: {}
},
methods: {
optionTap(e) {
let dataset = e.target.dataset
console.log(dataset)
this.setData({
current: dataset,
isShow: false
});
// 调用父组件方法,并传参
this.triggerEvent("change", { ...dataset })
},
openClose() {
this.setData({
isShow: !this.data.isShow
})
},
// 此方法供父组件调用
close() {
this.setData({
isShow: false
})
}
},
lifetimes: {
attached() {
// 属性名称转换, 如果不是 { id: '', name:'' } 格式,则转为 { id: '', name:'' } 格式
let result = []
if (this.data.key !== 'id' || this.data.text !== 'name') {
for (let item of this.data.options) {
let { [this.data.key]: id, [this.data.text]: name } = item
result.push({ id, name })
}
}
this.setData({
current: Object.assign({}, this.data.defaultOption),
result: result
})
}
}
})
select.wxml:
<view class="select-box">
<view class="select-current" catchtap="openClose">
<text class="current-name">{{current.name}}</text>
</view>
<view class="option-list" wx:if="{{isShow}}" catchtap="optionTap">
<text class="option"
data-id="{{defaultOption.id}}"
data-name="{{defaultOption.name}}">全部
</text>
<text class="option"
wx:for="{{result}}"
wx:key="{{item.id}}"
data-id="{{item.id}}"
data-name="{{item.name}}">{{item.name}}
</text>
</view>
</view>
select.wxss:
.select-box {
position: relative;
width: 100px;
font-size: 30rpx;
}
.select-current {
position: relative;
width: 100%;
padding: 0 10rpx;
line-height: 70rpx;
border: 1rpx solid #ddd;
border-radius: 6rpx;
box-sizing: border-box;
}
.select-current::after {
position: absolute;
display: block;
right: 16rpx;
top: 30rpx;
content: '';
width: 0;
height: 0;
border: 10rpx solid transparent;
border-top: 10rpx solid #999;
}
.current-name {
display: block;
width: 85%;
height: 100%;
word-wrap: normal;
overflow: hidden;
}
.option-list {
position: absolute;
left: 0;
top: 76rpx;
width: 100%;
padding: 12rpx 20rpx 10rpx 20rpx;
border-radius: 6rpx;
box-sizing: border-box;
z-index: 99;
box-shadow: 0rpx 0rpx 1rpx 1rpx rgba(0, 0, 0, 0.2) inset;
background-color: #fff;
}
.option {
display: block;
width: 100%;
line-height: 70rpx;
border-bottom: 1rpx solid #eee;
}
.option:last-child {
border-bottom: none;
padding-bottom: 0;
}
这样组件就写好了,组件是子页面,调用组件的页面是父页面。子页面和父页面之间相互传值的方式不同。
父页面向子页面传值,通常在标签中赋值就可以,不过能传的值需要在子页面的js文件中的properties中先定义类型和默认value,见上方select.js代码块中的properities部分。
子页面向父页面传值通常是定义一个方法,在方法中使用下述代码传值:
this.triggerEvent("change", {...dataset}) //第一个放方法名,父页面bind:change="(父页面自定义方法)"中关联引用。第二个是要传的数据名。
父页面代码示例:
index.wxml:
<view class="selectList" bindtap="close">
<view class="select-wrap">
<select id="select" defaultOption="{{teach_type}}" options="{{teach_type_list}}" key="type_id" text="type_name" bind:change="change_teach_type"></select>
</view>
</view>
index.js:
var app=getApp()
Page({
data: {
//类型
teach_type_target:"类型",
teach_type:{
id:"000",
name:"类型"
},
teach_type_list:[
{
type_id:"001",
type_name:"上门辅导"
},
{
type_id:"002",
type_name:"在线辅导"
},
],
change_teach_type(e){
this.setData({
teach_object_target:e.detail.name //e为子页面传回的数据
})
}
})