Vue修改数据页面不更新的原因和解决方案
vue2是通过Object.defineProperty来实现数据响应式 ,因此在vue中写在data中的属性是可以转换成getter和setter,换句话说就是响应式的,其他定义在data之外的数据,是无法响应的渲染,意思就是改变数据 页面也不会刷新,所以一切要渲染到页面上的数据,必须写在data中.
列举几个不刷新的实例: 修改对象的某一属性 vue只会将已经在data中声明的属性变为响应,没有声明的是不响应的
<template> <div> <div v-for=item in list :key="item">{ { item}}</div> <button @click=click>改变</button> <button @click=hadelClick>解决方法</button> </div> </template> <script> export default({ data(){ return{ list:{ a:a,b:b}, } }, methods: { click() { // 未声明不触发渲染 this.list.c=c }, hadelClick(){ // 解决方法,使用vue提供的$set方法来触发渲染 this.$set(this.list,d,d) } } }) </script>
当然如果我们要添加多个属性,可以使用 Object.assign() 用于将所有可枚举属性的值从一个或多个源对象复制到目标对象,并返回目标对象。(简单说就是合并到第一个参数中)
this.list = Object.assign({ },this.list,{ c:c,d:d})
修改数组对象的某一属性
<template> <div> <div v-for=item in list>{ { item.a}}</div> <button @click=click>改变</button> <button @click=hadelClick>解决方法</button> </div> </template> <script> export default({ data(){ return{ list:[{ a:vue},{ a:react},{ a:js}], } }, methods: { click() { //想这样直接给数组中的某一个对象直接赋值,是无法动态渲染的(即改变了数据,页面不渲染) this.list[0] = { a:css} //页面不渲染 console.log(this.list) //[{ a:css},{ a:react},{ a:js}] }, hadelClick(){ // 解决方法,使用vue提供的$set方法来触发渲染 this.$set(this.list[1],a,css) console.log(this.list)//[{ a:css},{ a:css},{ a:js}] } } }) </script>
vue中更多的是数组的操作不刷新,一种是通过索引赋值,一种是修改数组长度,vue官方也给出了答案: 数组的API,中能够改变原始数组的都能触发更新;
push() pop() shift() unshift() splice() sort() reverse()
如果上述全都无法执行,可以使用this.$forceUpdate()方法(强制刷新)
<template> <div> <div v-for=item in list>{ { item.a}}</div> <button @click=click>改变</button> <button @click=hadelClick>解决方法</button> </div> </template> <script> export default({ data(){ return{ list:[{ a:vue},{ a:react},{ a:js}], } }, methods: { click() { this.list[0] = { a:css} //页面不渲染 console.log(this.list) //[{ a:css},{ a:react},{ a:js}] }, hadelClick(){ this.list[0] = { a:css} //页面不渲染 console.log(this.list) //[{ a:css},{ a:react},{ a:js}] this.$forceUpdate();//强制刷新 } } })