如何“通过引用"将 SwipeView 的 currentIndex 设置为 TabBar 的 currentIndex转到特定页面后?

2022-01-19 00:00:00 qt qtquick2 qml qtquickcontrols2 c++

我开始使用 QtQuick Controls 2.0.我有 C++ 的经验和少量的 Qt 经验,但我之前没有使用过 QML.

I'm getting started with QtQuick Controls 2.0. I have experience with C++ and a small amount of experience with Qt, but I have not worked with QML before.

我有一个 TabBar 和一个 SwipeView 彼此链接.我的意思是,当您在 TabBar 上选择一个页面时,SwipeView 会转到该页面.当您从 SwipeView 滑动到页面时,TabBar 会自行更新以反映这一点.

I have a TabBar and a SwipeView that are linked to each other. What I mean by this is that when you select a page on the TabBar, the SwipeView goes to that page. When you swipe to a page from the SwipeView, the TabBar updates itself to reflect that.

作为学习练习,我决定创建一个按钮,将用户引导至第二页.问题是我似乎无法找到一种方法来避免弄乱 TabBarSwipeView 之间的链接.

As a learning exercise, I decided to create a button that would send the user to the second page. The issue is that I can't seem to find a way to do so without messing up the link between the TabBar and the SwipeView.

以下代码是我想出的最好的.它正确地转到第二页,当我使用 TabBar 更改当前页面时,SwipeView 仍然会更新.但是,滑动 到新页面不再更新 TabBar.似乎将 tabBar.currentIndex 设置为 swipeView.currentIndex 仅在使用冒号进行初始化时具有通过引用设置的效果.这样做是通过值设置等号.如何移动到特定页面,同时仍保持 swipeView.currentIndex == tabBar.currentIndex 的不变量?

The following code is the best I've come up with. It correctly goes to the second page, and when I change the current page with the TabBar the SwipeView still updates. However, swiping to a new page no longer updates the TabBar. It appears that setting tabBar.currentIndex to swipeView.currentIndex only has the effect of setting by reference when done with the colon to initialize. Doing so with an equals sign sets by value. How can I move to a specific page while still maintaining the invariant that swipeView.currentIndex == tabBar.currentIndex?

// main.qml
import QtQuick 2.7
import QtQuick.Controls 2.0
import QtQuick.Layouts 1.0

ApplicationWindow {
    visible: true
    width: 640
    height: 480
    title: qsTr("Hello World")
    SwipeView {
        id: swipeView
        anchors.fill: parent
        currentIndex: tabBar.currentIndex

        Page {
            Button {
                text: qsTr("Continue to Page 2")
                onClicked: {
                    tabBar.currentIndex = 1;
                    // this next line merely sets tabBar.currentIndex to 1
                    tabBar.currentIndex = swipeView.currentIndex
                }
                anchors.centerIn: parent
                width: text.implicitWidth
                height: text.implicitHeight
            }
        }

        Page {
            Label {
                text: qsTr("Second page")
                anchors.centerIn: parent
            }
        }
    }

    footer: TabBar {
        id: tabBar
        currentIndex: swipeView.currentIndex
        TabButton {
            text: qsTr("First")
        }
        TabButton {
            text: qsTr( "Second")
        }
    }
}

C++ 代码只是 Qt Creator 为我提供的默认代码:

The C++ code is simply the default that Qt Creator provided for me:

// main.cpp
#include <QGuiApplication>
#include <QQmlApplicationEngine>

int main(int argc, char *argv[])
{
    QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
    QGuiApplication app(argc, argv);

    QQmlApplicationEngine engine;
    engine.load(QUrl(QLatin1String("qrc:/main.qml")));

    return app.exec();
}

推荐答案

为了在不破坏 currentIndex 绑定的情况下移动到下一页或上一页,可以调用 incrementCurrentIndex()decrementCurrentIndex(),分别.这些方法是在 Qt 5.8 的 Qt Quick Controls 2.1 中引入的.

In order to move to the next or the previous page without breaking the currentIndex bindings, you can call incrementCurrentIndex() or decrementCurrentIndex(), respectively. These methods were introduced in Qt Quick Controls 2.1 in Qt 5.8.

鉴于 currentIndex 设置器又名.QQuickContainer::setCurrentIndex() 是一个槽,你也可以从 QML 调用 setCurrentIndex() 来跳转到任意页面.这也不会破坏现有的绑定.

Given that the currentIndex setter aka. QQuickContainer::setCurrentIndex() is a slot, you can also call setCurrentIndex() from QML to jump to an arbitrary page. This will not break the existing bindings either.

Button {
    onClicked: tabBar.setCurrentIndex(1)
}

相关文章