Vue.js数据绑定样式背景图片无法工作

140

我试图绑定元素中图像的src,但似乎不起作用。我得到了一个"无效表达式。生成的函数体:{backgroundImage: {url(image)} "。

文档中说要使用“短横线”或“驼峰式”。

<div class="circular" v-bind:style="{ backgroundImage: { url(image) }"></div>

这是一个样例代码:https://jsfiddle.net/0dw9923f/2/

19个回答

315

问题在于 backgroundImage 的值需要像这样的字符串:

<div class="circular" v-bind:style="{ backgroundImage: 'url(' + image + ')' }"></div>

这是一个简化版的示例,它可以正常工作:https://jsfiddle.net/89af0se9/1/

关于kebab-case的评论,以下是如何实现:

<div class="circular" v-bind:style="{ 'background-image': 'url(' + image + ')' }"></div>

换句话说,v-bind:style 的值只是一个普通的 JavaScript 对象,并遵循相同的规则。

更新:关于为什么您可能会在此处遇到麻烦,还有一点需要注意。

您应该确保您的 image 值被引用,以便最终生成的字符串是:

url('some/url/path/to/image.jpeg')
否则,如果您的图片URL中包含特殊字符(如空格或括号),则浏览器可能无法正确应用它。在JavaScript中,赋值看起来像这样:
this.image = "'some/url/path/to/image.jpeg'"
或者
this.image = "'" + myUrl + "'"

在技术上,这可以在模板中完成,但为了保持有效的HTML而需要进行的转义工作是不值得的。

更多信息请参见:是否必须对url()的值进行引用?


18
从2016年3月份开始,即使文档中说它可以使用连字符(background-image),但现在必须使用驼峰式命名法(backgroundImage)。请注意,这不改变原意。 - andrewtweber
2
如果有人像我一样粗心,可能会写成backgroundImage: image而不是backgroundImage: 'url('+image+')'。我太过关注Vue的语法,忘记了url() - bendytree
在Vue组件中,我只需要写v-bind:style="{ 'background-image': url(image) }"就可以了,但是在组件外部(普通页面上)似乎需要将url放在引号中。有人知道为什么吗? - Keara
@Keara,除非您有一个名为“url”的函数在适当的范围内生成正确的内容,否则它曾经起作用是没有意义的。您能否创建一个演示它的fiddle? - David K. Hess
2
@David 我想我实际上写了一个url方法,然后忘记了,它正好做我期望的事情...这真的很有趣。由于Vue组件在不同的文件中,我无法在fiddle中进行真正的测试,但我相信这才是导致奇怪行为的原因。谢谢! - Keara
请记住,在属性名称中不要使用“-”或任何数学运算符号。 - Mahdi Khansari

53
<div :style="{'background-image': 'url(' + require('./assets/media/img.jpg') + ')'}"></div>

32

另一种解决方案:

<template>
  <div :style="cssProps"></div>
</template>

<script>
  export default {
    data() {
      return {
        cssProps: {
          backgroundImage: `url(${require('@/assets/path/to/your/img.jpg')})`
        }
      }
    }
  }
</script>

这个解决方案的更大优点是什么? 首先,它更加清晰。如果您正在使用Vue CLI(我假设您在使用),那么您可以使用webpack加载它。

注意:不要忘记 require() 始终相对于当前文件的路径。


21
<div :style="{ backgroundImage: `url(${post.image})` }">

有多种方法,但我发现模板字符串简单易懂。


4
来这里发布这个。ES6绝对是最好的方法。 - corysimmons
ES5 模板字面量似乎是新的前进方向。连接操作很糟糕。 - zEELz
这绝对是最好的方法,而且更加清晰。 - Evidence Ekanem

11

我在这篇帖子中搜索,但没有人发布带有动态文件名的require,这就是为什么我要发布它的原因。

我搜索了这篇帖子,但没看到任何使用动态文件名的require的帖子,所以我来发一个。

:style="{ backgroundImage: `url(${require('@/assets/' + banner.image)})` }"

我不需要它是必需的,只需要是动态的,这个完美地运作。 - Andrew West

8

我尝试了@david的答案,但并没有解决我的问题。经过很多麻烦,我编写了一个方法并返回带有样式字符串的图像。

HTML 代码

<div v-for="slide in loadSliderImages" :key="slide.id">
    <div v-else :style="bannerBgImage(slide.banner)"></div>
</div>

方法

bannerBgImage(image){
    return `background-image: url(${image})`;
},

1
我不喜欢在不改变组件状态时使用“methods”。这就是“computed”的作用。 - Narxx
@Narxx当你在许多地方都有图片需要修复时,方法是非常有用的。只需调用该方法并将图像作为参数传递到想要修复背景图像的任何位置即可。这样就完成了! - devzakir
你可以使用computed做同样的事情。Computed也可以接受参数,尽管语法略有不同(但并不多)。在这里阅读:https://dev59.com/IFkS5IYBdhLWcg3wASHc - Narxx

4
对于单个重复组件,这种技术对我有效。
<div class="img-section" :style=img_section_style >

computed: {
            img_section_style: function(){
                var bgImg= this.post_data.fet_img
                return {
                    "color": "red",
                    "border" : "5px solid ",
                    "background": 'url('+bgImg+')'
                }
            },
}

4

尝试使用encodeURI()

我遇到的问题是由于URL中存在特殊字符和/或空格引起的。

所以我不得不将这个:

:style="{ backgroundImage : 'url(' + item.media.url + ')' }"

更改为这个:

:style="{ backgroundImage : 'url(' + encodeURI(item.media.url) + ')' }"


4

对我来说,接受的答案似乎没有解决我的问题,但是这个方法解决了

确保你的backgroundImage声明被包含在url(和引号中,这样样式才能正确地工作,无论文件名是什么。

ES2015样式:

<div :style="{ backgroundImage: `url('${image}')` }"></div>

不使用ES2015:

<div :style="{ backgroundImage: 'url(\'' + image + '\')' }"></div>

Source: vuejs/vue-loader issue #646


3

我使用了VUE选项(~@/

我定义了一个类

<template>
   <v-container class="bgExampleClass" fuild>
      <!-- Content-->
   </v-container>
</template>
<script></script>
<style>
  .bgExampleClass{
    background-image: url('~@/assets/imgs/backgroundExample.jpg');
  }
</style>

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接