Javascript 从v-bind:style中调用函数不会';t触发对视图的更新

Javascript 从v-bind:style中调用函数不会';t触发对视图的更新,javascript,vue.js,nativescript,Javascript,Vue.js,Nativescript,我有一个图像列表(像一个画廊)。图片上的长按(我使用的是Nativescript vue)将更改图像的样式,并使其显示为“选中”。这是图像: <ListView layout="grid" ref="backedupImages" for="image in sortedBackedupImages"> <v-template> <ImageComponent v-bind:style="{backgroundColo

我有一个图像列表(像一个画廊)。图片上的长按(我使用的是Nativescript vue)将更改图像的样式,并使其显示为“选中”。这是图像:

<ListView layout="grid" ref="backedupImages" for="image in sortedBackedupImages">
      <v-template>
        <ImageComponent
          v-bind:style="{backgroundColor:isSelected(image.identifier) ? 'cyan' : 'white'}"
          :onLongPress="()=>{onLongPress(image.identifier)}"
          :onShortPress="()=>{onShortPress(image.identifier)}"
          :image="image"
        ></ImageComponent>
      </v-template>
    </ListView>
这是onLongPress方法,用于切换图像选择状态:

onLongPress(identifier) {
            if(this.selectedImages.includes(identifier)){
                const index = this.selectedImages.indexOf(identifier);
                this.$delete(this.selectedImages,index);
            }else{
                const index = this.selectedImages.length;
                this.$set(this.selectedImages,index,identifier);
            }
        },

数组操作似乎有效,但我看不到任何反应。有什么问题吗?在Vue中是否有更好的方法?我认为我不能使用computed属性,因为我需要将一个参数传递给“计算”。

您遇到的问题是
ListView
上的
v-for
循环将无法按预期运行。此问题在以下章节中描述:

不会像使用
v-for
循环时所期望的那样循环列表项。相反,
只创建必要的视图,以显示屏幕上当前可见的项目,并在滚动时重用屏幕外的视图。这一概念称为视图回收,通常用于移动应用程序以提高性能

这一点很重要,因为您不能依赖
v-template
中附加的事件侦听器。相反,您需要使用
itemTap
事件,该事件包含点击项目的索引和列表中的实际项目

MTAP(事件){
console.log(event.index)
console.log(event.item)
}


我确实检查了它,因此使用了$set和$delete方法。它现在不应该工作吗?编辑:我尝试将这一行添加到onLongPress函数中-没有更改。啊,我的错误,我看到
$delete
应该是反应式的。你检查过控制台有没有错误?我用tns调试android来愚弄正在发生的事情,它看起来很好。此外,我还使用vue开发工具查看状态的变化,看起来也不错。我要提到的是,如果我向下滚动并再次向上滚动(ListView组件是Nativescript的虚拟化组件),一切都会正常工作。但是没有滚动,就没有反应。您必须提到这是Nativescript,而不是纯Vue.js。这大大改变了情况。请阅读下面这篇文章。它准确地描述了您的问题,这是使用
v-for
ListView
中对
v-template
的限制。这是一个性能优化功能。好吧,这似乎给我想要的功能设置了一个障碍,因为itemTap事件似乎没有区分短点击和长点击……你知道吗?老实说,我怀疑这是否真的是问题所在,因为我“以正常方式”检测事件没有问题。@sheff2k1在同一文档中提到了
refresh()
方法。这可以很好地解决问题:)如果这样做有效,请让我知道,我会相应地更新我的答案以反映这一点。可怕的文档,我甚至不知道如何使用这种刷新方法。我该怎么称呼它呢DOk,一个重要的更新:通过完全删除整个“selectedImages”数组,并将一个“selected”属性附加到image对象,我成功地实现了这一点。问题是,我正在修改一个对象上的属性,该属性作为道具从父对象接收。它现在可以工作了,但这是bug的来源吗?在这种情况下,永远都有“一个真理的来源”。Vue呢?你有时会在孩子体内修改道具吗?你不应该修改道具。相反,
查看
道具的任何更改,并在更改时创建一个副本以存储在本地数据中。这样可以确保父级更改仍然可以覆盖子组件的数据,但子组件的更改仅限于其自己的范围。
onLongPress(identifier) {
            if(this.selectedImages.includes(identifier)){
                const index = this.selectedImages.indexOf(identifier);
                this.$delete(this.selectedImages,index);
            }else{
                const index = this.selectedImages.length;
                this.$set(this.selectedImages,index,identifier);
            }
        },