直到我在 Vue Devtools 中单击 VueJS 组件才会呈现

Posted

技术标签:

【中文标题】直到我在 Vue Devtools 中单击 VueJS 组件才会呈现【英文标题】:VueJS component wont render until I click on it in Vue Devtools 【发布时间】:2018-04-19 03:34:20 【问题描述】:

我在博客后端的一个部分(不是 SPA)上使用 VueJS 2.5.3,该部分进行 API 调用以检查附加到帖子的特色图片。

如果找到,它会使用一个子组件来显示图像。问题是 API 调用成功后子组件没有渲染,因此图像对象也没有传递给它。

As you can see in this GIF,子组件没有渲染<!---->,我有一个v-if 来检查图像是否存在。但是,如果我单击 Vue DevTools 中的子组件,子组件会按预期呈现和显示图像。

我的问题是为什么只有在 Vue Devtools 中单击子组件后才会呈现子组件?当你点击一个组件时,Vue Devtools 是否会触发某种事件?

这是子组件:

<template>
    <div v-if="showImage" class="featured-image-container" :class="[ size ]">
        <img :src="processedSrc" >
    </div>
</template>

<script>
export default 
    props: 
        image: 
            type: Object
        ,
        size: 
            type: String,
            required: true
        
    ,
    data () 
        return 
            showImage: false
        
    ,
    computed: 
        processedSrc: function () 
            if (this.image && typeof this.image === 'object') 
                this.showImage = true
                return this.image.sizes[this.size].file
             else 
                this.showImage = false
            
        
    

</script>

And here is a link to the code for the parent and child components:

【问题讨论】:

能否给出相关代码?你的v-if 里有什么? @thanksd 当然,如果 API 调用返回图像,v-if 是我设置的简单布尔值。 v-if="showImage"我可以确认找到图像时已正确设置为true。 @thanksd 我已将父组件和子组件的完整代码添加到原始问题的底部。 请将PostFeaturedImage.vue 组件的代码添加到问题中,而不仅仅是提供链接。这就是核心问题所在,如果链接断开,就很难判断是什么导致了问题。 【参考方案1】:

问题出在您的 PostFeaturedImage.vue 组件中。您依赖计算值 processedSrc 来设置数据属性 showImage

但是,showImage 最初是 false,您在根元素的 v-if 指令中使用它。这意味着 Vue 不会渲染该元素或其中的 &lt;img&gt; 元素。

Vue 中的计算属性是延迟加载的,这意味着它们的函数在被引用之前不会被调用。由于processedSrc 计算属性仅在&lt;img&gt; 元素上被引用(并且由于该元素没有被渲染),因此它的方法不会被调用,这意味着showImage 属性永远不会设置为true

但是,当您在 Vue DevTools 中检查组件时,它会列出所有计算属性,这意味着 processedSrc 计算的方法被调用,并且在这种情况下正在设置 showImage 属性。


解决您的问题的最简单方法是使用v-show 而不是v-if,因为v-show 中的元素将被隐藏,但即使值为false,仍会呈现。

但是,我几乎从不建议根据计算属性的函数中的逻辑来设置数据属性的值。它会产生意想不到的、难以调试的副作用,从而导致您目前遇到的问题。

我建议将您的showImage 属性也设为计算属性,基于当前在processedSrc 计算方法中确定其值的逻辑。然后,您可以决定是否尝试根据showImage的值计算processedSrc的值。

computed: 
  showImage: function() 
    return this.image && typeof this.image === 'object';
  ,
  processedSrc: function () 
    if (this.showImage) 
      return this.image.sizes[this.size].file;
    
  

这样,更容易看到什么影响了什么,你的代码也更容易维护。

【讨论】:

那么 DevTools 真的会触发计算机属性吗?这会在您调试时导致一些奇怪的事情吗? 是的。它确实如此。计算属性的基本思想是根据依赖的 Vue 实例属性计算并返回一个值。所以 Vue 假设如果你从不尝试访问计算属性,那么运行该方法来计算值是没有意义的。但是,如果您违反计算属性的用途规则(通过设置其他属性,或发出事件,或进行 api 调用等),如果您的计算属性从未被访问过,您将得到一些意想不到的结果(或者如果它在您不期望的情况下被访问,例如在使用 Vue DevTools 进行检查时)。 感谢您对 Vue Devtools 的解释以及关于调整我如何使用计算属性的提示。

以上是关于直到我在 Vue Devtools 中单击 VueJS 组件才会呈现的主要内容,如果未能解决你的问题,请参考以下文章

Vue DevTools 可以检测到 Vue.js 但未显示在 F12 面板中

Vue.js 开发工具未显示

Nativescript-Vue 7 - 创建新项目后,我在 google chrome devtools 中看不到网络活动

如何禁止他人通过vue的devtools 查看

Vue devtools 刷新后停止

Vue DevTools 正确更新但浏览器窗口不正确