mirror of
https://github.com/tnodir/fort
synced 2024-11-15 06:35:23 +00:00
UI: Rules: Tree view by types
This commit is contained in:
parent
6df010c54a
commit
129c9095fa
39
src/ui/3rdparty/sqlite/sqlitedb.cpp
vendored
39
src/ui/3rdparty/sqlite/sqlitedb.cpp
vendored
@ -123,14 +123,15 @@ bool SqliteDb::executeStr(const QString &sql)
|
||||
return execute(sqlUtf8.data());
|
||||
}
|
||||
|
||||
QVariant SqliteDb::executeEx(const char *sql, const QVariantList &vars, int resultCount, bool *ok)
|
||||
QVariant SqliteDb::executeEx(const char *sql, const QVariantList &vars, const QVariantHash &varsMap,
|
||||
int resultCount, bool *ok)
|
||||
{
|
||||
QVariantList list;
|
||||
|
||||
SqliteStmt stmt;
|
||||
bool success = false;
|
||||
|
||||
if (prepare(stmt, sql, vars)) {
|
||||
if (prepare(stmt, sql, vars, varsMap)) {
|
||||
const auto stepRes = stmt.step();
|
||||
success = (stepRes != SqliteStmt::StepError);
|
||||
|
||||
@ -151,25 +152,47 @@ QVariant SqliteDb::executeEx(const char *sql, const QVariantList &vars, int resu
|
||||
return (listSize == 0) ? QVariant() : (listSize == 1 ? list.at(0) : list);
|
||||
}
|
||||
|
||||
bool SqliteDb::executeExOk(const char *sql, const QVariantList &vars)
|
||||
QVariant SqliteDb::executeEx(const char *sql, const QVariantList &vars, int resultCount, bool *ok)
|
||||
{
|
||||
return executeEx(sql, vars, {}, resultCount, ok);
|
||||
}
|
||||
|
||||
bool SqliteDb::executeExOk(const char *sql, const QVariantList &vars, const QVariantHash &varsMap)
|
||||
{
|
||||
bool ok = false;
|
||||
executeEx(sql, vars, 0, &ok);
|
||||
executeEx(sql, vars, varsMap, 0, &ok);
|
||||
return ok;
|
||||
}
|
||||
|
||||
bool SqliteDb::prepare(SqliteStmt &stmt, const char *sql, const QVariantList &vars)
|
||||
bool SqliteDb::executeExOk(const char *sql, const QVariantList &vars)
|
||||
{
|
||||
return executeExOk(sql, vars, {});
|
||||
}
|
||||
|
||||
bool SqliteDb::prepare(
|
||||
SqliteStmt &stmt, const char *sql, const QVariantList &vars, const QVariantHash &varsMap)
|
||||
{
|
||||
if (!stmt.prepare(db(), sql))
|
||||
return false;
|
||||
|
||||
return stmt.bindVars(vars);
|
||||
return stmt.bindVars(vars) && stmt.bindVarsMap(varsMap);
|
||||
}
|
||||
|
||||
bool SqliteDb::prepare(SqliteStmt &stmt, const char *sql, const QVariantList &vars)
|
||||
{
|
||||
return prepare(stmt, sql, vars, {});
|
||||
}
|
||||
|
||||
bool SqliteDb::prepare(
|
||||
SqliteStmt &stmt, const QString &sql, const QVariantList &vars, const QVariantHash &varsMap)
|
||||
{
|
||||
const auto sqlUtf8 = sql.toUtf8();
|
||||
return prepare(stmt, sqlUtf8.constData(), vars, varsMap);
|
||||
}
|
||||
|
||||
bool SqliteDb::prepare(SqliteStmt &stmt, const QString &sql, const QVariantList &vars)
|
||||
{
|
||||
const auto sqlUtf8 = sql.toUtf8();
|
||||
return prepare(stmt, sqlUtf8.constData(), vars);
|
||||
return prepare(stmt, sql, vars, {});
|
||||
}
|
||||
|
||||
bool SqliteDb::done(SqliteStmt *stmt)
|
||||
|
9
src/ui/3rdparty/sqlite/sqlitedb.h
vendored
9
src/ui/3rdparty/sqlite/sqlitedb.h
vendored
@ -79,13 +79,22 @@ public:
|
||||
bool execute(const char *sql);
|
||||
bool executeStr(const QString &sql);
|
||||
|
||||
QVariant executeEx(const char *sql, const QVariantList &vars, const QVariantHash &varsMap,
|
||||
int resultCount = 1, bool *ok = nullptr);
|
||||
QVariant executeEx(const char *sql, const QVariantList &vars = {}, int resultCount = 1,
|
||||
bool *ok = nullptr);
|
||||
|
||||
bool executeExOk(const char *sql, const QVariantList &vars, const QVariantHash &varsMap);
|
||||
bool executeExOk(const char *sql, const QVariantList &vars = {});
|
||||
|
||||
bool prepare(SqliteStmt &stmt, const char *sql, const QVariantList &vars,
|
||||
const QVariantHash &varsMap);
|
||||
bool prepare(SqliteStmt &stmt, const char *sql, const QVariantList &vars = {});
|
||||
|
||||
bool prepare(SqliteStmt &stmt, const QString &sql, const QVariantList &vars,
|
||||
const QVariantHash &varsMap);
|
||||
bool prepare(SqliteStmt &stmt, const QString &sql, const QVariantList &vars = {});
|
||||
|
||||
bool done(SqliteStmt *stmt);
|
||||
|
||||
qint64 lastInsertRowid() const;
|
||||
|
5
src/ui/3rdparty/sqlite/sqlitestmt.cpp
vendored
5
src/ui/3rdparty/sqlite/sqlitestmt.cpp
vendored
@ -164,8 +164,11 @@ bool SqliteStmt::bindVars(const QVariantList &vars, int index)
|
||||
return true;
|
||||
}
|
||||
|
||||
bool SqliteStmt::bindVarsMap(const QVariantMap &varsMap)
|
||||
bool SqliteStmt::bindVarsMap(const QVariantHash &varsMap)
|
||||
{
|
||||
if (varsMap.isEmpty())
|
||||
return true;
|
||||
|
||||
auto it = varsMap.constBegin();
|
||||
for (; it != varsMap.constEnd(); ++it) {
|
||||
const QString k = it.key();
|
||||
|
2
src/ui/3rdparty/sqlite/sqlitestmt.h
vendored
2
src/ui/3rdparty/sqlite/sqlitestmt.h
vendored
@ -46,7 +46,7 @@ public:
|
||||
bool bindVarBlob(int index, const QVariant &v);
|
||||
bool bindVar(int index, const QVariant &v);
|
||||
bool bindVars(const QVariantList &vars, int index = 1);
|
||||
bool bindVarsMap(const QVariantMap &varsMap);
|
||||
bool bindVarsMap(const QVariantHash &varsMap);
|
||||
|
||||
bool clearBindings();
|
||||
bool reset();
|
||||
|
@ -58,6 +58,7 @@ SOURCES += \
|
||||
form/controls/tableview.cpp \
|
||||
form/controls/textarea2splitter.cpp \
|
||||
form/controls/textarea2splitterhandle.cpp \
|
||||
form/controls/treeview.cpp \
|
||||
form/controls/zonesselector.cpp \
|
||||
form/dialog/dialogutil.cpp \
|
||||
form/dialog/passworddialog.cpp \
|
||||
@ -268,6 +269,7 @@ HEADERS += \
|
||||
form/controls/tableview.h \
|
||||
form/controls/textarea2splitter.h \
|
||||
form/controls/textarea2splitterhandle.h \
|
||||
form/controls/treeview.h \
|
||||
form/controls/zonesselector.h \
|
||||
form/dialog/dialogutil.h \
|
||||
form/dialog/passworddialog.h \
|
||||
|
@ -265,6 +265,26 @@ QLayout *ControlUtil::createRowLayout(QWidget *w1, QWidget *w2, int stretch1)
|
||||
return layout;
|
||||
}
|
||||
|
||||
void ControlUtil::clearLayout(QLayout *layout)
|
||||
{
|
||||
if (!layout)
|
||||
return;
|
||||
|
||||
int i = layout->count();
|
||||
while (--i >= 0) {
|
||||
auto item = layout->takeAt(i);
|
||||
|
||||
auto w = item->widget();
|
||||
if (w) {
|
||||
w->deleteLater();
|
||||
} else {
|
||||
clearLayout(item->layout());
|
||||
}
|
||||
|
||||
delete item;
|
||||
}
|
||||
}
|
||||
|
||||
QLayout *ControlUtil::createScrollLayout(QLayout *content, bool isBgTransparent)
|
||||
{
|
||||
auto scrollAreaContent = new QWidget();
|
||||
|
@ -90,6 +90,8 @@ public:
|
||||
|
||||
static QLayout *createRowLayout(QWidget *w1, QWidget *w2, int stretch1 = 1);
|
||||
|
||||
static void clearLayout(QLayout *layout);
|
||||
|
||||
static QLayout *createScrollLayout(QLayout *content, bool isBgTransparent = true);
|
||||
static QWidget *wrapToScrollArea(QWidget *content, bool isBgTransparent = true);
|
||||
|
||||
|
50
src/ui/form/controls/treeview.cpp
Normal file
50
src/ui/form/controls/treeview.cpp
Normal file
@ -0,0 +1,50 @@
|
||||
#include "treeview.h"
|
||||
|
||||
#include <QContextMenuEvent>
|
||||
#include <QMenu>
|
||||
|
||||
TreeView::TreeView(QWidget *parent) : QTreeView(parent)
|
||||
{
|
||||
setTabKeyNavigation(false);
|
||||
setUniformRowHeights(true);
|
||||
setAnimated(true);
|
||||
}
|
||||
|
||||
void TreeView::setModel(QAbstractItemModel *model)
|
||||
{
|
||||
QTreeView::setModel(model);
|
||||
|
||||
connect(model, &QAbstractItemModel::modelReset, this,
|
||||
[&] { emit currentIndexChanged(currentIndex()); });
|
||||
}
|
||||
|
||||
int TreeView::currentRow() const
|
||||
{
|
||||
return currentIndex().row();
|
||||
}
|
||||
|
||||
void TreeView::selectionChanged(const QItemSelection &selected, const QItemSelection &deselected)
|
||||
{
|
||||
QTreeView::selectionChanged(selected, deselected);
|
||||
|
||||
if (selected.isEmpty())
|
||||
return;
|
||||
|
||||
if (!currentIndex().isValid()) {
|
||||
setCurrentIndex(selected.indexes().first());
|
||||
}
|
||||
}
|
||||
|
||||
void TreeView::currentChanged(const QModelIndex ¤t, const QModelIndex &previous)
|
||||
{
|
||||
QTreeView::currentChanged(current, previous);
|
||||
|
||||
emit currentIndexChanged(current);
|
||||
}
|
||||
|
||||
void TreeView::contextMenuEvent(QContextMenuEvent *event)
|
||||
{
|
||||
if (m_menu) {
|
||||
m_menu->popup(event->globalPos());
|
||||
}
|
||||
}
|
34
src/ui/form/controls/treeview.h
Normal file
34
src/ui/form/controls/treeview.h
Normal file
@ -0,0 +1,34 @@
|
||||
#ifndef TREEVIEW_H
|
||||
#define TREEVIEW_H
|
||||
|
||||
#include <QTreeView>
|
||||
|
||||
class TreeView : public QTreeView
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
explicit TreeView(QWidget *parent = nullptr);
|
||||
|
||||
QMenu *menu() const { return m_menu; }
|
||||
void setMenu(QMenu *menu) { m_menu = menu; }
|
||||
|
||||
void setModel(QAbstractItemModel *model) override;
|
||||
|
||||
int currentRow() const;
|
||||
|
||||
signals:
|
||||
void currentIndexChanged(const QModelIndex &index);
|
||||
|
||||
protected:
|
||||
void selectionChanged(
|
||||
const QItemSelection &selected, const QItemSelection &deselected) override;
|
||||
void currentChanged(const QModelIndex ¤t, const QModelIndex &previous) override;
|
||||
|
||||
void contextMenuEvent(QContextMenuEvent *event) override;
|
||||
|
||||
private:
|
||||
QMenu *m_menu = nullptr;
|
||||
};
|
||||
|
||||
#endif // TREEVIEW_H
|
@ -107,6 +107,11 @@ void ZonesSelector::setupZones()
|
||||
|
||||
connect(m_menuZones, &QMenu::aboutToShow, this, &ZonesSelector::updateZonesMenu);
|
||||
|
||||
setupZonesChanged();
|
||||
}
|
||||
|
||||
void ZonesSelector::setupZonesChanged()
|
||||
{
|
||||
auto confZoneManager = IoC<ConfZoneManager>();
|
||||
|
||||
connect(confZoneManager, &ConfZoneManager::zoneRemoved, this, [&](int zoneId) {
|
||||
@ -114,14 +119,17 @@ void ZonesSelector::setupZones()
|
||||
retranslateZonesText();
|
||||
});
|
||||
|
||||
auto zoneListModel = IoC<ZoneListModel>();
|
||||
|
||||
connect(zoneListModel, &ZoneListModel::modelChanged, this, [&] {
|
||||
const auto refreshZonesMenu = [&] {
|
||||
clearZonesMenu();
|
||||
updateZonesMenuEnabled();
|
||||
});
|
||||
};
|
||||
|
||||
updateZonesMenuEnabled();
|
||||
refreshZonesMenu();
|
||||
|
||||
auto zoneListModel = IoC<ZoneListModel>();
|
||||
|
||||
connect(zoneListModel, &ZoneListModel::modelReset, this, refreshZonesMenu);
|
||||
connect(zoneListModel, &ZoneListModel::dataChanged, this, refreshZonesMenu);
|
||||
}
|
||||
|
||||
void ZonesSelector::resetZonesMenu()
|
||||
@ -134,12 +142,7 @@ void ZonesSelector::clearZonesMenu()
|
||||
{
|
||||
m_menuZones->close();
|
||||
|
||||
int i = m_menuLayout->count();
|
||||
while (--i >= 0) {
|
||||
auto item = m_menuLayout->takeAt(i);
|
||||
item->widget()->deleteLater();
|
||||
delete item;
|
||||
}
|
||||
ControlUtil::clearLayout(m_menuLayout);
|
||||
}
|
||||
|
||||
void ZonesSelector::createZonesMenu()
|
||||
|
@ -38,6 +38,7 @@ private:
|
||||
|
||||
void setupUi();
|
||||
void setupZones();
|
||||
void setupZonesChanged();
|
||||
|
||||
void resetZonesMenu();
|
||||
void clearZonesMenu();
|
||||
|
@ -14,6 +14,7 @@
|
||||
#include <form/controls/plaintextedit.h>
|
||||
#include <form/controls/zonesselector.h>
|
||||
#include <manager/windowmanager.h>
|
||||
#include <model/rulelistmodel.h>
|
||||
#include <util/iconcache.h>
|
||||
#include <util/net/netutil.h>
|
||||
|
||||
@ -100,11 +101,7 @@ void RuleEditDialog::retranslateUi()
|
||||
|
||||
void RuleEditDialog::retranslateComboRuleType()
|
||||
{
|
||||
const QStringList list = { tr("Application Rules"),
|
||||
tr("Global Rules, applied before App Rules"), tr("Global Rules, applied after App Rules"),
|
||||
tr("Preset Rules") };
|
||||
|
||||
ControlUtil::setComboBoxTexts(m_comboRuleType, list);
|
||||
ControlUtil::setComboBoxTexts(m_comboRuleType, RuleListModel::ruleTypeNames());
|
||||
}
|
||||
|
||||
void RuleEditDialog::retranslateRulePlaceholderText()
|
||||
|
@ -10,7 +10,7 @@
|
||||
#include <conf/confmanager.h>
|
||||
#include <conf/firewallconf.h>
|
||||
#include <form/controls/controlutil.h>
|
||||
#include <form/controls/tableview.h>
|
||||
#include <form/controls/treeview.h>
|
||||
#include <form/dialog/dialogutil.h>
|
||||
#include <manager/windowmanager.h>
|
||||
#include <model/rulelistmodel.h>
|
||||
@ -25,7 +25,7 @@
|
||||
|
||||
namespace {
|
||||
|
||||
constexpr int RULES_HEADER_VERSION = 1;
|
||||
constexpr int RULES_HEADER_VERSION = 2;
|
||||
|
||||
}
|
||||
|
||||
@ -74,7 +74,7 @@ void RulesWindow::saveWindowState(bool /*wasVisible*/)
|
||||
iniUser()->setRuleWindowGeometry(m_stateWatcher->geometry());
|
||||
iniUser()->setRuleWindowMaximized(m_stateWatcher->maximized());
|
||||
|
||||
auto header = m_ruleListView->horizontalHeader();
|
||||
auto header = m_ruleListView->header();
|
||||
iniUser()->setRulesHeader(header->saveState());
|
||||
iniUser()->setRulesHeaderVersion(RULES_HEADER_VERSION);
|
||||
|
||||
@ -87,7 +87,7 @@ void RulesWindow::restoreWindowState()
|
||||
iniUser()->ruleWindowMaximized());
|
||||
|
||||
if (iniUser()->rulesHeaderVersion() == RULES_HEADER_VERSION) {
|
||||
auto header = m_ruleListView->horizontalHeader();
|
||||
auto header = m_ruleListView->header();
|
||||
header->restoreState(iniUser()->rulesHeader());
|
||||
}
|
||||
}
|
||||
@ -124,14 +124,14 @@ void RulesWindow::setupUi()
|
||||
// Header
|
||||
auto header = setupHeader();
|
||||
|
||||
// Table
|
||||
setupTableRules();
|
||||
setupTableRulesHeader();
|
||||
// Tree
|
||||
setupTreeRules();
|
||||
setupTreeRulesHeader();
|
||||
|
||||
// Actions on zones table's current changed
|
||||
setupTableRulesChanged();
|
||||
// Actions on rules tree's current changed
|
||||
setupTreeRulesChanged();
|
||||
|
||||
// Actions on zone list model's changed
|
||||
// Actions on rule list model's changed
|
||||
setupRuleListModelChanged();
|
||||
|
||||
auto layout = new QVBoxLayout();
|
||||
@ -199,48 +199,52 @@ void RulesWindow::setupEditSearch()
|
||||
connect(this, &RulesWindow::aboutToShow, m_editSearch, qOverload<>(&QWidget::setFocus));
|
||||
}
|
||||
|
||||
void RulesWindow::setupTableRules()
|
||||
void RulesWindow::setupTreeRules()
|
||||
{
|
||||
m_ruleListView = new TableView();
|
||||
m_ruleListView = new TreeView();
|
||||
m_ruleListView->setAlternatingRowColors(true);
|
||||
m_ruleListView->setSelectionMode(QAbstractItemView::SingleSelection);
|
||||
m_ruleListView->setSelectionBehavior(QAbstractItemView::SelectItems);
|
||||
|
||||
m_ruleListView->setModel(ruleListModel());
|
||||
|
||||
const auto appRulesIndex = ruleListModel()->index(0, 0);
|
||||
m_ruleListView->expand(appRulesIndex);
|
||||
|
||||
m_ruleListView->setMenu(m_btEdit->menu());
|
||||
|
||||
connect(m_ruleListView, &TableView::activated, m_actEditRule, &QAction::trigger);
|
||||
connect(m_ruleListView, &TreeView::activated, m_actEditRule, &QAction::trigger);
|
||||
}
|
||||
|
||||
void RulesWindow::setupTableRulesHeader()
|
||||
void RulesWindow::setupTreeRulesHeader()
|
||||
{
|
||||
auto header = m_ruleListView->horizontalHeader();
|
||||
auto header = m_ruleListView->header();
|
||||
|
||||
header->setSectionResizeMode(0, QHeaderView::Interactive);
|
||||
header->setSectionResizeMode(1, QHeaderView::Stretch);
|
||||
header->setStretchLastSection(true);
|
||||
|
||||
header->resizeSection(0, 350);
|
||||
header->resizeSection(0, 360);
|
||||
}
|
||||
|
||||
void RulesWindow::setupTableRulesChanged()
|
||||
void RulesWindow::setupTreeRulesChanged()
|
||||
{
|
||||
const auto refreshTableRulesChanged = [&] {
|
||||
const auto refreshTreeRulesChanged = [&] {
|
||||
const int ruleIndex = ruleListCurrentIndex();
|
||||
const bool ruleSelected = (ruleIndex >= 0);
|
||||
m_actEditRule->setEnabled(ruleSelected);
|
||||
m_actRemoveRule->setEnabled(ruleSelected);
|
||||
};
|
||||
|
||||
refreshTableRulesChanged();
|
||||
refreshTreeRulesChanged();
|
||||
|
||||
connect(m_ruleListView, &TableView::currentIndexChanged, this, refreshTableRulesChanged);
|
||||
connect(m_ruleListView, &TreeView::currentIndexChanged, this, refreshTreeRulesChanged);
|
||||
}
|
||||
|
||||
void RulesWindow::setupRuleListModelChanged()
|
||||
{
|
||||
const auto refreshAddRule = [&] {
|
||||
m_actAddRule->setEnabled(ruleListModel()->rowCount() < ConfUtil::zoneMaxCount());
|
||||
m_actAddRule->setEnabled(ruleListModel()->rowCount() < ConfUtil::ruleMaxCount());
|
||||
};
|
||||
|
||||
refreshAddRule();
|
||||
|
@ -15,7 +15,7 @@ class IniUser;
|
||||
class RuleEditDialog;
|
||||
class RuleListModel;
|
||||
class RulesController;
|
||||
class TableView;
|
||||
class TreeView;
|
||||
class WidgetWindowStateWatcher;
|
||||
class WindowManager;
|
||||
|
||||
@ -50,9 +50,9 @@ private:
|
||||
void setupUi();
|
||||
QLayout *setupHeader();
|
||||
void setupEditSearch();
|
||||
void setupTableRules();
|
||||
void setupTableRulesHeader();
|
||||
void setupTableRulesChanged();
|
||||
void setupTreeRules();
|
||||
void setupTreeRulesHeader();
|
||||
void setupTreeRulesChanged();
|
||||
void setupRuleListModelChanged();
|
||||
|
||||
void addNewRule();
|
||||
@ -75,7 +75,7 @@ private:
|
||||
QAction *m_actRemoveRule = nullptr;
|
||||
QLineEdit *m_editSearch = nullptr;
|
||||
QPushButton *m_btMenu = nullptr;
|
||||
TableView *m_ruleListView = nullptr;
|
||||
TreeView *m_ruleListView = nullptr;
|
||||
|
||||
RuleEditDialog *m_formRuleEdit = nullptr;
|
||||
};
|
||||
|
@ -394,10 +394,10 @@ QIcon AppListModel::appIcon(const AppRow &appRow) const
|
||||
return appInfoCache()->appIcon(appRow.appPath);
|
||||
}
|
||||
|
||||
bool AppListModel::updateAppRow(const QString &sql, const QVariantList &vars, AppRow &appRow) const
|
||||
bool AppListModel::updateAppRow(const QString &sql, const QVariantHash &vars, AppRow &appRow) const
|
||||
{
|
||||
SqliteStmt stmt;
|
||||
if (!(sqliteDb()->prepare(stmt, sql, vars) && stmt.step() == SqliteStmt::StepRow)) {
|
||||
if (!(sqliteDb()->prepare(stmt, sql, {}, vars) && stmt.step() == SqliteStmt::StepRow)) {
|
||||
appRow.invalidate();
|
||||
return false;
|
||||
}
|
||||
@ -438,7 +438,7 @@ const AppRow &AppListModel::appRowAt(int row) const
|
||||
AppRow AppListModel::appRowById(qint64 appId) const
|
||||
{
|
||||
AppRow appRow;
|
||||
updateAppRow(sqlBase() + " WHERE t.app_id = ?1;", { appId }, appRow);
|
||||
updateAppRow(sqlBase() + " WHERE t.app_id = :id;", { { "id", appId } }, appRow);
|
||||
return appRow;
|
||||
}
|
||||
|
||||
@ -455,12 +455,8 @@ AppRow AppListModel::appRowByPath(const QString &appPath) const
|
||||
return appRow;
|
||||
}
|
||||
|
||||
bool AppListModel::updateTableRow(int row) const
|
||||
bool AppListModel::updateTableRow(const QVariantHash &vars, int /*row*/) const
|
||||
{
|
||||
QVariantList vars;
|
||||
fillSqlVars(vars);
|
||||
vars.append(row); // must be a last one for :OFFSET
|
||||
|
||||
return updateAppRow(sql(), vars, m_appRow);
|
||||
}
|
||||
|
||||
|
@ -42,7 +42,7 @@ public:
|
||||
AppRow appRowByPath(const QString &appPath) const;
|
||||
|
||||
protected:
|
||||
bool updateTableRow(int row) const override;
|
||||
bool updateTableRow(const QVariantHash &vars, int row) const override;
|
||||
TableRow &tableRow() const override { return m_appRow; }
|
||||
|
||||
QString sqlBase() const override;
|
||||
@ -57,7 +57,7 @@ private:
|
||||
|
||||
QIcon appIcon(const AppRow &appRow) const;
|
||||
|
||||
bool updateAppRow(const QString &sql, const QVariantList &vars, AppRow &appRow) const;
|
||||
bool updateAppRow(const QString &sql, const QVariantHash &vars, AppRow &appRow) const;
|
||||
|
||||
private:
|
||||
mutable AppRow m_appRow;
|
||||
|
@ -265,7 +265,7 @@ void ConnBlockListModel::updateConnIdRange()
|
||||
updateConnRows(oldIdMin, oldIdMax, idMin, idMax);
|
||||
}
|
||||
|
||||
bool ConnBlockListModel::updateTableRow(int row) const
|
||||
bool ConnBlockListModel::updateTableRow(const QVariantHash & /*vars*/, int row) const
|
||||
{
|
||||
const qint64 connId = connIdMin() + row;
|
||||
|
||||
|
@ -70,9 +70,11 @@ protected slots:
|
||||
void updateConnIdRange();
|
||||
|
||||
protected:
|
||||
bool updateTableRow(int row) const override;
|
||||
bool updateTableRow(const QVariantHash &vars, int row) const override;
|
||||
TableRow &tableRow() const override { return m_connRow; }
|
||||
|
||||
void fillQueryVarsForRow(QVariantHash & /*vars*/, int /*row*/) const override { }
|
||||
|
||||
int doSqlCount() const override;
|
||||
QString sqlBase() const override;
|
||||
QString sqlWhere() const override;
|
||||
|
@ -54,9 +54,6 @@ SqliteDb *RuleListModel::sqliteDb() const
|
||||
|
||||
void RuleListModel::initialize()
|
||||
{
|
||||
setSortColumn(1);
|
||||
setSortOrder(Qt::AscendingOrder);
|
||||
|
||||
auto confRuleManager = IoC<ConfRuleManager>();
|
||||
|
||||
connect(confRuleManager, &ConfRuleManager::ruleAdded, this, &TableItemModel::reset);
|
||||
@ -64,9 +61,51 @@ void RuleListModel::initialize()
|
||||
connect(confRuleManager, &ConfRuleManager::ruleUpdated, this, &TableItemModel::refresh);
|
||||
}
|
||||
|
||||
int RuleListModel::columnCount(const QModelIndex &parent) const
|
||||
QModelIndex RuleListModel::index(int row, int column, const QModelIndex &parent) const
|
||||
{
|
||||
return parent.isValid() ? 0 : 2;
|
||||
int id = row;
|
||||
if (parent.isValid()) {
|
||||
id = parent.internalId();
|
||||
if (id < 0)
|
||||
return QModelIndex();
|
||||
|
||||
id = -(id + 1);
|
||||
}
|
||||
|
||||
return createIndex(row, column, id);
|
||||
}
|
||||
|
||||
QModelIndex RuleListModel::parent(const QModelIndex &child) const
|
||||
{
|
||||
if (!child.isValid())
|
||||
return QModelIndex();
|
||||
|
||||
const int id = child.internalId();
|
||||
if (id >= 0)
|
||||
return QModelIndex();
|
||||
|
||||
const int row = -(id + 1);
|
||||
|
||||
return createIndex(row, 0, row);
|
||||
}
|
||||
|
||||
int RuleListModel::rowCount(const QModelIndex &parent) const
|
||||
{
|
||||
if (!parent.isValid())
|
||||
return Rule::RuleTypeCount;
|
||||
|
||||
const int id = parent.internalId();
|
||||
if (id < 0)
|
||||
return 0;
|
||||
|
||||
setSqlRuleType(id);
|
||||
|
||||
return FtsTableSqlModel::rowCount(parent);
|
||||
}
|
||||
|
||||
int RuleListModel::columnCount(const QModelIndex & /*parent*/) const
|
||||
{
|
||||
return 2;
|
||||
}
|
||||
|
||||
QVariant RuleListModel::headerData(int section, Qt::Orientation orientation, int role) const
|
||||
@ -82,6 +121,13 @@ QVariant RuleListModel::data(const QModelIndex &index, int role) const
|
||||
if (!index.isValid())
|
||||
return QVariant();
|
||||
|
||||
const QModelIndex parent = index.parent();
|
||||
if (!parent.isValid()) {
|
||||
return rootData(index, role);
|
||||
}
|
||||
|
||||
setSqlRuleType(parent.row());
|
||||
|
||||
switch (role) {
|
||||
// Label
|
||||
case Qt::DisplayRole:
|
||||
@ -95,6 +141,29 @@ QVariant RuleListModel::data(const QModelIndex &index, int role) const
|
||||
// Enabled
|
||||
case Qt::CheckStateRole:
|
||||
return dataCheckState(index);
|
||||
|
||||
// Row Height
|
||||
case Qt::SizeHintRole:
|
||||
return QSize(100, 24);
|
||||
}
|
||||
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
QVariant RuleListModel::rootData(const QModelIndex &index, int role) const
|
||||
{
|
||||
if (index.column() > 0)
|
||||
return QVariant();
|
||||
|
||||
switch (role) {
|
||||
// Label
|
||||
case Qt::DisplayRole:
|
||||
case Qt::ToolTipRole:
|
||||
return ruleTypeNames().value(index.row());
|
||||
|
||||
// Row Height
|
||||
case Qt::SizeHintRole:
|
||||
return QSize(100, 24);
|
||||
}
|
||||
|
||||
return QVariant();
|
||||
@ -155,13 +224,14 @@ QVariant RuleListModel::dataCheckState(const QModelIndex &index) const
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
bool RuleListModel::setData(const QModelIndex &index, const QVariant &value, int role)
|
||||
bool RuleListModel::setData(const QModelIndex &index, const QVariant & /*value*/, int role)
|
||||
{
|
||||
Q_UNUSED(value);
|
||||
|
||||
if (!index.isValid())
|
||||
return false;
|
||||
|
||||
const QModelIndex parent = index.parent();
|
||||
setSqlRuleType(parent.row());
|
||||
|
||||
switch (role) {
|
||||
case Qt::CheckStateRole:
|
||||
const auto ruleRow = ruleRowAt(index.row());
|
||||
@ -171,9 +241,23 @@ bool RuleListModel::setData(const QModelIndex &index, const QVariant &value, int
|
||||
return false;
|
||||
}
|
||||
|
||||
Qt::ItemFlags RuleListModel::flagHasChildren(const QModelIndex &index) const
|
||||
{
|
||||
const QModelIndex parent = index.parent();
|
||||
|
||||
return parent.isValid() ? Qt::ItemNeverHasChildren : Qt::NoItemFlags;
|
||||
}
|
||||
|
||||
Qt::ItemFlags RuleListModel::flagIsUserCheckable(const QModelIndex &index) const
|
||||
{
|
||||
return index.column() == 0 ? Qt::ItemIsUserCheckable : Qt::NoItemFlags;
|
||||
const QModelIndex parent = index.parent();
|
||||
|
||||
return parent.isValid() && index.column() == 0 ? Qt::ItemIsUserCheckable : Qt::NoItemFlags;
|
||||
}
|
||||
|
||||
void RuleListModel::fillQueryVars(QVariantHash &vars) const
|
||||
{
|
||||
vars.insert(":type", sqlRuleType());
|
||||
}
|
||||
|
||||
const RuleRow &RuleListModel::ruleRowAt(int row) const
|
||||
@ -183,20 +267,16 @@ const RuleRow &RuleListModel::ruleRowAt(int row) const
|
||||
return m_ruleRow;
|
||||
}
|
||||
|
||||
bool RuleListModel::updateTableRow(int row) const
|
||||
bool RuleListModel::updateTableRow(const QVariantHash &vars, int /*row*/) const
|
||||
{
|
||||
QVariantList vars;
|
||||
fillSqlVars(vars);
|
||||
vars.append(row); // must be a last one for :OFFSET
|
||||
|
||||
return updateRuleRow(sql(), vars, m_ruleRow);
|
||||
}
|
||||
|
||||
bool RuleListModel::updateRuleRow(
|
||||
const QString &sql, const QVariantList &vars, RuleRow &ruleRow) const
|
||||
const QString &sql, const QVariantHash &vars, RuleRow &ruleRow) const
|
||||
{
|
||||
SqliteStmt stmt;
|
||||
if (!(sqliteDb()->prepare(stmt, sql, vars) && stmt.step() == SqliteStmt::StepRow)) {
|
||||
if (!(sqliteDb()->prepare(stmt, sql, {}, vars) && stmt.step() == SqliteStmt::StepRow)) {
|
||||
ruleRow.invalidate();
|
||||
return false;
|
||||
}
|
||||
@ -230,15 +310,36 @@ QString RuleListModel::sqlBase() const
|
||||
" accept_zones,"
|
||||
" reject_zones,"
|
||||
" mod_time"
|
||||
" FROM rule t";
|
||||
" FROM rule t"
|
||||
" WHERE rule_type = :type";
|
||||
}
|
||||
|
||||
QString RuleListModel::sqlWhereFts() const
|
||||
{
|
||||
return " WHERE t.rule_id IN ( SELECT rowid FROM rule_fts(:match) )";
|
||||
return " AND t.rule_id IN ( SELECT rowid FROM rule_fts(:match) )";
|
||||
}
|
||||
|
||||
QString RuleListModel::sqlOrderColumn() const
|
||||
{
|
||||
return "rule_type, lower(name)";
|
||||
}
|
||||
|
||||
void RuleListModel::setSqlRuleType(qint8 v) const
|
||||
{
|
||||
if (m_sqlRuleType == v)
|
||||
return;
|
||||
|
||||
m_sqlRuleType = v;
|
||||
|
||||
invalidateRowCache();
|
||||
}
|
||||
|
||||
QStringList RuleListModel::ruleTypeNames()
|
||||
{
|
||||
return {
|
||||
RuleListModel::tr("Application Rules"),
|
||||
RuleListModel::tr("Global Rules, applied before App Rules"),
|
||||
RuleListModel::tr("Global Rules, applied after App Rules"),
|
||||
RuleListModel::tr("Preset Rules"),
|
||||
};
|
||||
}
|
||||
|
@ -29,6 +29,11 @@ public:
|
||||
|
||||
void initialize();
|
||||
|
||||
QModelIndex index(
|
||||
int row, int column, const QModelIndex &parent = QModelIndex()) const override;
|
||||
QModelIndex parent(const QModelIndex &child) const override;
|
||||
|
||||
int rowCount(const QModelIndex &parent = QModelIndex()) const override;
|
||||
int columnCount(const QModelIndex &parent = QModelIndex()) const override;
|
||||
|
||||
QVariant headerData(
|
||||
@ -38,25 +43,37 @@ public:
|
||||
|
||||
const RuleRow &ruleRowAt(int row) const;
|
||||
|
||||
static QStringList ruleTypeNames();
|
||||
|
||||
protected:
|
||||
Qt::ItemFlags flagHasChildren(const QModelIndex &index) const override;
|
||||
Qt::ItemFlags flagIsUserCheckable(const QModelIndex &index) const override;
|
||||
|
||||
bool updateTableRow(int row) const override;
|
||||
void fillQueryVars(QVariantHash &vars) const override;
|
||||
|
||||
bool updateTableRow(const QVariantHash &vars, int row) const override;
|
||||
TableRow &tableRow() const override { return m_ruleRow; }
|
||||
|
||||
bool updateRuleRow(const QString &sql, const QVariantList &vars, RuleRow &ruleRow) const;
|
||||
bool updateRuleRow(const QString &sql, const QVariantHash &vars, RuleRow &ruleRow) const;
|
||||
|
||||
QString sqlBase() const override;
|
||||
QString sqlWhereFts() const override;
|
||||
QString sqlOrderColumn() const override;
|
||||
|
||||
qint8 sqlRuleType() const { return m_sqlRuleType; }
|
||||
void setSqlRuleType(qint8 v) const;
|
||||
|
||||
private:
|
||||
QVariant rootData(const QModelIndex &index, int role) const;
|
||||
|
||||
QVariant headerDataDisplay(int section) const;
|
||||
QVariant dataDisplay(const QModelIndex &index, int role) const;
|
||||
QVariant dataDecoration(const QModelIndex &index) const;
|
||||
QVariant dataCheckState(const QModelIndex &index) const;
|
||||
|
||||
private:
|
||||
mutable qint8 m_sqlRuleType = -1;
|
||||
|
||||
mutable RuleRow m_ruleRow;
|
||||
};
|
||||
|
||||
|
@ -114,7 +114,7 @@ QVariant ServiceListModel::dataDecoration(const QModelIndex &index) const
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
bool ServiceListModel::updateTableRow(int /*row*/) const
|
||||
bool ServiceListModel::updateTableRow(const QVariantHash & /*vars*/, int /*row*/) const
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
@ -33,9 +33,11 @@ public:
|
||||
const ServiceInfo &serviceInfoAt(int index) const;
|
||||
|
||||
protected:
|
||||
bool updateTableRow(int row) const override;
|
||||
bool updateTableRow(const QVariantHash &vars, int row) const override;
|
||||
TableRow &tableRow() const override { return m_serviceRow; }
|
||||
|
||||
void fillQueryVarsForRow(QVariantHash & /*vars*/, int /*row*/) const override { }
|
||||
|
||||
private:
|
||||
QVariant dataDisplay(const QModelIndex &index) const;
|
||||
QVariant dataDisplayProcessId(const ServiceInfo &info) const;
|
||||
|
@ -177,7 +177,7 @@ void TrafListModel::reset()
|
||||
}
|
||||
}
|
||||
|
||||
bool TrafListModel::updateTableRow(int row) const
|
||||
bool TrafListModel::updateTableRow(const QVariantHash & /*vars*/, int row) const
|
||||
{
|
||||
m_trafRow.trafTime = getTrafTime(row);
|
||||
|
||||
|
@ -54,9 +54,11 @@ public slots:
|
||||
void reset();
|
||||
|
||||
protected:
|
||||
bool updateTableRow(int row) const override;
|
||||
bool updateTableRow(const QVariantHash &vars, int row) const override;
|
||||
TableRow &tableRow() const override { return m_trafRow; }
|
||||
|
||||
void fillQueryVarsForRow(QVariantHash & /*vars*/, int /*row*/) const override { }
|
||||
|
||||
QString formatTrafUnit(qint64 bytes) const;
|
||||
QString formatTrafTime(qint32 trafTime) const;
|
||||
|
||||
|
@ -171,26 +171,32 @@ QVariant ZoneListModel::zoneSourceByCode(const QString &sourceCode) const
|
||||
return m_zoneSourcesMap.value(sourceCode);
|
||||
}
|
||||
|
||||
bool ZoneListModel::updateTableRow(int row) const
|
||||
bool ZoneListModel::updateTableRow(const QVariantHash &vars, int /*row*/) const
|
||||
{
|
||||
return updateZoneRow(sql(), vars, m_zoneRow);
|
||||
}
|
||||
|
||||
bool ZoneListModel::updateZoneRow(
|
||||
const QString &sql, const QVariantHash &vars, ZoneRow &zoneRow) const
|
||||
{
|
||||
SqliteStmt stmt;
|
||||
if (!(sqliteDb()->prepare(stmt, sql(), { row }) && stmt.step() == SqliteStmt::StepRow))
|
||||
if (!(sqliteDb()->prepare(stmt, sql, {}, vars) && stmt.step() == SqliteStmt::StepRow))
|
||||
return false;
|
||||
|
||||
m_zoneRow.zoneId = stmt.columnInt(0);
|
||||
m_zoneRow.enabled = stmt.columnBool(1);
|
||||
m_zoneRow.customUrl = stmt.columnBool(2);
|
||||
m_zoneRow.zoneName = stmt.columnText(3);
|
||||
m_zoneRow.sourceCode = stmt.columnText(4);
|
||||
m_zoneRow.url = stmt.columnText(5);
|
||||
m_zoneRow.formData = stmt.columnText(6);
|
||||
m_zoneRow.addressCount = stmt.columnInt(7);
|
||||
m_zoneRow.textInline = stmt.columnText(8);
|
||||
m_zoneRow.textChecksum = stmt.columnText(9);
|
||||
m_zoneRow.binChecksum = stmt.columnText(10);
|
||||
m_zoneRow.sourceModTime = stmt.columnDateTime(11);
|
||||
m_zoneRow.lastRun = stmt.columnDateTime(12);
|
||||
m_zoneRow.lastSuccess = stmt.columnDateTime(13);
|
||||
zoneRow.zoneId = stmt.columnInt(0);
|
||||
zoneRow.enabled = stmt.columnBool(1);
|
||||
zoneRow.customUrl = stmt.columnBool(2);
|
||||
zoneRow.zoneName = stmt.columnText(3);
|
||||
zoneRow.sourceCode = stmt.columnText(4);
|
||||
zoneRow.url = stmt.columnText(5);
|
||||
zoneRow.formData = stmt.columnText(6);
|
||||
zoneRow.addressCount = stmt.columnInt(7);
|
||||
zoneRow.textInline = stmt.columnText(8);
|
||||
zoneRow.textChecksum = stmt.columnText(9);
|
||||
zoneRow.binChecksum = stmt.columnText(10);
|
||||
zoneRow.sourceModTime = stmt.columnDateTime(11);
|
||||
zoneRow.lastRun = stmt.columnDateTime(12);
|
||||
zoneRow.lastSuccess = stmt.columnDateTime(13);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
@ -47,9 +47,11 @@ public:
|
||||
protected:
|
||||
Qt::ItemFlags flagIsUserCheckable(const QModelIndex &index) const override;
|
||||
|
||||
bool updateTableRow(int row) const override;
|
||||
bool updateTableRow(const QVariantHash &vars, int row) const override;
|
||||
TableRow &tableRow() const override { return m_zoneRow; }
|
||||
|
||||
bool updateZoneRow(const QString &sql, const QVariantHash &vars, ZoneRow &zoneRow) const;
|
||||
|
||||
QString sqlBase() const override;
|
||||
|
||||
private:
|
||||
|
@ -48,9 +48,11 @@ signals:
|
||||
protected:
|
||||
Qt::ItemFlags flagIsUserCheckable(const QModelIndex &index) const override;
|
||||
|
||||
bool updateTableRow(int /*row*/) const override { return true; }
|
||||
bool updateTableRow(const QVariantHash & /*vars*/, int /*row*/) const override { return true; }
|
||||
TableRow &tableRow() const override { return m_taskRow; }
|
||||
|
||||
void fillQueryVarsForRow(QVariantHash & /*vars*/, int /*row*/) const override { }
|
||||
|
||||
private:
|
||||
QVariant dataDisplay(const QModelIndex &index) const;
|
||||
QVariant dataCheckState(const QModelIndex &index) const;
|
||||
|
@ -30,10 +30,10 @@ void FtsTableSqlModel::setFtsFilter(const QString &filter)
|
||||
resetLater();
|
||||
}
|
||||
|
||||
void FtsTableSqlModel::fillSqlVars(QVariantList &vars) const
|
||||
void FtsTableSqlModel::fillQueryVars(QVariantHash &vars) const
|
||||
{
|
||||
if (!ftsFilterMatch().isEmpty()) {
|
||||
vars.append(ftsFilterMatch());
|
||||
vars.insert(":match", ftsFilterMatch());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -15,7 +15,7 @@ public:
|
||||
void setFtsFilter(const QString &filter);
|
||||
|
||||
protected:
|
||||
void fillSqlVars(QVariantList &vars) const override;
|
||||
void fillQueryVars(QVariantHash &vars) const override;
|
||||
|
||||
QString sqlWhere() const override;
|
||||
virtual QString sqlWhereFts() const = 0;
|
||||
|
@ -9,23 +9,14 @@ QModelIndex TableItemModel::index(int row, int column, const QModelIndex &parent
|
||||
return hasIndex(row, column, parent) ? createIndex(row, column) : QModelIndex();
|
||||
}
|
||||
|
||||
QModelIndex TableItemModel::parent(const QModelIndex &child) const
|
||||
QModelIndex TableItemModel::parent(const QModelIndex & /*child*/) const
|
||||
{
|
||||
Q_UNUSED(child);
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
QModelIndex TableItemModel::sibling(int row, int column, const QModelIndex &index) const
|
||||
{
|
||||
Q_UNUSED(index);
|
||||
|
||||
return this->index(row, column);
|
||||
}
|
||||
|
||||
bool TableItemModel::hasChildren(const QModelIndex &parent) const
|
||||
{
|
||||
return !parent.isValid() && rowCount() > 0;
|
||||
return rowCount(parent) > 0;
|
||||
}
|
||||
|
||||
Qt::ItemFlags TableItemModel::flags(const QModelIndex &index) const
|
||||
@ -33,7 +24,7 @@ Qt::ItemFlags TableItemModel::flags(const QModelIndex &index) const
|
||||
if (!index.isValid())
|
||||
return Qt::NoItemFlags;
|
||||
|
||||
return Qt::ItemIsSelectable | Qt::ItemIsEnabled | Qt::ItemNeverHasChildren
|
||||
return Qt::ItemIsSelectable | Qt::ItemIsEnabled | flagHasChildren(index)
|
||||
| flagIsUserCheckable(index);
|
||||
}
|
||||
|
||||
@ -48,6 +39,11 @@ void TableItemModel::resetLater()
|
||||
m_resetTimer->startTrigger();
|
||||
}
|
||||
|
||||
Qt::ItemFlags TableItemModel::flagHasChildren(const QModelIndex & /*index*/) const
|
||||
{
|
||||
return Qt::ItemNeverHasChildren;
|
||||
}
|
||||
|
||||
Qt::ItemFlags TableItemModel::flagIsUserCheckable(const QModelIndex & /*index*/) const
|
||||
{
|
||||
return Qt::NoItemFlags;
|
||||
@ -70,7 +66,7 @@ void TableItemModel::refresh()
|
||||
emit dataChanged(firstCell, lastCell);
|
||||
}
|
||||
|
||||
void TableItemModel::invalidateRowCache()
|
||||
void TableItemModel::invalidateRowCache() const
|
||||
{
|
||||
tableRow().invalidate();
|
||||
}
|
||||
@ -80,9 +76,18 @@ void TableItemModel::updateRowCache(int row) const
|
||||
if (tableRow().isValid(row))
|
||||
return;
|
||||
|
||||
if (row >= 0 && !updateTableRow(row)) {
|
||||
row = -1;
|
||||
if (row >= 0) {
|
||||
QVariantHash vars;
|
||||
fillQueryVarsForRow(vars, row);
|
||||
|
||||
if (!updateTableRow(vars, row)) {
|
||||
row = -1;
|
||||
}
|
||||
}
|
||||
|
||||
tableRow().row = row;
|
||||
}
|
||||
|
||||
void TableItemModel::fillQueryVars(QVariantHash & /*vars*/) const { }
|
||||
|
||||
void TableItemModel::fillQueryVarsForRow(QVariantHash & /*vars*/, int /*row*/) const { }
|
||||
|
@ -25,7 +25,6 @@ public:
|
||||
int row, int column, const QModelIndex &parent = QModelIndex()) const override;
|
||||
QModelIndex parent(const QModelIndex &child) const override;
|
||||
|
||||
QModelIndex sibling(int row, int column, const QModelIndex &index) const override;
|
||||
bool hasChildren(const QModelIndex &parent = QModelIndex()) const override;
|
||||
|
||||
Qt::ItemFlags flags(const QModelIndex &index) const override;
|
||||
@ -36,12 +35,16 @@ public slots:
|
||||
void refresh();
|
||||
|
||||
protected:
|
||||
virtual Qt::ItemFlags flagHasChildren(const QModelIndex &index) const;
|
||||
virtual Qt::ItemFlags flagIsUserCheckable(const QModelIndex &index) const;
|
||||
|
||||
virtual void invalidateRowCache();
|
||||
virtual void invalidateRowCache() const;
|
||||
void updateRowCache(int row) const;
|
||||
|
||||
virtual bool updateTableRow(int row) const = 0;
|
||||
virtual void fillQueryVars(QVariantHash &vars) const;
|
||||
virtual void fillQueryVarsForRow(QVariantHash &vars, int row) const;
|
||||
|
||||
virtual bool updateTableRow(const QVariantHash &vars, int row) const = 0;
|
||||
virtual TableRow &tableRow() const = 0;
|
||||
|
||||
private:
|
||||
|
@ -5,15 +5,13 @@
|
||||
|
||||
TableSqlModel::TableSqlModel(QObject *parent) : TableItemModel(parent) { }
|
||||
|
||||
int TableSqlModel::rowCount(const QModelIndex &parent) const
|
||||
int TableSqlModel::rowCount(const QModelIndex & /*parent*/) const
|
||||
{
|
||||
Q_UNUSED(parent);
|
||||
|
||||
if (m_rowCount < 0) {
|
||||
m_rowCount = doSqlCount();
|
||||
if (m_sqlRowCount < 0) {
|
||||
m_sqlRowCount = doSqlCount();
|
||||
}
|
||||
|
||||
return m_rowCount;
|
||||
return m_sqlRowCount;
|
||||
}
|
||||
|
||||
void TableSqlModel::sort(int column, Qt::SortOrder order)
|
||||
@ -26,26 +24,26 @@ void TableSqlModel::sort(int column, Qt::SortOrder order)
|
||||
}
|
||||
}
|
||||
|
||||
void TableSqlModel::invalidateRowCache()
|
||||
void TableSqlModel::invalidateRowCache() const
|
||||
{
|
||||
m_rowCount = -1;
|
||||
setSqlRowCount(-1);
|
||||
TableItemModel::invalidateRowCache();
|
||||
emit modelChanged();
|
||||
}
|
||||
|
||||
void TableSqlModel::fillSqlVars(QVariantList &vars) const
|
||||
void TableSqlModel::fillQueryVarsForRow(QVariantHash &vars, int row) const
|
||||
{
|
||||
Q_UNUSED(vars);
|
||||
fillQueryVars(vars);
|
||||
vars.insert(":offset", row);
|
||||
}
|
||||
|
||||
int TableSqlModel::doSqlCount() const
|
||||
{
|
||||
QVariantList vars;
|
||||
fillSqlVars(vars);
|
||||
QVariantHash vars;
|
||||
fillQueryVars(vars);
|
||||
|
||||
const auto sqlUtf8 = sqlCount().toUtf8();
|
||||
|
||||
return sqliteDb()->executeEx(sqlUtf8, vars).toInt();
|
||||
return sqliteDb()->executeEx(sqlUtf8, {}, vars).toInt();
|
||||
}
|
||||
|
||||
QString TableSqlModel::sqlCount() const
|
||||
@ -83,5 +81,5 @@ QString TableSqlModel::sqlOrderColumn() const
|
||||
|
||||
QString TableSqlModel::sqlLimitOffset() const
|
||||
{
|
||||
return " LIMIT 1 OFFSET :row";
|
||||
return " LIMIT 1 OFFSET :offset";
|
||||
}
|
||||
|
@ -18,13 +18,10 @@ public:
|
||||
|
||||
void sort(int column, Qt::SortOrder order = Qt::AscendingOrder) override;
|
||||
|
||||
signals:
|
||||
void modelChanged();
|
||||
|
||||
protected:
|
||||
void invalidateRowCache() override;
|
||||
void invalidateRowCache() const override;
|
||||
|
||||
virtual void fillSqlVars(QVariantList &vars) const;
|
||||
void fillQueryVarsForRow(QVariantHash &vars, int row) const override;
|
||||
|
||||
virtual int doSqlCount() const;
|
||||
virtual QString sqlCount() const;
|
||||
@ -43,11 +40,14 @@ protected:
|
||||
Qt::SortOrder sortOrder() const { return m_sortOrder; }
|
||||
void setSortOrder(Qt::SortOrder v) { m_sortOrder = v; }
|
||||
|
||||
int sqlRowCount() const { return m_sqlRowCount; }
|
||||
void setSqlRowCount(int v) const { m_sqlRowCount = v; }
|
||||
|
||||
private:
|
||||
int m_sortColumn = -1;
|
||||
Qt::SortOrder m_sortOrder = Qt::AscendingOrder;
|
||||
|
||||
mutable int m_rowCount = -1;
|
||||
mutable int m_sqlRowCount = -1;
|
||||
};
|
||||
|
||||
#endif // TABLESQLMODEL_H
|
||||
|
Loading…
Reference in New Issue
Block a user