这是我参与8月更文挑战的第19天,活动详情查看:8月更文挑战
前面写了封装button组件、dialog组件和input组件,有需要的童鞋请冲~~
这篇来写下如何封装switch组件。
一、封装Switch组件
1.参数支持
| 参数名称 | 参数类型 | 参数描述 | 默认值 |
|---|---|---|---|
| v-model | Boolean | 双向绑定 | false |
| name | String | name属性 | text |
| activeColor | String | 自定义的激活的颜色 | |
| inactiveColor | String | 自定义的不激活的颜色 |
1.1. 设置支持v-model参数
由于v-model 默认会利用名为 value 的 prop 和名为 input 的事件,所以应该用props接收value属性,设置对应类名is-checked来控制样式。由于switch是用点击来修改value属性,所以我们给switch组件设置一个click事件,当点击时触发用户组件中的input事件,更改用户组件中的value。
<template>
<div class="zh-switch" :class="{'is-checked': value}" @click="handleClick">
<span class="zh-switch__core" ref="core">
<span class="zh-switch__button"></span>
</span>
</div>
</template>
props: {
value: {
type: Boolean,
default: false
},
},
methods: {
handleClick() {
this.$emit("input", !this.value);
},
}
1.2. 设置name属性,绑定input
- 因为switch是个表单元素,本质上是一个复选框,所以我们需要绑定一个复选框并给复选框加上name属性,但是样式上应该隐藏该复选框。
- 复选框除了绑定name属性,还要根据value值的变化改变checked属性。
- 由于value属性是用户组件传入的,所以每当value改变时,触发用户组件中value的改变后,等待视图更新,再设置checked属性等于当前新的value值。
<template>
<div class="zh-switch" :class="{'is-checked': value}" @click="handleClick">
<span class="zh-switch__core" ref="core">
<span class="zh-switch__button"></span>
</span>
<input class="zh-switch__input" type="checkbox" :name="name" ref="input">
</div>
</template>
<script>
export default {
props: {
....
name: {
type: String,
default: ""
},
},
methods: {
async handleClick() {
this.$emit("input", !this.value);
//等待视图更新
await this.$nextTick();
this.setInputChecked();
},
// 设置input的checked与value同步
setInputChecked() {
this.$refs.input.checked = this.value;
}
},
mounted() {
this.setInputChecked();
}
};
</script>
1.3. 设置activeColor、inactiveColor
- 同样使用props接收用户传入的这两个参数,设置setColor方法来改变switch的borderColor和backgroundColor。
- 为了操作元素样式,给类名为zh-switch__core的span加上ref="core",操作该元素时直接用$refs。
- 挂载完需要设置颜色;每当value改变时,触发用户组件中value的改变后,等待视图更新后,也需要重新设置颜色。所以在mounted生命周期和handleClick中加上setColor方法。
<span class="zh-switch__core" ref="core">
export default {
.....
props: {
.....
activeColor: {
type: String,
default: ""
},
inactiveColor: {
type: String,
default: ""
}
},
methods: {
async handleClick() {
this.$emit("input", !this.value);
await this.$nextTick();
this.setColor();
this.setInputChecked();
},
setColor() {
if (this.activeColor || this.inactiveColor) {
let color = this.value ? this.activeColor : this.inactiveColor;
this.$refs.core.style.borderColor = color;
this.$refs.core.style.backgroundColor = color;
}
},
......
},
mounted() {
this.setColor();
this.setInputChecked();
}
};
2.事件支持
| 事件名称 | 事件描述 |
|---|---|
| change | change时触发的事件 |
系列文章
以下是从0搭建Vue2 UI组件库系列的文章,有需要的同学请冲~~ 从0搭建Vue2 UI组件库(一)