开发者问题收集

Vue 属性未定义

2018-04-28
164

我正在尝试完成 FreeCodeCamp 挑战之一。这是一个随机引号生成器,我终于找到了一个可以在 CodePen 上运行的 API 站点。

我的问题是它似乎可以工作。我运行脚本,它给了我一个随机引号,因此 API 和 fetch() 可以工作。但控制台一直给我一个 无法读取未定义的属性“引号” ,这会破坏我的 JavaScript,并且不允许我单击按钮来获取另一个。

我在这里使用 Vue,我对 Vue 还很陌生。我今天之前实际上从未使用过 Vue,但在阅读了 Vue.js 的介绍后,我想我至少可以处理这个问题,所以我决定用 Vue 来做这件事。据我所知,我不明白引号数组是如何未定义的。我的 JSON 文件中有 10 个引号,并且随机函数包含在内,因此它只会抓取 0-9,所以这不是索引越界的问题。

这是相关代码(一个 .html 文件和一个 .js 文件):

<h1>Random Quote Generator</h1>

<div id="quote-block">
  <span id="quote">{{ quotes[index].quote }}</span>
  <p><span id="author">-{{ quotes[index].author }}</span></p>
  <p><button id="new-quote">New Quote</button></p>
</div>

const app = new Vue({
    el: '#quote-block',
    data: {
      quotes: [],
      index: random(0,9)
    },
    created() {
      fetch('https://api.myjson.com/bins/1fb9jb')
        .then(response => response.json())
        .then(json => this.quotes = json.quotes)
        .catch(error => console.log(error));
      currentColor = colorize();
    },
    // getQuotes: ()=> {
    //   this.index = random(0,9);
    //   currentColor = colorize();
    // }
});

完整的代码笔(其余的只是一个随机颜色生成器和与 Vue 或此问题无关的鼠标悬停)在这里: https://codepen.io/jkuhl/pen/JMrxGV?editors=1010

注释掉的代码将是使用 @click 实现的点击事件代码

每次我尝试访问引号数组中对象的值时都会出现此错误。我可以访问引号数组本身,这些值显示没有问题。例如,如果我使用 {{ quotes}} 而不是 {{quotes[index].quote }},整个数组就可以正常显示。当我尝试访问数组中对象的值时,我的脚本就崩溃了。我做错了什么?

2个回答

您看到的错误是由于在获取引文之前尝试绑定 quotes[index].quote 的值而导致的,因此您需要使用 v-if 有条件地呈现该部分:

<div id="quote-block" v-if="quotes.length">
  <span id="quote">{{ quotes[index].quote }}</span>
  <p><span id="author">-{{ quotes[index].author }}</span></p>
  <p><button id="new-quote">New Quote</button></p>
</div>

仅当您的引文数组的长度大于零时,这才会呈现 div 。除此之外,您应该尝试按照其他答案所说的“vue 方式”来组织代码。

Amr Noman
2018-04-28

首先,vue 组件中的函数需要放在 methods 对象中,就像 data 一样。参考: https://v2.vuejs.org/v2/guide/events.html 。然后,您可以使用 v-on 为 HTML 中的元素设置监听器: <button id="new-quote" v-on:click="getQuotes">New Quote</button>

我只需按照上面链接中的正确模式,就可以让您的代码正常工作。

这是相关代码。

HTML:

<div id="quote-block">
  <span id="quote">{{ quotes[index].quote }}</span>
  <p><span id="author">-{{ quotes[index].author }}</span></p>
  <p><button id="new-quote" v-on:click="getQuotes">New Quote</button></p>
</div>

JS:

const app = new Vue({
    el: '#quote-block',
    data: {
      quotes: [],
      index: random(0,9)
    },
    created() {
      fetch('https://api.myjson.com/bins/1fb9jb')
        .then(response => response.json())
        .then(json => this.quotes = json.quotes)
        .catch(error => console.log(error));
      currentColor = colorize();
    },
    methods: {
      getQuotes: function (event) {
        this.index = random(0,9);
        currentColor = colorize();
      } 
    }
  }); //End Vue

您可以在 https://codepen.io/anon/pen/odBbLW?editors=1011 看到完整的笔(为了简洁,我删除了一些着色器代码)。加载时仍会出现错误,但按钮可以正常工作。

额外提示:将代码包装在匿名自执行函数中意味着您无法在控制台中引用该范围内定义的变量。因此,您无法在 codepen/devtools 控制台中执行 app.$data.quotes ,这只会使调试变得困难。当您只是测试这样的小东西时,无需使用匿名自执行函数。

Dhruv Murarka
2018-04-28