TornadoFX-如何在删除项目时使用自定义单元格工厂修复ListView不能正确更新?

时间:2018-08-16 21:33:50

标签: tornadofx

我有一个ListView,它显示域模型中的自定义对象,如果我使用自定义单元工厂在列表的每一行中显示对象的属性,则删除项目时会出现奇怪的行为。如果该项目不是列表中的最后一项,则删除的项目仍然可见,并且最后一项消失。但是,该项目已按预期方式从后备列表中删除,并且尝试删除幻影对象没有任何进一步的作用。

显示似乎没有正确刷新,因为在任意调整窗口大小之后,列表最终会刷新到其期望值。我尝试手动在refresh()上调用ListView,但效果不明显。

删除我的自定义单元工厂可以解决此问题,并且我已经看到其他使用标准JavaFX(ListView using custom cell factory doesn't update after items deleted)也有类似问题的帖子,其中通过更改updateItem(Object item, boolean empty)的实现解决了该问题。 ,但我不知道如何在TornadoFX中做到这一点。

这是一个演示更新问题的示例(但不是幻象项,仅当删除按钮是自定义单元格的一部分时才会发生):

package example

import javafx.scene.control.ListView
import tornadofx.*

data class DomainClass(val name: String, val flag1: Boolean, val flag2: Boolean, val info: String)

class UpdateIssue : App(UpdateIssueView::class)

class UpdateIssueView : View() {

    val listSource = mutableListOf(
            DomainClass("object1", true, false, "more info"),
            DomainClass("object2", false, true, "even more info"),
            DomainClass("object3", false, false, "all the info")
    ).observable()
    var lst: ListView<DomainClass> by singleAssign()

    override val root = vbox {
        lst = listview(listSource) {
            cellFormat {
                graphic = cache {
                    hbox {
                        textfield(it.name)
                        combobox<Boolean> {
                            selectionModel.select(it.flag1)
                        }
                        combobox<Boolean> {
                            selectionModel.select(it.flag2)
                        }
                        textfield(it.info)
                    }
                }
            }
        }
        button("delete") {
            action {
                listSource.remove(lst.selectedItem)
            }
        }
    }
}

任何帮助都将不胜感激!

2 个答案:

答案 0 :(得分:0)

@Edvin Syse提出的删除缓存块的建议为我解决了这一问题(尽管请注意,他还说,更高性能的解决方案是实施ListCellFragment,在此我没有做过):< / p>

    ....
    lst = listview(listSource) {
        cellFormat {
            graphic = hbox {
                textfield(it.name)
                combobox<Boolean> {
                    selectionModel.select(it.flag1)
                }
                combobox<Boolean> {
                    selectionModel.select(it.flag2)
                }
                textfield(it.info)
            }
        }
    }

答案 1 :(得分:0)

我注意到ComboBoxes除了it.flag1和flag2之外,没有显示任何其他可选值。您需要将values属性设置为true / false或true / false / null。然后,您可以直接设置值项。

(v)->