代码之家  ›  专栏  ›  技术社区  ›  Mateusz Drost

ListView.onRemove动画vs children Rect.height

  •  0
  • Mateusz Drost  · 技术社区  · 9 年前

    当我使用ListView.onRemove动画从其模型中删除元素时,我注意到ListView children Rect.height中的奇怪行为。当我删除除最后一个元素之外的所有元素时,childrenRect.height属性错误,但contentHeight属性正常。删除ListView.onRemove动画会导致问题消失。为什么孩子们的体重不对?

    使用 this code 您将看到,在删除除最后一个元素之外的所有元素后,您无法在某个区域中单击。

    import QtQuick 2.0
    import QtQuick.Controls 1.0
    MouseArea
    {
        id: container
        height: 400; width: 600
        Rectangle { id: point; visible: false; width: 6; height: 6; radius: 3; color: "black" }
        onPressed: { point.visible = true; point.x = mouse.x - 3; point.y = mouse.y - 3; }
        ListModel {
            id: listModel
            ListElement { lorem: "Lorem ipsum dolor sit amet, consectetur adipisicing elit. Proin nibh augue, suscipit a, scelerisque sed, lacinia in, mi. Cras vel lorem." }
            ListElement { lorem: "Etiam pellentesque aliquet tellus. Phasellus pharetra nulla ac diam." }
            ListElement { lorem: "Quisque semper justo at risus. Donec venenatis, turpis vel hendrerit interdum, dui ligula ultricies purus, sed posuere libero dui id orci." }
            ListElement { lorem: "Nam congue, pede vitae dapibus aliquet, elit magna vulputate arcu, vel tempus metus leo non est." }
        }
        ListView {
            id: messageListView
            model: listModel
            anchors.top: container.top; anchors.left: container.left; anchors.right: container.right
            height: childrenRect.height
            onCountChanged: console.log("count: " + count)
            onHeightChanged: console.log("height: " + height) // sometimes wrong
            onContentHeightChanged: console.log("contentHeight: " + contentHeight) // rather ok
            delegate: Item {
                id: messageItem
                anchors.left: parent.left; anchors.right: parent.right
                height: Math.max(50, messageText.height + 12)
                Rectangle { anchors.fill: parent; anchors.margins: 1; opacity: 0.75; color: "green"; radius: 5 }
                Text {
                    id: messageText
                    anchors.verticalCenter: parent.verticalCenter; anchors.left: parent.left; anchors.right: removeButton.left; anchors.margins: 10
                    text: lorem
                    color: "white"; horizontalAlignment: Text.AlignHCenter; wrapMode: Text.WordWrap
                    font.pixelSize: 16; font.weight: Font.Bold
                    style: Text.Outline; styleColor: "black"
                    maximumLineCount: 6; elide: Text.ElideRight
                }
                Button {
                    id: removeButton
                    enabled: (index !== -1) && (messageItem.opacity === 1.0)
                    anchors.right: parent.right; anchors.margins: 5
                    anchors.verticalCenter: parent.verticalCenter; implicitHeight: 40; implicitWidth: 40
                    onClicked: {
                        console.log("remove: " + index);
                        listModel.remove(index);
                    }
                }
                ListView.onRemove: SequentialAnimation {
                    PropertyAction { target: messageItem; property: "ListView.delayRemove"; value: true }
                    /// PROBLEM BEGIN
                    NumberAnimation { target: messageItem; properties: "opacity"; from: 1.0; to: 0.0; duration: 500 }
                    /// PROBLEM END
                    PropertyAction { target: messageItem; property: "ListView.delayRemove"; value: false }
                }
            }
        }
    }
    
    1 回复  |  直到 9 年前
        1
  •  2
  •   mcchu    9 年前

    因为 ListView.childrenRect 可以由其自身动态地改变。例如,尝试在示例代码启动时拖动视图。当所有四名代表从视图顶部消失时, childrenRect.height 增加(即使您对 NumberAnimation ). 这意味着 ListView 使用它的 childrenRect 对某些内部属性,如拖动动画,因此此属性对ListView用户不可靠。

    使用 contentHeight 而不是 儿童身高 因此您可以始终获得正确的值。或使用 contentItem.childrenRect.height 根据 Flickable .