Vue.js v-for 在循环组件中增加一些变量

Posted

技术标签:

【中文标题】Vue.js v-for 在循环组件中增加一些变量【英文标题】:Vue.js v-for increment some variable in looped component 【发布时间】:2017-07-22 14:53:59 【问题描述】:

我正在尝试显示活动议程上的项目列表。

事件有一个start_date结束议程上的每个项目在分钟内都有一个duration,例如:

event:
  start_date: '2017-03-01 14:00:00',
  agendas:[
      id:1,duration:10,
      id:2,duration:15,
      id:3,duration:25,
      id:4,duration:10
  ]

现在,在我的event 组件中,我用v-for 加载agendas

<agenda v-for="(agenda,index) in event.agendas" 
        :key="agenda.id"
        :index="index" 
        :agenda="agenda">

agenda组件中,我想增加每个项目开始的时间:

<div class="agenda">
  //adding minutes to start_date with momentJs library
   moment(event.start_date).add(agenda.duration,'m')  //this should increment, not add to the fixed event start date
</div>

目前它只添加到固定事件start_date...我想显示时间14:00 用于事件114:10 用于事件214:25 用于事件314:50 用于事件4

如何在 Vue.js 2.0 中增加 v-for 指令中的值?

【问题讨论】:

【参考方案1】:

您似乎已经找到了适合您的答案,但我会在此处发布,以防有​​人正在寻找替代解决方案。接受的答案可能对议程的初始渲染有好处,但如果议程数组发生突变或任何事情导致列表重新渲染,则将开始中断,因为开始时间计算基于每次迭代都会递增的存储值。

下面的代码添加了一个计算属性(基于event.agendas),它返回一个新的议程对象数组,每个对象都添加了一个start 属性。

Vue.component('agenda', 
  template: '<div>Agenda  agenda.id  —  agenda.duration  min —  agenda.start </div>',
  props: 
    agenda: Object
  
);

new Vue(
  el: "#root",
  data: ..., 
  computed: 
    agendas_with_start() 
      const result = [];

      let start = moment(this.event.start_date);
      for(let agenda of this.event.agendas) 
        result.push(
          id: agenda.id,
          duration: agenda.duration,
          start: start.format('HH:mm')
        );
        start = start.add(agenda.duration, 'm');
      
      return result;
    
  
);

然后,在模板中,agendas_with_start 计算属性用于 v-for:

<div id="root">
  <h3>Event Start:  event.start_date </h3>
  <agenda v-for="agenda in agendas_with_start" 
          :key="agenda.id"
          :agenda="agenda"></agenda>
</div>

这里是a working codepen。这种方法的好处是,如果底层的议程数组发生了变异或重新排序,或者事件开始时间发生了变化,或者任何事情导致 Vue 重新渲染 DOM,这个计算属性将被重新评估,并且开始时间将被重新计算。 - 计算正确。

【讨论】:

你是对的。变异时,时间会随着另一个答案而继续增加。谢谢【参考方案2】:

Vue.js 实际上会让你将 prop 值绑定到父作用域上的方法,因此最简单的方法是执行以下操作:

<agenda class="agenda" v-for="(agenda,index) in event.agendas"
    :key="agenda.id"
    :index="index"
    :agenda="agenda"
    :start-time="get_start_time(agenda.duration)">
</agenda>

然后get_start_time()是父范围内的方法:

new Vue(
  el: '#app',
  data: 
    time_of_day: '',
    event:
      // ...
    ,
  ,

  methods: 
    get_start_time(duration) 
      if (this.next_event_start === '') 
        this.next_event_start = moment(this.event.start_date);
       
      this.event_start = this.next_event_start.format('h:mm a');
      this.next_event_start.add(duration, 'minutes');
      return this.event_start;
    ,
  ,
);

我制作了一个quick CodePen 作为基本示例来展示它的实际效果,但您需要更新实际代码以弥补多天的损失。

【讨论】:

不错的答案......但是,当我查看 codepen 时,它显示了从 3:10 开始的议程,即使事件从 2 开始。似乎 get_start_time() 方法被调用的次数超过每个议程一次。另外,您知道如果议程数组发生突变,这是否会起作用?似乎如果您修改议程(添加、删除、反向),开始时间将从已经增加的 time_of_day 值开始重新计算。 @Peter 我认为这可能是由于在每次迭代中将 Moment 库重新应用于自身。我已经修复了 codepen,现在可以正常工作了。 至于您关于重新计算的问题,根据我刚刚所做的修改,您只需将next_event_start 设置回一个空字符串(next_event_start = '' ) 当您修改议程值时。它应该在 Vue 组件更新周期的下一个 tick 重新正确计算。

以上是关于Vue.js v-for 在循环组件中增加一些变量的主要内容,如果未能解决你的问题,请参考以下文章

Vue.js v-for 循环绑定数组中的项目对象并在更改时更新

Vue.js v-for 循环遍历数组不起作用(非零长度的零元素)

Vue.JS v-for循环后,想要实现每个单独项实现单独的show的true\false

如何在 Vue.js 中获取 v-for 索引?

vue.js v-for怎么循环传给它的整数?

Vue js数组反向导致v-for循环出错