Vue — CheckboxGroup.vue
最后更新于:2022-04-02 08:09:24
[TOC]
>[success] # CheckboxGroup
~~~
1.无论是使用iview 还是element ui,都可以发现在'checkbox'这里他们都会提供一个组件叫
'CheckboxGroup',会将'checkbox' 数据统一管理,我们来以'iview' 为例:
选项 1
选项 2
选项 3
选项 4
所以这章节就是封装一个'CheckboxGroup' 组件
~~~
>[info] ## 上个章节分装的checkbox组件和实际原生的区别
~~~
1.在封装之前,给先知道原生的'checkbox' 和我们上个章节封装的不同点
~~~
>[danger] ##### 原生
~~~
1.这里直接用了vue官方文档的案例
2.可以发现原生"checkbox" 本身绑定的就是数组,是不是有点懵了,上个章节我们封装的'checkbox'组件绑定
的只能是'String,Number,Boolean'这三种类型,其实上个章节案例将'value' 这个绑定值改为数组,在做一些
略微逻辑跳转也可以实现类似原生的方法
~~~
~~~
Checked names: {{ checkedNames }}
~~~
~~~
new Vue({
el: '#example-3',
data: {
checkedNames: []
}
})
~~~
>[info] ## 为了可以和原生一样绑定数组写 -- CheckboxGroup 组件
~~~
1.写组件从三个方面入手'props','events','slots',根据iview组件我们也可以简单分析出来,
首先使用的时候用的是'v-model',那就一定有两个一个是'value',一个是'input'事件,
再就是有一个'solt' 用来放置封装好的'checkbox'组件
~~~
>[danger] ##### 改进我们的checkbox 组件让更像原生用法
~~~
1.现在我们要将我们上一个章节的'checkbox'可以也绑定数组,对照iview我们大体设计如下:
~~~
* iview
~~~
选项 1
~~~
* 我们大体猜想
~~~
1.iview 中'选项 1 ' label 作为封装组件的'props'中的属性传递给
'label',在就保证这一组的input中'v-model'绑定都是相同的数组
~~~
~~~
~~~
>[danger] ##### 改造checkbox组件
~~~
1.我们将checkbox组件通过if分割成了两组,一组是我们之前的用绑定是'String,Number,Boolean'这三种类型,
一组是我们为了让他像原生一样绑定的是数组
2.我们现在可以确定一点的思路就是如果是最外层使用的是'CheckboxGroup' 组件,那将使用的就是我们的数组
形式的input,这里在'mounted'声明周期使用'findComponentUpward'在组件通讯章节讲的写法,去找当前组件的
父级是否是使用'CheckboxGroup' 组件包裹来决定使用哪种模式的'checkbox'
~~~
~~~
~~~
>[danger] ##### 现在来分析我们的 CheckboxGroup 组件写法
~~~
1.上面有个'updateModel'方法具体思路,我们先思考一下首先,'CheckboxGroup' 组件插槽中的每一个
'checkedbox' 组件的'v-model'绑定的数组一定要是一个数组,这个数组就是'CheckboxGroup' 传入进来的数组
2.因此现在的思路就是使用我们组件通信章节说的'findComponentsDownward'向下找到所有在当前组件
'CheckboxGroup' 里面的每一个'checkedbox'组件,并且给他们的'v-model'绑定的数组值都赋值成'CheckboxGroup'
的数组。
3.在'updateModel'方法中有个地方需要说明一下:
if (this.childrens) {
// 这里的this 指代的是当前'CheckboxGroup' 组件,首先因为是一个实例所以肯定是一个对象
// 这里又使用了es6 解构获取 value 值,这个value值是谁呢?
// 首先我们看使用 ,因此其实当前这个组件有个隐藏的props
// 这个props 就是value 这个value 绑定的又是获取每一项的数组
// 因此将每一项'checkedbox'要管理的数组我们找到了,现在又有每一个子项的对象
// 将每一个子项对象中的'model ' 都绑定上这个统一的数组
const { value } = this;
console.log(this);
this.childrens.forEach(child => {
child.model = value;
if (update) {
child.currentValue = value.indexOf(child.label) >= 0;
child.group = true;
}
});
}
~~~
~~~
~~~
>[danger] ##### 使用的效果
~~~
';
Checked names: {{ checkedNames }}
{{multiple}}
选项 1
选项 2
~~~