пока делать было не чего запилил по быстрому нечто подобное.
В программе две таблицы. Таблица рабочих, в ней id и имя работника. Таблица рабочих часов работника, в ней дата и количество отработаных часов.
Все это стандартные компоненты QTableView и к ним модель QSqlQueryModel безо всяких допиливаний, используются как есть.
Код комментировал как только можно, так что думаю все будет понятно.
заголовочный файл
Код:
#ifndef WIDGET_H
#define WIDGET_H
#include <QSqlDatabase>
#include <QWidget>
#include <QTableView>
#include <QPushButton>
#include <QDoubleSpinBox>
#include <QDateEdit>
#include <QLineEdit>
#include <QSqlQueryModel>
class Widget : public QWidget
{
Q_OBJECT
public:
Widget(QWidget *parent = 0);
~Widget();
private:
// Подключение к БД, создание таблиц
bool connectDatabase();
private slots:
// Слот добавления нового работника
void onAddWorker();
// Слот добавления рабочих часов
void onAddHours();
// Слот обработки кликанья мышью по таблице работников
void onWorkerTableClicked(QModelIndex index);
private:
QSqlDatabase database;
QTableView *table_workers; // Таблица работников
QTableView *table_hours; // Таблица часов
QLineEdit *le_name_worker; // Однострочное поле ввода имени работника
QPushButton *btn_add_worker; // Кнопка добавления работника
QPushButton *btn_add_hour; // Кнопка добавления часов
QDateEdit *date_edit; // Дата работы
QDoubleSpinBox *sb_hours; // Спинбокс добавления часов
QSqlQueryModel *model_workers; // Модель работников
QSqlQueryModel *model_hours; // Модель часов
QString current_id_worker;
};
#endif // WIDGET_H
.cpp
Код:
#include "widget.h"
#include <QSqlQuery>
#include <QSqlError>
#include <QDate>
#include <QLabel>
#include <QVBoxLayout>
#include <QHBoxLayout>
#include <QMessageBox>
#include <QDebug>
Widget::Widget(QWidget *parent)
: QWidget(parent)
{
// Устанавливаем заголовок окна
setWindowTitle("Tabel");
// Подключаемся к базе данных
if(!connectDatabase())
return;
table_workers = new QTableView;
connect(table_workers, SIGNAL(clicked(QModelIndex)), this, SLOT(onWorkerTableClicked(QModelIndex)));
table_hours = new QTableView;
le_name_worker = new QLineEdit;
btn_add_worker = new QPushButton("Add worker");
connect(btn_add_worker, SIGNAL(clicked()), this, SLOT(onAddWorker()));
btn_add_hour = new QPushButton("Add hours");
connect(btn_add_hour, SIGNAL(clicked()), this, SLOT(onAddHours()));
date_edit = new QDateEdit;
date_edit->setDate(QDate::currentDate());
sb_hours = new QDoubleSpinBox;
sb_hours->setSuffix(" h");
sb_hours->setMaximum(24);
QVBoxLayout *vb_left = new QVBoxLayout;
vb_left->addWidget(table_workers);
QHBoxLayout *hb_left = new QHBoxLayout;
hb_left->addWidget(new QLabel("name worker: "));
hb_left->addWidget(le_name_worker);
vb_left->addLayout(hb_left);
vb_left->addWidget(le_name_worker);
vb_left->addWidget(btn_add_worker);
QVBoxLayout *vb_right = new QVBoxLayout;
vb_right->addWidget(table_hours);
QHBoxLayout *hb_right = new QHBoxLayout;
hb_right->addWidget(date_edit);
hb_right->addWidget(sb_hours);
hb_right->addWidget(btn_add_hour);
vb_right->addLayout(hb_right);
QHBoxLayout *hb = new QHBoxLayout;
hb->addLayout(vb_left);
hb->addLayout(vb_right);
setLayout(hb);
model_workers = new QSqlQueryModel(this);
table_workers->setModel(model_workers);
model_workers->setQuery("SELECT id, name_worker FROM workers_table");
// Подгоняем ширину колонок под контент
table_workers->resizeColumnsToContents();
model_hours = new QSqlQueryModel(this);
table_hours->setModel(model_hours);
}
Widget::~Widget()
{
}
bool Widget::connectDatabase()
{
database = QSqlDatabase::addDatabase("QSQLITE");
database.setDatabaseName("database_tabel.sql");
// открываем БД, проверяем ошибки
if(!database.open())
{
// Выводим сообщение об ошибке и выходим
QMessageBox::information(this, " SQL ERROR", database.lastError().text());
return false;
}
// Проверяем существует ли таблица workers_table, если нет создаем ее.
if(!database.tables().contains("workers_table"))
{
QSqlQuery query;
QString str = "CREATE TABLE workers_table (id INTEGER PRIMARY KEY AUTOINCREMENT"
", name_worker VARCHAR(20));";
if(!query.exec(str))
{
QMessageBox::information(this, "SQL ERROR", query.lastError().text());
return false;
}
qDebug()<<"CREATE TABLE workers_table";
}
// Проверяем существует ли таблица hours_table, если нет создаем ее.
if(!database.tables().contains("hours_table"))
{
QSqlQuery query;
QString str = "CREATE TABLE hours_table (id INTEGER PRIMARY KEY AUTOINCREMENT, "
"id_worker INTEGER, "
"date_w VARCHAR(10), "
"hours_w VARCHAR(2));";
if(!query.exec(str))
{
QMessageBox::information(this, "SQL ERROR", query.lastError().text());
return false;
}
qDebug()<<"CREATE TABLE hoers_table";
}
return true;
}
void Widget::onAddWorker()
{
QString str_name = le_name_worker->text();
// Если поле ввода имени пустое, выводим сообщение о ошибке
if(str_name.isEmpty())
{
QMessageBox::information(this, "", "enter the name of the worker");
return;
}
le_name_worker->clear();
QSqlQuery query;
QString str_query = "INSERT INTO workers_table (name_worker) "
"VALUES ('" + str_name + "');";
if(!query.exec(str_query))
{
QMessageBox::information(this, "SQL ERROR", query.lastError().text());
return;
}
model_workers->setQuery("SELECT *FROM workers_table");
table_workers->resizeColumnsToContents();
}
void Widget::onAddHours()
{
QSqlQuery query;
QString str_query = "INSERT INTO hours_table (id_worker, date_w, hours_w) "
"VALUES ("
"'" + current_id_worker + "', "
"'" + date_edit->date().toString("yyyy_MM_dd") + "', "
"'" + QString::number(sb_hours->value()) + "'"
");";
if(!query.exec(str_query))
{
QMessageBox::information(this, "SQL ERROR", query.lastError().text());
return;
}
model_hours->setQuery("SELECT date_w, hours_w FROM hours_table WHERE id_worker = " + current_id_worker +
" ORDER BY date_w;");
date_edit->setDate(QDate::currentDate());
}
void Widget::onWorkerTableClicked(QModelIndex index)
{
current_id_worker = model_workers->data(model_workers->index(index.row(), 0)).toString();
model_hours->setQuery("SELECT date_w, hours_w FROM hours_table WHERE id_worker = " + current_id_worker +
" ORDER BY date_w;");
}
может несколько аляписто, но все это для примера, по быстрому на коленке.
вы интересовались как связать две таблицы. собственно это происходит в слоте
Код:
void Widget::onWorkerTableClicked(QModelIndex index)
{
current_id_worker = model_workers->data(model_workers->index(index.row(), 0)).toString();
model_hours->setQuery("SELECT date_w, hours_w FROM hours_table WHERE id_worker = " + current_id_worker +
" ORDER BY date_w;");
}