More description to help understand the case.
I want to populate a tableview with user data stored inside a SQLite DB. In the main.c I connect to DB and register the CredentialsModel as a Type:
#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
#include <QStandardPaths>
#include <QSqlDatabase>
#include <QSqlError>
#include <QtQml>
#include "sqlcredentialsmodel.h"
static void connectToDatabase()
{
if (!database.isValid()) {
if (!database.isValid())
qFatal("Cannot add database: %s", qPrintable(database.lastError().text()));
}
const QDir writeDir
= QStandardPaths
::writableLocation(QStandardPaths
::AppDataLocation);
if (!writeDir.mkpath("."))
qFatal("Failed to create writable directory at %s", qPrintable(writeDir.absolutePath()));
// Ensure that we have a writable location on all devices.
const QString fileName
= writeDir.
absolutePath() + "/chat-database.sqlite3";
qDebug()<< "file: "<<fileName;
// When using the SQLite driver, open() will create the SQLite database if it doesn't exist.
database.setDatabaseName(fileName);
if (!database.open()) {
qFatal("Cannot open database: %s", qPrintable(database.lastError().text()));
}
}
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
connectToDatabase();
QQmlApplicationEngine engine;
qmlRegisterType<SqlCredentialsModel>("credentials", 1, 0, "SqlCredentialsModel");
const QUrl url
(QStringLiteral
("qrc:/main.qml"));
QObject::connect(&engine,
&QQmlApplicationEngine
::objectCreated,
if (!obj && url == objUrl)
}, Qt::QueuedConnection);
engine.load(url);
return app.exec();
}
#include <QGuiApplication>
#include <QQmlApplicationEngine>
#include <QQmlContext>
#include <QStandardPaths>
#include <QSqlDatabase>
#include <QSqlError>
#include <QtQml>
#include "sqlcredentialsmodel.h"
static void connectToDatabase()
{
QSqlDatabase database = QSqlDatabase::database();
if (!database.isValid()) {
database = QSqlDatabase::addDatabase("QSQLITE");
if (!database.isValid())
qFatal("Cannot add database: %s", qPrintable(database.lastError().text()));
}
const QDir writeDir = QStandardPaths::writableLocation(QStandardPaths::AppDataLocation);
if (!writeDir.mkpath("."))
qFatal("Failed to create writable directory at %s", qPrintable(writeDir.absolutePath()));
// Ensure that we have a writable location on all devices.
const QString fileName = writeDir.absolutePath() + "/chat-database.sqlite3";
qDebug()<< "file: "<<fileName;
// When using the SQLite driver, open() will create the SQLite database if it doesn't exist.
database.setDatabaseName(fileName);
if (!database.open()) {
qFatal("Cannot open database: %s", qPrintable(database.lastError().text()));
QFile::remove(fileName);
}
}
int main(int argc, char *argv[])
{
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling);
QGuiApplication app(argc, argv);
connectToDatabase();
QQmlApplicationEngine engine;
qmlRegisterType<SqlCredentialsModel>("credentials", 1, 0, "SqlCredentialsModel");
const QUrl url(QStringLiteral("qrc:/main.qml"));
QObject::connect(&engine, &QQmlApplicationEngine::objectCreated,
&app, [url](QObject *obj, const QUrl &objUrl) {
if (!obj && url == objUrl)
QCoreApplication::exit(-1);
}, Qt::QueuedConnection);
engine.load(url);
return app.exec();
}
To copy to clipboard, switch view to plain text mode
The model is implemented as following:
sqlcredentialsmodel.h
#ifndef SQLCREDENTIALSMODEL_H
#define SQLCREDENTIALSMODEL_H
#include <QSqlQueryModel>
{
public:
SqlCredentialsModel
(QObject *parent
= 0);
};
#endif // SQLCREDENTIALSMODEL_H
#ifndef SQLCREDENTIALSMODEL_H
#define SQLCREDENTIALSMODEL_H
#include <QSqlQueryModel>
class SqlCredentialsModel : public QSqlQueryModel
{
public:
SqlCredentialsModel(QObject *parent = 0);
};
#endif // SQLCREDENTIALSMODEL_H
To copy to clipboard, switch view to plain text mode
sqlcredentialsmodel.cpp
#include "sqlcredentialsmodel.h"
#include <QDebug>
#include <QSqlError>
#include <QSqlQuery>
static void createTable()
{
qDebug()<<"table "<<table;
}
if (QSqlDatabase::database().
tables().
contains(QStringLiteral
("Credentials"))) { // The table already exists; we don't need to do anything.
return;
}
if (!query.exec(
"CREATE TABLE IF NOT EXISTS 'Credentials' ("
" 'username', 'password' TEXT NOT NULL,"
" PRIMARY KEY(username)"
")")) {
qFatal("Failed to query database: %s", qPrintable(query.lastError().text()));
}
query.exec("INSERT INTO Credentials VALUES('bert', 'b&c' )");
query.exec("INSERT INTO Credentials VALUES('emmy', 'e&c' )");
query.exec("INSERT INTO Credentials VALUES('hans', 'h&c' )");
}
SqlCredentialsModel
::SqlCredentialsModel(QObject *parent
) :{
createTable();
if (!query.exec("SELECT * FROM Credentials"))
qFatal("Contacts SELECT query failed: %s", qPrintable(query.lastError().text()));
setQuery(query);
if (lastError().isValid())
qFatal("Cannot set query on SqlCredentialsModel: %s", qPrintable(lastError().text()));
}
#include "sqlcredentialsmodel.h"
#include <QDebug>
#include <QSqlError>
#include <QSqlQuery>
static void createTable()
{
for (auto table: QSqlDatabase::database().tables()){
qDebug()<<"table "<<table;
}
if (QSqlDatabase::database().tables().contains(QStringLiteral("Credentials"))) {
// The table already exists; we don't need to do anything.
return;
}
QSqlQuery query;
if (!query.exec(
"CREATE TABLE IF NOT EXISTS 'Credentials' ("
" 'username', 'password' TEXT NOT NULL,"
" PRIMARY KEY(username)"
")")) {
qFatal("Failed to query database: %s", qPrintable(query.lastError().text()));
}
query.exec("INSERT INTO Credentials VALUES('bert', 'b&c' )");
query.exec("INSERT INTO Credentials VALUES('emmy', 'e&c' )");
query.exec("INSERT INTO Credentials VALUES('hans', 'h&c' )");
}
SqlCredentialsModel::SqlCredentialsModel(QObject *parent) :
QSqlQueryModel(parent)
{
createTable();
QSqlQuery query;
if (!query.exec("SELECT * FROM Credentials"))
qFatal("Contacts SELECT query failed: %s", qPrintable(query.lastError().text()));
setQuery(query);
if (lastError().isValid())
qFatal("Cannot set query on SqlCredentialsModel: %s", qPrintable(lastError().text()));
}
To copy to clipboard, switch view to plain text mode
QML is implemented as following:
main.qml
import QtQuick 2.12
import QtQuick.Controls 2.5
ApplicationWindow {
visible: true
width: 100
height: 120
title: qsTr("Credentials")
SwipeView {
id: swipeView
anchors.fill: parent
CredentialsView{
id: credentialsView
}
}
}
import QtQuick 2.12
import QtQuick.Controls 2.5
ApplicationWindow {
visible: true
width: 100
height: 120
title: qsTr("Credentials")
SwipeView {
id: swipeView
anchors.fill: parent
CredentialsView{
id: credentialsView
}
}
}
To copy to clipboard, switch view to plain text mode
CredentialsView.ui.qml
import QtQuick 2.9
import QtQuick.Controls 2.2
import QtQuick.Layouts 1.3
import credentials 1.0
Page {
id: page_Credentials
header: Label {
text: qsTr("Credentials")
font.pixelSize: Qt.application.font.pixelSize
padding: 10
}
CredentialsTableView{
anchors.fill: parent
}
}
import QtQuick 2.9
import QtQuick.Controls 2.2
import QtQuick.Layouts 1.3
import credentials 1.0
Page {
id: page_Credentials
header: Label {
text: qsTr("Credentials")
font.pixelSize: Qt.application.font.pixelSize
padding: 10
}
CredentialsTableView{
anchors.fill: parent
}
}
To copy to clipboard, switch view to plain text mode
CredentialsTableView.ui.qml
import QtQuick 2.12
import QtQuick.Controls 2.12
import credentials 1.0
TableView {
id: credentialsTableView
property alias credentialsTableView: credentialsTableView
anchors.fill: parent
columnSpacing: 2
rowSpacing: 2
clip: true
model: SqlCredentialsModel{}
delegate: Rectangle {
color: "lightblue"
implicitWidth: lbl_tableCell.width
implicitHeight: lbl_tableCell.height
Label {
id: lbl_tableCell
text: display
}
}
}
import QtQuick 2.12
import QtQuick.Controls 2.12
import credentials 1.0
TableView {
id: credentialsTableView
property alias credentialsTableView: credentialsTableView
anchors.fill: parent
columnSpacing: 2
rowSpacing: 2
clip: true
model: SqlCredentialsModel{}
delegate: Rectangle {
color: "lightblue"
implicitWidth: lbl_tableCell.width
implicitHeight: lbl_tableCell.height
Label {
id: lbl_tableCell
text: display
}
}
}
To copy to clipboard, switch view to plain text mode
Thanks in advance
Bookmarks