Add database indexing of FITS files

This commit is contained in:
2022-04-09 12:40:40 +02:00
parent 46a4715ce5
commit 04e2cfa290
6 changed files with 174 additions and 5 deletions
+1
View File
@@ -18,6 +18,7 @@ find_library(RAW_LIB NAMES raw_r raw REQUIRED)
set(TENMON_SRC
database.cpp
databaseview.cpp
filesystemwidget.cpp
imageinfo.cpp
imageringlist.cpp
+1 -1
View File
@@ -48,7 +48,7 @@ bool Database::init()
m_checkFile = QSqlQuery(m_database);
m_checkFile.prepare("SELECT id,mtime FROM fits_files WHERE file=?");
m_headerKeywords = QSqlQuery(m_database);
m_headerKeywords.prepare("SELECT DISTINCT key FROM fits_headers");
m_headerKeywords.prepare("SELECT DISTINCT key FROM fits_headers ORDER BY key");
m_deleteFile = QSqlQuery(m_database);
m_deleteFile.prepare("DELETE FROM fits_files WHERE id=?");
return true;
+112
View File
@@ -0,0 +1,112 @@
#include "databaseview.h"
#include <QVBoxLayout>
#include <QPushButton>
#include <QSettings>
#include <QDialogButtonBox>
#include <QHeaderView>
const QStringList DEFAULT_COLUMNS = {"EXPTIME", "OBJECT", "RA", "DEC"};
SelectColumnsDialog::SelectColumnsDialog(QWidget *parent) : QDialog(parent)
{
m_listWidget = new QListWidget(this);
m_listWidget->setSelectionMode(QAbstractItemView::MultiSelection);
QVBoxLayout *layout = new QVBoxLayout(this);
setLayout(layout);
layout->addWidget(m_listWidget);
QDialogButtonBox *buttonBox = new QDialogButtonBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel);
connect(buttonBox, &QDialogButtonBox::accepted, this, &QDialog::accept);
connect(buttonBox, &QDialogButtonBox::rejected, this, &QDialog::reject);
layout->addWidget(buttonBox);
setWindowTitle(tr("Select columns"));
}
void SelectColumnsDialog::setColumns(QStringList columns)
{
QSettings settings;
m_listWidget->addItems(columns);
QStringList selected = settings.value("databaseview/selectedColumns", DEFAULT_COLUMNS).toStringList();
for(auto &sel : selected)
{
int i = columns.indexOf(sel);
if(i>=0)
m_listWidget->item(i)->setSelected(true);
}
}
QStringList SelectColumnsDialog::selectedColumns()
{
QStringList ret;
for(auto &sel : m_listWidget->selectedItems())
ret.append(sel->text());
return ret;
}
DataBaseView::DataBaseView(Database *database, QWidget *parent) : QWidget(parent)
,m_database(database)
{
QVBoxLayout *layout = new QVBoxLayout(this);
setLayout(layout);
m_tableView = new QTableView(this);
m_tableView->verticalHeader()->setDefaultSectionSize(1);
layout->addWidget(m_tableView);
m_model = new QSqlQueryModel(this);
QSettings settings;
m_tableView->setModel(m_model);
m_tableView->horizontalHeader()->restoreState(settings.value("databaseview/header").toByteArray());
QHBoxLayout *hlayout = new QHBoxLayout(this);
layout->addLayout(hlayout);
QPushButton *selectColumnsButton = new QPushButton(tr("Select columns"), this);
hlayout->addWidget(selectColumnsButton);
connect(selectColumnsButton, &QPushButton::pressed, this, &DataBaseView::selectColumns);
QPushButton *loadDatabaseButton = new QPushButton(tr("Load database"), this);
hlayout->addWidget(loadDatabaseButton);
connect(loadDatabaseButton, &QPushButton::pressed, this, &DataBaseView::loadDatabase);
}
DataBaseView::~DataBaseView()
{
QSettings settings;
settings.setValue("databaseview/header", m_tableView->horizontalHeader()->saveState());
}
void DataBaseView::selectColumns()
{
SelectColumnsDialog dialog;
QStringList columns = m_database->getFitsKeywords();
dialog.setColumns(columns);
if(dialog.exec() == QDialog::Accepted)
{
QSettings settings;
QStringList columns = dialog.selectedColumns();
settings.setValue("databaseview/selectedColumns", columns);
prepareQuery(columns);
}
}
void DataBaseView::loadDatabase()
{
QSettings settings;
prepareQuery(settings.value("databaseview/selectedColumns", DEFAULT_COLUMNS).toStringList());
}
void DataBaseView::prepareQuery(const QStringList &columns)
{
QString sql = "SELECT file,";
for(auto &column : columns)
{
sql += QString("GROUP_CONCAT(CASE WHEN key=\"%1\" THEN value END) AS \"%1\",").arg(column);
}
sql.chop(1);
sql += " FROM fits_files LEFT JOIN fits_headers ON fits_files.id=id_file GROUP BY fits_files.id";
m_model->setQuery(sql);
}
+37
View File
@@ -0,0 +1,37 @@
#ifndef DATABASEVIEW_H
#define DATABASEVIEW_H
#include <QDialog>
#include <QWidget>
#include <QSqlQueryModel>
#include <QTableView>
#include <QListWidget>
#include "database.h"
class SelectColumnsDialog : public QDialog
{
Q_OBJECT
QListWidget *m_listWidget;
public:
SelectColumnsDialog(QWidget *parent = nullptr);
void setColumns(QStringList columns);
QStringList selectedColumns();
};
class DataBaseView : public QWidget
{
Q_OBJECT
Database *m_database;
QTableView *m_tableView;
QSqlQueryModel *m_model;
public:
explicit DataBaseView(Database *database, QWidget *parent = nullptr);
~DataBaseView();
public slots:
void selectColumns();
void loadDatabase();
protected:
void prepareQuery(const QStringList &columns);
};
#endif // DATABASEVIEW_H
+20 -4
View File
@@ -51,6 +51,12 @@ MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent)
m_filesystem = new FilesystemWidget(m_ringList, this);
connect(m_filesystem, SIGNAL(fileSelected(int)), this, SLOT(loadFile(int)));
m_database = new Database(this);
if(!m_database->init())
QMessageBox::critical(this, tr("Can't open DB"), tr("Can't open SQLITE database"));
m_databaseView = new DataBaseView(m_database, this);
QDockWidget *stretchDock = new QDockWidget(tr("Stretch"), this);
stretchDock->setWidget(m_stretchPanel);
stretchDock->setObjectName("strechDock");
@@ -61,6 +67,12 @@ MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent)
filesystemDock->setObjectName("filesystemDock");
addDockWidget(Qt::LeftDockWidgetArea, filesystemDock);
QDockWidget *databaseViewDock = new QDockWidget(tr("FITS files database"), this);
databaseViewDock->setWidget(m_databaseView);
databaseViewDock->setObjectName("databaseViewDock");
databaseViewDock->hide();
addDockWidget(Qt::RightDockWidgetArea, databaseViewDock);
setWindowTitle(tr("Tenmon"));
connect(m_ringList, SIGNAL(pixmapLoaded(Image*)), this, SLOT(pixmapLoaded(Image*)));
@@ -118,14 +130,11 @@ MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent)
analyzeMenu->addActions({statsAction, peakAction, starAction});
menuBar()->addMenu(analyzeMenu);
m_database = new Database(this);
if(!m_database->init())
QMessageBox::critical(this, tr("Can't open DB"), tr("Can't open SQLITE database"));
QMenu *dockMenu = new QMenu(tr("Docks"), this);
dockMenu->addAction(infoDock->toggleViewAction());
dockMenu->addAction(stretchDock->toggleViewAction());
dockMenu->addAction(filesystemDock->toggleViewAction());
dockMenu->addAction(databaseViewDock->toggleViewAction());
menuBar()->addMenu(dockMenu);
setupSigterm();
@@ -267,6 +276,13 @@ void MainWindow::loadFile(int row)
m_ringList->loadFile(row);
}
void MainWindow::indexDir()
{
QString dir = QFileDialog::getExistingDirectory(this, tr("Index directory"), _lastDir);
if(!dir.isEmpty())
m_database->indexDir(dir);
}
void MainWindow::saveAs()
{
QString file = QFileDialog::getSaveFileName(this, tr("Save as"), _lastDir, tr("Images (*.jpg *.png *.JPG *.PNG)"));
+3
View File
@@ -10,6 +10,7 @@
#include "imagescrollareagl.h"
#include "filesystemwidget.h"
#include "stretchpanel.h"
#include "databaseview.h"
class MainWindow : public QMainWindow
{
@@ -21,6 +22,7 @@ class MainWindow : public QMainWindow
Database *m_database;
ImageInfo *m_info;
FilesystemWidget *m_filesystem;
DataBaseView *m_databaseView;
static int socketPair[2];
QSocketNotifier *socketNotifier;
QString _lastDir;
@@ -41,6 +43,7 @@ protected slots:
void loadFile();
void loadFile(const QString path);
void loadFile(int row);
void indexDir();
void saveAs();
void markImage();
void unmarkImage();