Vue 实例中使用$refs的注意事项


Posted in Vue.js onJanuary 29, 2021

在开发过程中,经常会通过实例的vm.$refs(this.$refs)取得通过ref注册过的组件,并进行相应操作,但存在取不到元素的情况,其根本原因是因为$refs只能取得mounted(渲染)之后的元素。

Vue 实例中使用$refs的注意事项

例如,在这种情况中,若flag从真值切换到假值取不到节点是正常的,因为v-if如果为假值,那么该节点不会被渲染。

但如果从假值切换到真值时,也可能取不到节点,这是因为渲染需要时间,通常可以使用$nextTick()解决。

...
<el-table v-if="flag" ref="table">
  <el-table-column prop="prop1"></el-table-column>
  <el-table-column prop="prop2"></el-table-column>
</el-table>
...
 
 
export default {
  methods: {
    this.$refs.table.XXX()
  }
}

但存在一个极特殊的情况,第一次页面渲染的时候,$refs也取不到值。这个时候就要考虑v-show进行组件元素的隐藏与展示。

因为v-show是通过css的display:none进行隐藏控制,所以一开始就会渲染,肯定能够取到元素

补充:Vue.js中ref ($refs)用法举例总结及应注意的坑

一、根据官方文档总结的用法:

看Vue.js文档中的ref部分,自己总结了下ref的使用方法以便后面查阅。

1、ref使用在外面的组件上

HTML 部分

<div id="ref-outside-component" v-on:click="consoleRef">
  <component-father ref="outsideComponentRef">
  </component-father>
  <p>ref在外面的组件上</p>
</div>

js部分

var refoutsidecomponentTem={
    template:"<div class='childComp'><h5>我是子组件</h5></div>"
  };
  var refoutsidecomponent=new Vue({
    el:"#ref-outside-component",
    components:{
      "component-father":refoutsidecomponentTem
    },
    methods:{
      consoleRef:function () {
        console.log(this); // #ref-outside-component   vue实例
        console.log(this.$refs.outsideComponentRef); // div.childComp vue实例
      }
    }
  });

2、ref使用在外面的元素上

HTML部分

<!--ref在外面的元素上-->
<div id="ref-outside-dom" v-on:click="consoleRef" >
  <component-father>
  </component-father>
  <p ref="outsideDomRef">ref在外面的元素上</p>
</div>

JS部分

var refoutsidedomTem={
    template:"<div class='childComp'><h5>我是子组件</h5></div>"
  };
  var refoutsidedom=new Vue({
    el:"#ref-outside-dom",
    components:{
      "component-father":refoutsidedomTem
    },
    methods:{
      consoleRef:function () {
        console.log(this); // #ref-outside-dom  vue实例
        console.log(this.$refs.outsideDomRef); //  <p> ref在外面的元素上</p>
      }
    }
  });

3、ref使用在里面的元素上---局部注册组件

HTML部分

<!--ref在里面的元素上-->
<div id="ref-inside-dom">
  <component-father>
  </component-father>
  <p>ref在里面的元素上</p>
</div>

JS部分

var refinsidedomTem={
    template:"<div class='childComp' v-on:click='consoleRef'>" +
            "<h5 ref='insideDomRef'>我是子组件</h5>" +
         "</div>",
    methods:{
      consoleRef:function () {
        console.log(this); // div.childComp  vue实例 
        console.log(this.$refs.insideDomRef); // <h5 >我是子组件</h5>
      }
    }
  };
  var refinsidedom=new Vue({
    el:"#ref-inside-dom",
    components:{
      "component-father":refinsidedomTem
    }
  });

4、ref使用在里面的元素上---全局注册组件

HTML部分

<!--ref在里面的元素上--全局注册-->
<div id="ref-inside-dom-all">
  <ref-inside-dom-quanjv></ref-inside-dom-quanjv>
</div>

JS部分

Vue.component("ref-inside-dom-quanjv",{
    template:"<div class='insideFather'> " +
          "<input type='text' ref='insideDomRefAll' v-on:input='showinsideDomRef'>" +
          " <p>ref在里面的元素上--全局注册 </p> " +
         "</div>",
    methods:{
      showinsideDomRef:function () {
        console.log(this); //这里的this其实还是div.insideFather
        console.log(this.$refs.insideDomRefAll); // <input type="text">
      }
    }
  });
  var refinsidedomall=new Vue({
    el:"#ref-inside-dom-all"
  });

二、应注意的坑

1、如果通过v-for 遍历想加不同的ref时记得加 :号,即 :ref =某变量 ;

这点和其他属性一样,如果是固定值就不需要加 :号,如果是变量记得加 :号

Vue 实例中使用$refs的注意事项

2、通过 :ref =某变量 添加ref(即加了:号) ,如果想获取该ref时需要加 [0],如this.$refs[refsArrayItem] [0];如果不是:ref =某变量的方式而是 ref =某字符串时则不需要加,如this.$refs[refsArrayItem]

Vue 实例中使用$refs的注意事项

加和不加[0]的区别--未展开

Vue 实例中使用$refs的注意事项

加和不加[0]的区别--展开了

3、想在element ui 对话框打开后取dom时,应该使用$nextTick,而不是直接使用this.$refs. imgLocal2:

console.log('this.$refs.imgLocal2外面', this.$refs.imgLocal2);
    setTimeout(() => {
     console.log('this.$refs.imgLocal2 setTimeout', this.$refs.imgLocal2);
    }, 500); // 不推荐
    this.$nextTick(() => {
     console.log('this.$refs.imgLocal2 $nextTick', this.$refs.imgLocal2);
    });

Vue 实例中使用$refs的注意事项

以上为个人经验,希望能给大家一个参考,也希望大家多多支持三水点靠木。如有错误或未考虑完全的地方,望不吝赐教。

Vue.js 相关文章推荐
Vue使用Element实现增删改查+打包的步骤
Nov 25 Vue.js
Vue Elenent实现表格相同数据列合并
Nov 30 Vue.js
vue使用element-ui实现表单验证
Dec 13 Vue.js
Vue如何跨组件传递Slot的实现
Dec 14 Vue.js
vue 在单页面应用里使用二级套嵌路由
Dec 19 Vue.js
解决vue项目本地启动时无法携带cookie的问题
Feb 06 Vue.js
Vue包大小优化的实现(从1.72M到94K)
Feb 18 Vue.js
Vue实现tab导航栏并支持左右滑动功能
Jun 28 Vue.js
vue ref如何获取子组件属性值
Mar 31 Vue.js
VUE之图片Base64编码使用ElementUI组件上传
Apr 09 Vue.js
vue使用element-ui按需引入
May 20 Vue.js
Vue2项目中对百度地图的封装使用详解
Jun 16 Vue.js
vue 项目@change多个参数传值多个事件的操作
Jan 29 #Vue.js
vue 实现click同时传入事件对象和自定义参数
Jan 29 #Vue.js
聊聊vue 中的v-on参数问题
Jan 29 #Vue.js
vue集成一个支持图片缩放拖拽的富文本编辑器
Jan 29 #Vue.js
Vue 事件的$event参数=事件的值案例
Jan 29 #Vue.js
Vue 3自定义指令开发的相关总结
Jan 29 #Vue.js
vue 中this.$set 动态绑定数据的案例讲解
Jan 29 #Vue.js
You might like
LotusPhp笔记之:基于ObjectUtil组件的使用分析
2013/05/06 PHP
PHP 开发者该知道的 5 个 Composer 小技巧
2016/02/03 PHP
简单实现php上传文件功能
2017/09/21 PHP
PHP判断是否是微信打开,浏览器打开的方法
2018/03/14 PHP
javascript 弹出层组件(升级版)
2011/05/12 Javascript
Three.js源码阅读笔记(光照部分)
2012/12/27 Javascript
js实现屏幕自适应局部代码分享
2015/01/30 Javascript
EasyUi datagrid 实现表格分页
2015/02/10 Javascript
JavaScript控制图片加载完成后调用回调函数的方法
2015/03/20 Javascript
js点击列表文字对应该行显示背景颜色的实现代码
2015/08/05 Javascript
jquery遍历json对象集合详解
2016/05/18 Javascript
新手学习前端之js模仿淘宝主页网站
2016/10/31 Javascript
微信小程序 天气预报开发实例代码源码
2017/01/20 Javascript
angularJS+requireJS实现controller及directive的按需加载示例
2017/02/20 Javascript
JS添加或删除HTML dom元素的方法实例分析
2019/03/05 Javascript
jQuery动态生成的元素绑定事件操作实例分析
2019/05/04 jQuery
Python urllib模块urlopen()与urlretrieve()详解
2013/11/01 Python
获取django框架orm query执行的sql语句实现方法分析
2019/06/20 Python
python中时间、日期、时间戳的转换的实现方法
2019/07/06 Python
简单了解Django ContentType内置组件
2019/07/23 Python
python range实例用法分享
2020/02/06 Python
Python matplotlib修改默认字体的操作
2020/03/05 Python
python实现同一局域网下传输图片
2020/03/20 Python
Python+Appium实现自动化测试的使用步骤
2020/03/24 Python
彪马日本官网:PUMA日本
2019/01/31 全球购物
金融专业推荐信
2013/11/14 职场文书
七匹狼男装广告词
2014/03/21 职场文书
植树节口号
2014/06/21 职场文书
群众路线专项整治方案
2014/10/27 职场文书
2014小学二年级班主任工作总结
2014/12/05 职场文书
教代会闭幕词
2015/01/28 职场文书
慈善献爱心倡议书
2015/04/27 职场文书
工程款催款函
2015/06/24 职场文书
使用Golang的channel交叉打印两个数组的操作
2021/04/29 Golang
nginx从安装到配置详细说明(安装,安全配置,防盗链,动静分离,配置 HTTPS,性能优化)
2022/02/12 Servers
JavaScript实现两个数组的交集
2022/03/25 Javascript