在 Vue 中动态地将元素添加到可排序的 LI

Posted

技术标签:

【中文标题】在 Vue 中动态地将元素添加到可排序的 LI【英文标题】:Dynamically add an element to a sortable LI in Vue 【发布时间】:2021-06-12 10:41:12 【问题描述】:

我有一个可排序的列表,我想在其中完成两件事:

    使用 +/- 符号向此列表添加/删除 LI 元素。 可排序列表有一个带有数据的文本区域 - 当我添加删除 LI 项时,我很难将其存储在数据属性中。例如,当我重新加载页面时,我希望我的新 LI 项与新数据项一起可见。

非常感谢任何方向。

HTML

<div id="app" class="container ">
  <ul ref="list" class="list" v-sortable="animation: 250, onUpdate: work">
    <li v-for="item in orderedItems" :_id="item.id" :order="item.order">
      |||
      <textarea row="5" v-model="item.text"></textarea>
    </li>
  </ul>
  <pre> $data 
</div>

JS

Vue.directive('sortable', 
  // When the bound element is inserted into the DOM...
  inserted: function (el, binding) 
    Sortable.create(el, binding.value || ) 
  
)

new Vue(
  el: '#app',
  
  data: 
    items: [
      id: 1, text: 'AAA', order: 2,
      id: 2, text: 'BBB', order: 5,
      id: 3, text: 'CCC', order: 1,
      id: 4, text: 'DDD', order: 4,
      id: 5, text: 'EEE', order: 3,
    ]
  ,
  
  created: function()
  
    this.orderedItems = _.orderBy(this.items, 'order')
  ,
  
  methods: 
    work: function(event)
    
      var vm = this
      var els = vm.$refs.list.children
      
      for (var i=0; i < els.length; i++) 
      
        var id = els[i].getAttribute('_id')        
        vm.items.map(function(item)
                     
          if (item.id == id)
          
            item.order = i+1
          
        )
        //console.log(vm.items[i].order)  
      
    
  
)

这是可排序的列表:https://codepen.io/syedhuss/pen/bGBZoEe

【问题讨论】:

【参考方案1】:

您的代码对我来说看起来不错,这是一个与持久性相关的概念问题。

Vue 本身不会存储您在客户端中调整的任何内容,因此刷新页面并恢复默认设置是完全正常的。您应该将添加的新项目存储在数据库中,或者使用网络存储、cookie 等机制将数据存储在客户端。

我认为您需要一个数据库,用于保存用户添加的所有项目

【讨论】:

感谢您的回复。从本质上讲,我正在努力添加一个新项目并让该项目呈现:codepen.io/syedhuss/pen/yLVwqBq 单击“添加”按钮时,我无法获得 v-for 来呈现新组件。同样,当我单击删除时,我无法重新渲染以删除组件。【参考方案2】:

有几个问题:

    orderedItems 需要在 data() 中声明才能使其具有反应性。

    export default 
      data() 
        orderedItems: []
      
    
    

    work() 更新 DOM 而不是绑定模型(在这种情况下为orderedItems)。但是orderedItems 需要对 Vue 进行响应才能呈现更改。

    看起来work() 旨在增加每个项目的order 属性,但我怀疑您实际上想根据移动的项目更改项目顺序。 event 参数包含oldIndexnewIndex,它们指的是orderedItems 中移动项目的数组索引。您可以将该信息与Array.prototype.splice 一起使用以在orderedItems 中执行移动:

    const movedItem = this.orderedItems.splice(oldIndex, 1) // remove
    this.orderedItems.splice(newIndex, 0, movedItem) // insert
    

    鉴于v-for 中的项目正在被重新排序或删除,为每个项目指定一个唯一的key 非常重要,这样Vue 才能正确呈现这些项目。在这种情况下,item.id 在项目之间具有足够的唯一性,因此应该绑定到 key

    <li v-for="item in orderedItems" :key="item.id"></li>
    

updated codepen

【讨论】:

以上是关于在 Vue 中动态地将元素添加到可排序的 LI的主要内容,如果未能解决你的问题,请参考以下文章

使用 Angular 和 ANYWHERE 将元素动态添加到可编辑的 div

在 Groovy 中动态地将元素添加到 ArrayList

可拖动项目添加到可排序列表

li元素后动态添加ul元素

jquery 怎么获得动态添加后的子元素个数

如何在angularjs中动态地将样式属性添加到具有ng-class的元素