Animate `positionViewAtIndex`

2019-05-16 08:40发布

I have ListViewshowing a Model, in which, at random positions I might add a entry.

Now I want to see my new entry, and try to move the ListView to it, with the

positionViewAtIndex(newIndex, ListView.Visible)

But this change somtimes feeles very hard. Is there a posibility to smooth it with som animation?

A somewhat lengthy example to play with:

import QtQuick 2.7
import QtQuick.Controls 2.0

ApplicationWindow
{
    width: 1024
    height: 800
    visible: true
    property int lastAddedIndex: -1
    onLastAddedIndexChanged: lv.positionViewAtIndex(lastAddedIndex, ListView.Contain)

    Button {
        property int num: 10
        text: 'Add element: ' + num
        onClicked: {
            lastAddedIndex = Math.floor(Math.random(num) * lm.count)
            lm.insert(lastAddedIndex, { num : this.num })
            num++
        }
    }

    ListModel {
        id: lm
        ListElement { num: 0 }
        ListElement { num: 1 }
        ListElement { num: 2 }
        ListElement { num: 3 }
        ListElement { num: 4 }
        ListElement { num: 5 }
        ListElement { num: 6 }
        ListElement { num: 7 }
        ListElement { num: 8 }
        ListElement { num: 9 }
    }

    ListView {
        id: lv
        model: lm
        y: 150
        width: 800
        height: 100
        spacing: 2
        clip: true
        orientation: ListView.Horizontal
        delegate: Rectangle {
            width: 150
            height: 100
            border.color: 'black'
            color: lastAddedIndex === index ? 'purple' : 'white'
            Text {
                anchors.centerIn: parent
                text: index + ': ' + num
            }
        }
        add: Transition { NumberAnimation { property: 'width'; from: 0; to: 150; duration: 600 } }
    }
}

1条回答
ゆ 、 Hurt°
2楼-- · 2019-05-16 08:45

You can do it by adding addition animation element for contentX (as you have your element horizontally placed), and running it in order to animate changing view position at a given index, it will give you smooth animation:

source

import QtQuick 2.7
import QtQuick.Controls 2.0

ApplicationWindow
{
    width: 1024
    height: 800
    visible: true
    property int lastAddedIndex: -1
    onLastAddedIndexChanged: gotoIndex(lastAddedIndex)

    function gotoIndex(idx) {
        anim.running = false;

        var pos = lv.contentX;
        var destPos;

        lv.positionViewAtIndex(idx, ListView.Contain);
        destPos = lv.contentX;

        anim.from = pos;
        anim.to = destPos;
        anim.running = true;
    }

    NumberAnimation { id: anim; target: lv; property: "contentX"; duration: 500 }

    Button {
        property int num: 10
        text: 'Add element: ' + num
        onClicked: {
            lastAddedIndex = Math.floor(Math.random(num) * lm.count)
            lm.insert(lastAddedIndex, { num : this.num })
            num++
        }
    }

    ListModel {
        id: lm
        ListElement { num: 0 }
        ListElement { num: 1 }
        ListElement { num: 2 }
        ListElement { num: 3 }
        ListElement { num: 4 }
        ListElement { num: 5 }
        ListElement { num: 6 }
        ListElement { num: 7 }
        ListElement { num: 8 }
        ListElement { num: 9 }
    }

    ListView {
        id: lv
        model: lm
        y: 150
        width: 800
        height: 100
        spacing: 2
        clip: true
        orientation: ListView.Horizontal
        delegate: Rectangle {
            width: 150
            height: 100
            border.color: 'black'
            color: lastAddedIndex === index ? 'purple' : 'white'
            Text {
                anchors.centerIn: parent
                text: index + ': ' + num
            }
        }

        add: Transition { NumberAnimation { property: 'width'; from: 0; to: 150; duration: 600 } }
    }
}
查看更多
登录 后发表回答