尽管组件中存在prop和事件,但有时候仍需要直接访问一个子组件;为了达到这个目的,可以通过ref这个属性为子组件赋予一个ID引用。
vue2组件中ref的使用
//base-input子组件
<template>
<input
ref="input"
type="text"
:value="value"
@input="$emit('input', $event.target.value)"
/>
</template>
<script>
export default {
props:{
value:[String, Number]
},
data(){
return { }
},
methods:{
/*获取焦点方法*/
focus(e){
this.$refs.input.focus();
}
}
}
</script>
/*父组件*/
<template>
<div class="index-main">
<base-input ref="usernameInput" v-model="inputVal"></base-input>
</div>
</template>
<script>
import base-input from '../components/BaseInput';//普通组件
export default {
components:{
'base-input': base-input
},
data(){
return {
inputVal:""
}
},
mounted(){
/*父组件页面加载完成后使input自动获取焦点*/
this.$refs.usernameInput.focus();
},
}
</script>
父组件使用ref属性定义一个唯一值,通过this.$refs.usernameInput访问子组件中的data和method;
$refs 只会在组件渲染完成之后生效,并且它们不是响应式的。这仅作为一个用于直接操作子组件的“逃生舱”——你应该避免在模板或计算属性中访问 $refs。
vue3组件中ref的用法
当vue3子组件使用组合式API时,即使用< script setup >的写法,组件是默认关闭的——即通过模板引用或者 $parent 链获取到的组件的公开实例,不会暴露任何在 < script setup> 中声明的绑定。
如果需要暴露子组件中某个方法或者属性,需要通过defineExpose 编译器宏来显式指定。
/*子组件*/
<template>
<input ref="inputRef" type="text" :value="value" />
</template>
<script setup>
import { ref } from 'vue'
const props = defineProps({
value: [String,Number]
})
const inputRef = ref();
const msg = ref('测试');
function focus(){
inputRef.value.focus();
}
defineExpose({focus,msg})
</script>
/*父组件*/
<script setup>
import {ref } from 'vue';
import BaseInput from '@/components/BaseInput.vue'
const inputVal = ref('');
const usernameInput = ref();
onMounted(()=>{
console.log(usernameInput.value.msg);//测试,获取子组件msg的值
usernameInput.value.focus(); //调取子组件的focus方法
})
</script>
<template>
<div class="index-main">
<BaseInput ref="usernameInput" :value="inputVal"></BaseInput>
</div>
</template>