一直以来,我对于 VueJS 中对于使用 ref
注册的组件,在使用 $refs
调用时,为什么有时候是一个 DOM元素/组件实例,是时候会是一个实例数组。
所以在很长一段时间内我觉得 ref
注册的的组件在使用 $refs
调用时有很大的不确定性,虽然我的弹窗组件一直都是用的 $refs.modal.open()
来打开的。
直到前一段时间,我在一个场景下想在 v-for
循环渲染的组件下 slot
模板中想使用 ref
注册成一个实例集合来调用时,发现怎么样重写返回的都只是一个组件实例,而不是一个组件实例集合。
所以有了这样一篇笔记。
注册 | ref
用来给元素或子组件注册引用信息。引用信息将会注册在父组件的 $refs 对象上。
- 如果在普通的 DOM 元素上使用,引用指向的就是 DOM 元素;
- 如果用在子组件上,引用就指向组件实例:
关于 ref
注册时间的重要说明:因为 ref
本身是作为 渲染结果 被创建的,在初始渲染的时候你不能访问它们 - 它们还不存在!$refs
也 不是响应式 的,因此你不应该试图用它在模板中做数据绑定。
所以不要在 mounted()
之前的生命周期钩子里边直接使用 $refs
来获取元素,
或者在没有渲染组件的情况下调用元素内的属性或方法,如果一定要的话,记得放在 $nextTick()
里。
使用 | $refs
一个对象,持有注册过 ref attribute 的所有 DOM 元素和组件实例。
- 只读
- 允许父级组件通过
$refs
来访问子组件实例内部元素的访问,比如来访问子组件实例内的data
和methods
- 当
ref
和v-for
一起使用的时候,将得到一个 DOM 节点数组 或 包含了对应数据源 的组件实例的。
1、什么时候只返回一个组件/DOM实例
一般来说,直接在一个没有使用 v-for
循环的元素上使用 ref
注册的元素,在使用 this.$refs.xxx
获取时,返回的只会是一个组件实例。
2、什么时候返回一个实例集合
按照文档上边来看,在使用 v-for
循环的元素上使用 ref
注册的元素,在使用 this.$refs.xxx
获取时,会返回一个实例集合。
有没有其他办法?比如我不是使用 v-for
循环出来的实例,但是我想注册在同一个 ref
下。
暂时没有办法。
附:
ref — Vue.js
vm.$refs — Vue.js
访问子组件实例或子元素 — Vue.js
Document.querySelectorAll - MDN
querySelectorAll 方法相比 getElementsBy 系列方法有什么区别?- 知乎