gpt4 book ai didi

c++ - 用 C++ 创建的模型不能从 QML 修改

转载 作者:塔克拉玛干 更新时间:2023-11-03 07:39:11 25 4
gpt4 key购买 nike

已解决:我做了所有像 eyllanesc answer 和我的 FirstPage.qml 里面的委托(delegate)我访问模型数据的地方我将 modelData 放在名称之前。以前在 FirstPage.qml 委托(delegate)中我使用了:名称、完成和未完成,现在我使用 modelData.name、modelData.completed 和modelData.未完成。现在一切都很好。

我是 QT/QML 的新手,我尝试过但找不到问题的答案。

我在 QML 中使用模型(用 C++ 创建)。当应用程序启动时,一切都很好,但是当我尝试向模型添加新元素时,它不会显示在 QML 中。模型从一开始就一样。

我有类 modcontroller 并在其中创建列表。

modcontroller.h

#ifndef MODCONTROLLER_H
#define MODCONTROLLER_H

#include <QObject>
#include <list.h>

class modcontroller : public QObject
{
Q_OBJECT

public:
explicit modcontroller(QObject *parent = nullptr);

QList<QObject*> getList();

Q_INVOKABLE void addList(QString nam);

signals:
void listChanged();

public slots:

private:
QList<QObject*> m_dataList;
};

#endif // MODCONTROLLER_H

modcontroller.cpp

#include "modcontroller.h"
#include <QDebug>

modcontroller::modcontroller(QObject *parent) : QObject(parent)
{
m_dataList.append(new List("Test"));
}

QList<QObject *> modcontroller::getList()
{
return m_dataList;
}

void modcontroller::addList(QString nam)
{
m_dataList.append(new List(nam));
qDebug() << "Function addList called";

qDebug() << m_dataList;
}

主要.cpp

#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>

#include "list.h"
#include "modcontroller.h"

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

QGuiApplication app(argc, argv);


QQmlApplicationEngine engine;


modcontroller controller;
engine.rootContext()->setContextProperty("myModel", QVariant::fromValue(controller.getList()));
engine.rootContext()->setContextProperty("controller",&controller);

engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;



return app.exec();
}

在 QML 文件中,我有带有 model: myModel 的 ListView 和带有

的按钮
onClicked: {
controller.addList(textInput.text)
myStackView.push(firstPage)
}

当我点击创建时,我只看到在开始时创建的第一个项目“测试”,但在控制台中我得到这个:

Function addList called
(List(0x2b7e60bc2c0), List(0x2b82d5891b0))

提前致谢。

主.qml

    ApplicationWindow {
visible: true
width: 580
height: 360
title: qsTr("Hello World")

StackView{
id: myStackView
initialItem: firstPage
anchors.fill: parent
}

Component{
id: firstPage
FirstPage{}
}

Component{
id: createNewListPage
CreateNewListPage{}
}

}

第一页.qml

Item {    
ListView{
id: lists
width: 150
height: childrenRect.height
x: 15
y: 70

model: myModel

delegate: Row{
width: 150
height: 25
spacing: 5

Rectangle{
width: {
if(uncompleted < 3){return 3;}
else if(uncompleted < 6){return 6;}
else {return 10;}
}
height: {
if(uncompleted < 3){return 3;}
else if(uncompleted < 6){return 6;}
else {return 10;}
}
radius: 10
color: "#494949"
anchors.verticalCenter: parent.verticalCenter
}
Button {
id:button1
height: 23

contentItem: Text {
id: textTask
text: name
font.underline: true
color: "blue"
font.bold: true
font.pointSize: 10
height: 20
anchors.verticalCenter: parent.verticalCenter
anchors.left: parent.left
}

background: Rectangle {
id: rectangle
color: "transparent"
}
states:[
State {
name: "Hovering"
PropertyChanges {
target: textTask
color: "white"
font.bold: true
font.underline: false
}
PropertyChanges {
target: rectangle
color: "blue"
}
}]

MouseArea{
hoverEnabled: true
anchors.fill: button1
onEntered: { button1.state='Hovering'}
onExited: { button1.state=''}
}
}
Text{
font.pointSize: 8
text: {
if(uncompleted == 0)return "";
return "- " + uncompleted + " left";
}
color: "#494949"
anchors.verticalCenter: parent.verticalCenter
}
}
}
}

创建新列表页面.qml

Item {
Rectangle{
width: 580
height: 360

Rectangle{
width: 350
height: 30
y: 100
x: 30
border.color: "#7b9cd3"
border.width: 1

TextInput {
id: textInput
anchors.topMargin: 3
cursorVisible: true
anchors.fill: parent
font.bold: true
font.pointSize: 14
}

}



Button{
height: 20
text: "Create this list"
onClicked: {
controller.addList(textInput.text)
myStackView.push(firstPage)
}

background: Rectangle{
id: rect1
anchors.fill: parent
radius: 20
border.color: "#88b6cf"
gradient: Gradient {
GradientStop { position: 0.0; color: "#fcfefe" }
GradientStop { position: 1.0; color: "#d5e8f3" }
}
}

}

}
}

最佳答案

列表是一个虚拟模型,因为它本身不会通知 View 是否有任何更改(例如元素数量),因此针对您的情况的解决方案是使其成为 mod_controller 的 Q_PROPERTY,然后当您添加项目时,标志 listChanged 将通知 View 某些内容已更改,因此需要重新绘制。不必从 Controller 中单独导出列表,因为 Q_PROPERTY 可以在 QML 中访问,所以解决方案是:

modcontroller.h

#ifndef MODCONTROLLER_H
#define MODCONTROLLER_H

#include <QObject>

class modcontroller : public QObject
{
Q_OBJECT
Q_PROPERTY(QList<QObject *> lists READ getList NOTIFY listsChanged) // <---
public:
explicit modcontroller(QObject *parent = nullptr);
QList<QObject *> getList() const;
Q_INVOKABLE void addList(const QString &nam);
Q_SIGNAL void listsChanged();
private:
QList<QObject*> m_dataList;
};

#endif // MODCONTROLLER_H

modcontroller.cpp

#include "modcontroller.h"
#include "list.h"

#include <QDebug>

modcontroller::modcontroller(QObject *parent) : QObject(parent)
{
m_dataList.append(new List("Test"));
}

QList<QObject *> modcontroller::getList() const
{
return m_dataList;
}

void modcontroller::addList(const QString & nam)
{
m_dataList.append(new List(nam));
qDebug() << "Function addList called";
qDebug() << m_dataList;
Q_EMIT listsChanged(); // <---
}

main.cpp

#include "modcontroller.h"

#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>

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

QGuiApplication app(argc, argv);

QQmlApplicationEngine engine;
modcontroller controller;
engine.rootContext()->setContextProperty("controller",&controller);
engine.load(QUrl(QStringLiteral("qrc:/main.qml")));
if (engine.rootObjects().isEmpty())
return -1;

return app.exec();
}

在 QML 的情况下,绑定(bind)是通过 Controller 的 Q_PROPERTY 列表完成的:

ListView{
// ...
model: controller.lists // <---
// ...

关于c++ - 用 C++ 创建的模型不能从 QML 修改,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55271179/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com