Vue踩过的坑

-
-
2024-06-13

 

0x01 对引用对象赋值引用不会触发响应!

直接上代码

<template>
    <div class="userSelector">
        <input v-model="sUserName"><button @keydown.enter="searchUser" @click="searchUser">检索用户</button>
    </div>
    <div>
        <userCat v-show="isNull" /> <!-- userCat组件在下面 -->
    </div>
</template>
<script>
import userCat from './userCat.vue'
import Data from '@/datas/data.js'
export default {
 . . . 
    data() {
        return {
            sUserName: "",
            user: Data.user
        }
    },
    methods: {

        async searchUser() {
            const data = { text: this.sUserName.toString() };
            try {
                const response = await this.axios.post("http://localhost:9090/api/findbyname", data);
                console.debug(response.data);
                if (response.data.length != 0) {
                    this.user = response.data;  // 这里之间赋值引用,Data.user的数据确实变了,但userCat里的{{ user }}就是不变
                    console.debug(this.user);
                } else {
                    alert("妹有啊!");
                }
            } catch (error) {
                alert(error);
            }
        }
    },

}
</script>

image

![image](https://pic.aketer.me//i/e1144918-0a79-4264-916b-c076f4d98450.jpg)

这里怎么点下面插件内容都不变,我看后端给的回应都正常的,打了个debug输出Data,Data里面的user也对的,怎么改都不行,最后翻了半天文档才搞明白

下面要这么写

—|  this.user = response.data 
 |
+|  Object.keys(response.data).forEach(key => {
+|      this.user[key] = response.data[key];
+|  });

响应式系统的数据钩子在对象上(settergetter),对象内容改变会触发响应,但对象的引用上没有,给引用赋值新的引用虽然数值变了,但钩子在旧的对象上,和新的没关系,所以不能触发响应。只有改旧的对象或者他的子对象,才能触发响应事件。可以使用.array.map .splice或者使用Vue全局响应的工具。

btw, Vue的$set在Vue3里已经废弃了,不能用了

 

0x02 插值表达式{{}}中绑定响应式对象的子元素,不会触发响应

太怪了,搞一晚上

在Vue中,当你使用双大括号插值(Mustache 语法){{ user }} 时,它会自动调用 user.toString() 方法,这会导致 user.iduser.username 的值被提取并显示。当 user 对象发生变化时,Vue 会检测到 user 对象的引用发生了变化,因此会重新渲染 {{ user }} 的内容。

但是,user.iduser.username 是直接引用 user 对象的属性,并不会触发 Vue 的响应式系统。因此,即使 user 对象本身发生了变化,user.iduser.username 的值也不会自动更新。

如果你希望 user.iduser.usernameuser 对象发生变化时也能够自动更新,你可以使用 Vue 的计算属性或者监听 user 对象的变化来手动更新这些值。例如:

<template>
<!-- 调试点--> {{user}} <!-- 这里在user刷新之后马上会刷新 -->
    <div  class="userCat">
        <div class="userDetails"> 
        	<h2> {{user.username}} </h2>  <!-- 这里当user刷新后根本不会变-->
            <h2>用户名: {{ username }}</h2>  <!-- 在这里引入个新变量,在computed里更新,因为响应式更新会触发computed -->
            <slot />
        </div>
    </div>
</template>

<script>
// 因为传参太麻烦,我把数据放到data.js里了,data.js放下面 
import Data from '@/datas/data.js';
export default {
    data() {
        return {
            user: Data.user // 绑定user
        };
    },
    computed: {
        username() {return this.user.username;},
    }
}
</script>
// data.js
const Data = new reactive({
  isUser,
  isBook,
  books: [],
  users:[],
  book,
  user:{}
});

export default Data;

<img src="https://pic.aketer.me//i/0ee05a2b-c1b3-403f-99ff-72461a072f9c.jpg" alt="image">

ok了

“您的支持是我持续分享的动力”

微信收款码
微信
支付宝收款码
支付宝

目录