vue3通过ref获取元素及注意事项

常规用法(获取单个元素)

<template>
    <div class="search-input">
        <input type="text" ref="searchInputElem" v-model="searchValue" @keyup.enter="onSearch" placeholder="输入关键词" />    <!-- 【step1】dom层定义ref="searchInputElem",注意ref不要用双向绑定形式(即:ref) -->
    </div>
</template>

<script>
import { onMounted, reactive, toRefs, ref } from "vue";
export default {
    setup() {
        const state = reactive({
            searchValue: ""
        });

        function onSearch(){ ... }

        const searchInputElem = ref(null)  //【step2】定义searchInputElem 【注意】:这里定义的searchInputElem必须和dom层里定义的ref="searchInputElem"保持一致
        onMounted(()=>{
            console.log(searchInputElem.value)  //【step4】:获取元素,注意需要在元素加载出来后才能获取,比如可在onMounted生命周期或者nextTick中使用
            searchInputElem.value.focus()
        })

        return {
            onSearch,
            searchInputElem,  // 【step3】注意:必须return出来
            ...toRefs(state),
        };
    },
};
</script>

基于自己代码风格的写法(获取单个元素)

<template>
    <div class="search-input">
        <input type="text" ref="searchInputElem" v-model="searchValue" @keyup.enter="onSearch" placeholder="输入关键词" />    <!-- 【step1】dom层定义ref="searchInputElem", 注意ref不要用双向绑定形式(即:ref)-->
    </div>
</template>

<script>
import { onMounted, reactive, toRefs } from "vue";
export default {
    setup() {
        const state = reactive({
            searchValue: "",
            searchInputElem: null  //【step2】定义searchInputElem 【注意】:这里定义的searchInputElem必须和dom层里定义的ref="searchInputElem"保持一致
        });

        function onSearch(){ ... }

        onMounted(()=>{
            console.log(state.searchInputElem)  //【step4】:获取元素,注意需要在元素加载出来后才能获取,比如可在onMounted生命周期或者nextTick中使用
            state.searchInputElem.focus()
        })

        return {
            onSearch,
            ...toRefs(state),  // 【step3】注意:必须return出来
        };
    },
};
</script>

基于自己代码风格的写法(获取多个元素)

<template>
    <div class="search-input" v-for="(item,index) in lits" :key="index">
        <div type="text" :ref="(defaultData)=>getTheInstance(defaultData,item)">{{item.name}}</div>    <!-- 【step2】dom层定义:ref="(defaultData)=>getTheInstance(defaultData,item)"-->
    </div>
</template>

<script>
import { reactive, toRefs } from "vue";
export default {
    setup() {
        const state = reactive({
            theInstanceGather: {}  //【step3】定义theInstanceGather,用于存储多个元素实例
        });

        // 【step1】定义一个方法,用于获取元素实例。即在dom层中:ref绑定的那个方法
        function getTheInstance(elem,info){  //elem是元素实例,info是for循环中的数据
            if(elem){
                state.theInstanceGather[`instance${info.id}`] = elem
                console.log(state.theInstanceGather)  //打印结果如下图
            }
        }

        return {
            getTheInstance,
            ...toRefs(state), 
        };
    },
};
</script>

基于上述方法实现父组件调用子组件中定义的方法

【父】
<div>
    <comp-son ref="compSonInstance" />  <!-- 【step1】dom层定义ref="compSonInstance", 注意ref不要用双向绑定形式(即:ref)-->
</div>

<script>
import { onMounted, reactive, toRefs } from "vue";
export default {
    setup() {
        const state = reactive({
            compSonInstance: null  //【step2】定义compSonInstance 【注意】:这里定义的compSonInstance必须和dom层里定义的ref="compSonInstance"保持一致
        });

        function onSearch(){ ... }

        onMounted(()=>{
            console.log(state.compSonInstance)  //【step4】:获取子组件实例,注意需要在元素加载出来后才能获取,比如可在onMounted生命周期或者nextTick中使用
            state.compSonInstance.testFromSon()  //打印出 "我是子组件的方法"
        })

        return {
            ...toRefs(state),  // 【step3】注意:必须return出来
        };
    },
};
</script>
【子】
export default {
    name: "CompSon",
    setup() {
        function testFromSon(){  //【step1】 这里定义一个子组件的方法
            console.log("我是子组件的方法")
        }
        
        return {
            testFromSon,  //【step2】需要return出去
        }
    },
};
posted @   huihuihero  阅读(1005)  评论(0编辑  收藏  举报
相关博文:
阅读排行:
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
点击右上角即可分享
微信分享提示