From 035709b70f2770a16f05daba6f9ef15a170da3e9 Mon Sep 17 00:00:00 2001 From: Claveau Joshua Date: Sat, 4 Apr 2020 17:43:58 +0200 Subject: [PATCH] Revamp the structur of project database --- sources/bordertitleblock.cpp | 40 +++--- sources/bordertitleblock.h | 4 +- sources/dataBase/projectdatabase.cpp | 208 +++++++++++++++++++++------ sources/dataBase/projectdatabase.h | 6 +- sources/diagram.cpp | 8 ++ sources/diagram.h | 4 + sources/diagramcontext.cpp | 8 ++ sources/diagramcontext.h | 1 + sources/qetapp.cpp | 5 +- sources/qetdiagrameditor.cpp | 6 +- sources/titleblockproperties.h | 2 +- 11 files changed, 224 insertions(+), 68 deletions(-) diff --git a/sources/bordertitleblock.cpp b/sources/bordertitleblock.cpp index 9256276d4..39b928a1d 100644 --- a/sources/bordertitleblock.cpp +++ b/sources/bordertitleblock.cpp @@ -40,12 +40,12 @@ BorderTitleBlock::BorderTitleBlock(QObject *parent) : QObject(parent) { // at first, the internal titleblock template renderer uses the default titleblock template - titleblock_template_renderer_ = new TitleBlockTemplateRenderer(this); - titleblock_template_renderer_ -> setTitleBlockTemplate(QETApp::defaultTitleBlockTemplate()); + m_titleblock_template_renderer = new TitleBlockTemplateRenderer(this); + m_titleblock_template_renderer -> setTitleBlockTemplate(QETApp::defaultTitleBlockTemplate()); // disable the QPicture-based cache from Qt 4.8 to avoid rendering errors and crashes if (!QRegExp("4\\.[0-7]\\.").exactMatch(qVersion())) { - titleblock_template_renderer_ -> setUseCache(false); + m_titleblock_template_renderer -> setUseCache(false); } // dimensions par defaut du schema @@ -73,9 +73,13 @@ BorderTitleBlock::~BorderTitleBlock() { QRectF BorderTitleBlock::titleBlockRect() const { if (m_edge == Qt::BottomEdge) - return QRectF(diagram_rect_.bottomLeft(), QSize(diagram_rect_.width(), titleblock_template_renderer_ -> height())); + return QRectF(diagram_rect_.bottomLeft(), QSize(diagram_rect_.width(), m_titleblock_template_renderer -> height())); else - return QRectF(diagram_rect_.topRight(), QSize(titleblock_template_renderer_ -> height(), diagram_rect_.height())); + return QRectF(diagram_rect_.topRight(), QSize(m_titleblock_template_renderer -> height(), diagram_rect_.height())); +} + +DiagramContext BorderTitleBlock::titleblockInformation() const { + return m_titleblock_template_renderer->context(); } /** @@ -93,7 +97,7 @@ QRectF BorderTitleBlock::titleBlockRectForQPainter() const if (m_edge == Qt::BottomEdge) //Rect at bottom have same position and dimension of displayed rect return titleBlockRect(); else - return QRectF (diagram_rect_.bottomRight(), QSize(diagram_rect_.height(), titleblock_template_renderer_ -> height())); + return QRectF (diagram_rect_.bottomRight(), QSize(diagram_rect_.height(), m_titleblock_template_renderer -> height())); } @@ -317,7 +321,7 @@ void BorderTitleBlock::importBorder(const BorderProperties &bp) { @see TitleBlockTemplateRenderer::titleBlockTemplate() */ const TitleBlockTemplate *BorderTitleBlock::titleBlockTemplate() { - return(titleblock_template_renderer_ -> titleBlockTemplate()); + return(m_titleblock_template_renderer -> titleBlockTemplate()); } /** @@ -325,14 +329,14 @@ const TitleBlockTemplate *BorderTitleBlock::titleBlockTemplate() { @see TitleBlockTemplateRenderer::setTitleBlockTemplate() */ void BorderTitleBlock::setTitleBlockTemplate(const TitleBlockTemplate *titleblock_template) { - titleblock_template_renderer_ -> setTitleBlockTemplate(titleblock_template); + m_titleblock_template_renderer -> setTitleBlockTemplate(titleblock_template); } /** @return The name of the template used to render the titleblock. */ QString BorderTitleBlock::titleBlockTemplateName() const { - QString tbt_name = titleblock_template_renderer_ -> titleBlockTemplate() -> name(); + QString tbt_name = m_titleblock_template_renderer -> titleBlockTemplate() -> name(); return((tbt_name == "default") ? "" : tbt_name); } @@ -344,7 +348,7 @@ QString BorderTitleBlock::titleBlockTemplateName() const { */ void BorderTitleBlock::titleBlockTemplateChanged(const QString &template_name) { if (titleBlockTemplateName() != template_name) return; - titleblock_template_renderer_ -> invalidateRenderedTemplate(); + m_titleblock_template_renderer -> invalidateRenderedTemplate(); } /** @@ -496,14 +500,14 @@ void BorderTitleBlock::draw(QPainter *painter) if (m_edge == Qt::BottomEdge) { painter -> translate(tbt_rect.topLeft()); - titleblock_template_renderer_ -> render(painter, tbt_rect.width()); + m_titleblock_template_renderer -> render(painter, tbt_rect.width()); painter -> translate(-tbt_rect.topLeft()); } else { painter->translate(tbt_rect.topLeft()); painter->rotate(-90); - titleblock_template_renderer_ -> render(painter, tbt_rect.width()); + m_titleblock_template_renderer -> render(painter, tbt_rect.width()); painter->rotate(90); painter -> translate(-tbt_rect.topLeft()); } @@ -581,7 +585,7 @@ void BorderTitleBlock::drawDxf(int width, int height, bool keep_aspect_ratio, QS if (display_titleblock_) { //qp -> translate(titleblock_rect_.topLeft()); QRectF rect = titleBlockRect(); - titleblock_template_renderer_ -> renderDxf(rect, rect.width(), file_path, color); + m_titleblock_template_renderer -> renderDxf(rect, rect.width(), file_path, color); //qp -> translate(-titleblock_rect_.topLeft()); } @@ -765,7 +769,7 @@ void BorderTitleBlock::updateDiagramContextForTitleBlock(const DiagramContext &i context.addValue("previous-folio-num", m_previous_folio_num); context.addValue("next-folio-num", m_next_folio_num); - titleblock_template_renderer_ -> setContext(context); + m_titleblock_template_renderer -> setContext(context); } QString BorderTitleBlock::incrementLetters(const QString &string) { @@ -866,9 +870,9 @@ void BorderTitleBlock::setAutoPageNum(const QString &auto_page_num) { void BorderTitleBlock::setPreviousFolioNum(const QString &previous) { m_previous_folio_num = previous; - DiagramContext context = titleblock_template_renderer_->context(); + DiagramContext context = m_titleblock_template_renderer->context(); context.addValue("previous-folio-num", m_previous_folio_num); - titleblock_template_renderer_->setContext(context); + m_titleblock_template_renderer->setContext(context); } /** @@ -878,7 +882,7 @@ void BorderTitleBlock::setPreviousFolioNum(const QString &previous) void BorderTitleBlock::setNextFolioNum(const QString &next) { m_next_folio_num = next; - DiagramContext context = titleblock_template_renderer_->context(); + DiagramContext context = m_titleblock_template_renderer->context(); context.addValue("next-folio-num", m_next_folio_num); - titleblock_template_renderer_->setContext(context); + m_titleblock_template_renderer->setContext(context); } diff --git a/sources/bordertitleblock.h b/sources/bordertitleblock.h index bb5574d9e..4bade8bb2 100644 --- a/sources/bordertitleblock.h +++ b/sources/bordertitleblock.h @@ -76,6 +76,8 @@ class BorderTitleBlock : public QObject qreal diagramHeight() const { return(rowsTotalHeight() + columnsHeaderHeight()); } QRectF titleBlockRect () const; + + DiagramContext titleblockInformation() const; private: QRectF titleBlockRectForQPainter () const; @@ -255,6 +257,6 @@ class BorderTitleBlock : public QObject bool display_columns_; bool display_rows_; bool display_border_; - TitleBlockTemplateRenderer *titleblock_template_renderer_; + TitleBlockTemplateRenderer *m_titleblock_template_renderer; }; #endif diff --git a/sources/dataBase/projectdatabase.cpp b/sources/dataBase/projectdatabase.cpp index 76732cd9a..0989b9e19 100644 --- a/sources/dataBase/projectdatabase.cpp +++ b/sources/dataBase/projectdatabase.cpp @@ -127,7 +127,10 @@ QStringList projectDataBase::headersFromElementsInfoQuery(const QString &query) */ void projectDataBase::updateDB() { - populateElementsTable(); + populateDiagramTable(); + populateDiagramInfoTable(); + populateElementTable(); + populateElementInfoTable(); emit dataBaseUpdated(); } @@ -158,62 +161,152 @@ bool projectDataBase::createDataBase(const QString &connection_name, const QStri { m_data_base = QSqlDatabase::addDatabase("QSQLITE", connect_name); m_data_base.setDatabaseName(name); - if(!m_data_base.open()) - { + if(!m_data_base.open()) { m_data_base.close(); return false; } - //Create the elements table - QString elements_table("CREATE TABLE element_info("); - bool first = true; - for (auto string : elementsInfoKeys()) + m_data_base.exec("PRAGMA temp_store = MEMORY"); + m_data_base.exec("PRAGMA journal_mode = MEMORY"); + m_data_base.exec("PRAGMA synchronous = OFF"); + + QSqlQuery query_(m_data_base); + bool first_ = true; + + //Create diagram table + QString diagram_table("CREATE TABLE diagram (" + "uuid VARCHAR(50) PRIMARY KEY NOT NULL," + "pos INTEGER)"); + if (!query_.exec(diagram_table)) { + qDebug() << "diagram_table query : "<< query_.lastError(); + } + + //Create the table element + QString element_table("CREATE TABLE element" + "( " + "uuid VARCHAR(50) PRIMARY KEY NOT NULL, " + "diagram_uuid VARCHAR(50) NOT NULL," + "pos VARCHAR(6) NOT NULL," + "type VARCHAR(50)," + "sub_type VARCHAR(50)," + "FOREIGN KEY (diagram_uuid) REFERENCES diagram (uuid)" + ")"); + if (!query_.exec(element_table)) { + qDebug() <<" element_table query : "<< query_.lastError(); + } + + //Create the diagram info table + QString diagram_info_table("CREATE TABLE diagram_info (diagram_uuid VARCHAR(50) PRIMARY KEY NOT NULL, "); + first_ = true; + for (auto string : QETApp::diagramInfoKeys()) { - if (first) { - first = false; + if (first_) { + first_ = false; } else { - elements_table += ","; + diagram_info_table += ", "; + } + diagram_info_table += string += string=="date" ? " DATE" : " VARCHAR(100)"; + } + diagram_info_table += ", FOREIGN KEY (diagram_uuid) REFERENCES diagram (uuid))"; + if (!query_.exec(diagram_info_table)) { + qDebug() << "diagram_info_table query : " << query_.lastError(); + } + + //Create the element info table + QString element_info_table("CREATE TABLE element_info(element_uuid VARCHAR(50) PRIMARY KEY NOT NULL,"); + first_=true; + for (auto string : QETApp::elementInfoKeys()) + { + if (first_) { + first_ = false; + } else { + element_info_table += ","; } - elements_table += string += " VARCHAR(512)"; + element_info_table += string += " VARCHAR(100)"; } - elements_table += ");"; + element_info_table += ", FOREIGN KEY (element_uuid) REFERENCES element (uuid));"; - QSqlQuery query_(elements_table, m_data_base); - query_.exec(); + if (!query_.exec(element_info_table)) { + qDebug() << " element_info_table query : " << query_.lastError(); + } } updateDB(); return true; } +void projectDataBase::populateDiagramTable() +{ + QSqlQuery query_(m_data_base); + query_.exec("DELETE FROM diagram"); + + QString insert_("INSERT INTO diagram (uuid, pos) VALUES (:uuid, :pos)"); + query_.prepare(insert_); + for (auto diagram : m_project->diagrams()) + { + query_.bindValue(":uuid", diagram->uuid().toString()); + query_.bindValue(":pos", m_project->folioIndex(diagram)); + if(!query_.exec()) { + qDebug() << "projectDataBase::populateDiagramTable insert error : " << query_.lastError(); + } + } +} + +/** + * @brief projectDataBase::populateElementTable + * Populate the element table + */ +void projectDataBase::populateElementTable() +{ + QSqlQuery query_(m_data_base); + query_.exec("DELETE FROM element"); + + QString insert_("INSERT INTO element (uuid, diagram_uuid, pos, type, sub_type) VALUES (:uuid, :diagram_uuid, :pos, :type, :sub_type)"); + query_.prepare(insert_); + + for (auto diagram : m_project->diagrams()) + { + ElementProvider ep(diagram); + QList elements_list = ep.find(Element::Simple | Element::Terminale | Element::Master); + //Insert all value into the database + for (auto elmt : elements_list) + { + query_.bindValue(":uuid", elmt->uuid().toString()); + query_.bindValue(":diagram_uuid", diagram->uuid().toString()); + query_.bindValue(":pos", diagram->convertPosition(elmt->scenePos()).toString()); + query_.bindValue(":type", elmt->linkTypeToString()); + query_.bindValue(":sub_type", elmt->kindInformations()["type"].toString()); + if (!query_.exec()) { + qDebug() << "projectDataBase::populateElementTable insert error : " << query_.lastError(); + } + } + } +} + /** * @brief projectDataBase::populateElementsTable * Populate the elements table */ -void projectDataBase::populateElementsTable() +void projectDataBase::populateElementInfoTable() { - //Very ugly, in futur we should update the table instead of delete all - QSqlQuery clear_table(m_data_base); - if (!clear_table.exec("DELETE FROM element_info")) { - qDebug() << "last error " << clear_table.lastError(); - } + QSqlQuery query(m_data_base); + query.exec("DELETE FROM element_info"); + //Prepare the query used for insert new record QStringList bind_values; - for (auto key : elementsInfoKeys()) { + for (auto key : QETApp::elementInfoKeys()) { bind_values << key.prepend(":"); } - QString insert("INSERT INTO element_info (" + - elementsInfoKeys().join(", ") + - ") VALUES (" + + QString insert("INSERT INTO element_info (element_uuid," + + QETApp::elementInfoKeys().join(", ") + + ") VALUES (:uuid," + bind_values.join(", ") + ")"); - QSqlQuery query(m_data_base); query.prepare(insert); - for (auto *diagram : m_project->diagrams()) { ElementProvider ep(diagram); @@ -222,6 +315,7 @@ void projectDataBase::populateElementsTable() //Insert all value into the database for (auto elmt : elements_list) { + query.bindValue(":uuid", elmt->uuid().toString()); auto hash = elementInfoToString(elmt); for (auto key : hash.keys()) { @@ -230,17 +324,53 @@ void projectDataBase::populateElementsTable() query.bindValue(bind, value); } - query.bindValue(":element_type", elmt->linkTypeToString()); - query.bindValue(":element_subtype", elmt->kindInformations()["type"].toString()); - query.bindValue(":pos", elmt->diagram()->convertPosition(elmt->scenePos()).toString()); - if (!query.exec()) { - qDebug() << "projectDataBase::populateElementsTable insert error : " << query.lastError(); + qDebug() << "projectDataBase::populateElementInfoTable insert error : " << query.lastError(); } } } } +void projectDataBase::populateDiagramInfoTable() +{ + QSqlQuery query(m_data_base); + query.exec("DELETE FROM diagram_info"); + + //Prepare the query used for insert new record + QStringList bind_values; + for (auto key : QETApp::diagramInfoKeys()) { + bind_values << key.prepend(":"); + } + QString insert("INSERT INTO diagram_info (diagram_uuid, " + + QETApp::diagramInfoKeys().join(", ") + + ") VALUES (:uuid, " + + bind_values.join(", ") + + ")"); + + query.prepare(insert); + + for (auto *diagram : m_project->diagrams()) + { + query.bindValue(":uuid", diagram->uuid()); + + auto infos = diagram->border_and_titleblock.titleblockInformation(); + for (auto key : QETApp::diagramInfoKeys()) + { + if (key == "date") { + query.bindValue(":date", QDate::fromString(infos.value("date").toString(), Qt::SystemLocaleShortDate)); + } else { + auto value = infos.value(key); + auto bind = key.prepend(":"); + query.bindValue(bind, value); + } + } + + if (!query.exec()) { + qDebug() << "projectDataBase::populateDiagramInfoTable insert error : " << query.lastError(); + } + } +} + /** * @brief projectDataBase::elementInfoToString * @param elmt @@ -262,18 +392,6 @@ QHash projectDataBase::elementInfoToString(Element *elmt) return hash; } -/** - * @brief projectDataBase::elementsInfoKeys - * @return QETApp::elementInfoKeys() + "element_type" and "element_subtype" - */ -QStringList projectDataBase::elementsInfoKeys() -{ - auto keys_ = QETApp::elementInfoKeys(); - keys_<< "element_type" << "subtype" << "pos"; - - return keys_; -} - /** * @brief projectDataBase::exportDb * @param parent @@ -308,5 +426,7 @@ void projectDataBase::exportDb(projectDataBase *db, QWidget *parent, const QStri } //Database is filled at creation, work is done. - projectDataBase file_db(db->project(), "export_project_db_" + db->project()->uuid().toString(), path_); + QString connection_name("export_project_db_" + db->project()->uuid().toString()); + projectDataBase file_db(db->project(), connection_name, path_); + QSqlDatabase::removeDatabase(connection_name); } diff --git a/sources/dataBase/projectdatabase.h b/sources/dataBase/projectdatabase.h index 44da85046..610a9d2ba 100644 --- a/sources/dataBase/projectdatabase.h +++ b/sources/dataBase/projectdatabase.h @@ -49,7 +49,6 @@ class projectDataBase : public QObject void updateDB(); QETProject *project() const; - static QStringList elementsInfoKeys(); static QStringList headersFromElementsInfoQuery(const QString &query); signals: @@ -57,7 +56,10 @@ class projectDataBase : public QObject private: bool createDataBase(const QString &connection_name= QString(), const QString &name = QString()); - void populateElementsTable(); + void populateDiagramTable(); + void populateElementTable(); + void populateElementInfoTable(); + void populateDiagramInfoTable(); static QHash elementInfoToString(Element *elmt); private: diff --git a/sources/diagram.cpp b/sources/diagram.cpp index 249b632b7..6b46922f5 100644 --- a/sources/diagram.cpp +++ b/sources/diagram.cpp @@ -444,6 +444,14 @@ void Diagram::keyReleaseEvent(QKeyEvent *e) } } +/** + * @brief Diagram::uuid + * @return the uuid of this diagram + */ +QUuid Diagram::uuid() { + return m_uuid; +} + /** * @brief Diagram::setEventInterface * Set event_interface has current interface. diff --git a/sources/diagram.h b/sources/diagram.h index 3cedd53df..0cbbfa616 100644 --- a/sources/diagram.h +++ b/sources/diagram.h @@ -20,6 +20,8 @@ #include #include #include +#include + #include "bordertitleblock.h" #include "conductorproperties.h" #include "exportproperties.h" @@ -119,6 +121,7 @@ class Diagram : public QGraphicsScene bool m_freeze_new_elements; bool m_freeze_new_conductors_; + QUuid m_uuid = QUuid::createUuid(); // METHODS protected: @@ -133,6 +136,7 @@ class Diagram : public QGraphicsScene void keyReleaseEvent (QKeyEvent *) override; public: + QUuid uuid(); void setEventInterface (DiagramEventInterface *event_interface); void clearEventInterface(); diff --git a/sources/diagramcontext.cpp b/sources/diagramcontext.cpp index b2bc39cf2..80f4b1569 100644 --- a/sources/diagramcontext.cpp +++ b/sources/diagramcontext.cpp @@ -35,6 +35,14 @@ void DiagramContext::add(DiagramContext other) } } +/** + * @brief DiagramContext::remove + * @param key + */ +void DiagramContext::remove(const QString &key) { + m_content.remove(key); +} + /** @return a list containing all the keys in the context object. */ diff --git a/sources/diagramcontext.h b/sources/diagramcontext.h index ad94eb275..247bc4159 100644 --- a/sources/diagramcontext.h +++ b/sources/diagramcontext.h @@ -62,6 +62,7 @@ class DiagramContext }; void add(DiagramContext other); + void remove(const QString &key); QList keys(KeyOrder = None) const; bool contains(const QString &) const; const QVariant operator[](const QString &) const; diff --git a/sources/qetapp.cpp b/sources/qetapp.cpp index b05f29028..655f7a381 100644 --- a/sources/qetapp.cpp +++ b/sources/qetapp.cpp @@ -408,7 +408,7 @@ QString QETApp::conductorTranslatedInfoKey(const QString &key) /** * @brief QETApp::diagramInfoKeys - * @return the diagram default information keys + * @return the diagram default default information keys */ QStringList QETApp::diagramInfoKeys() { @@ -420,6 +420,8 @@ QStringList QETApp::diagramInfoKeys() list.append("plant"); list.append("locmach"); list.append("indexrev"); + list.append("date"); + list.append("display_folio"); return list; } @@ -439,6 +441,7 @@ QString QETApp::diagramTranslatedInfoKey(const QString &key) else if (key == "plant") return tr("Installation"); else if (key == "locmach") return tr("Localisation"); else if (key == "indexrev") return tr("Indice Rev"); + else if (key == "date") return tr("Date"); else return QString(); } diff --git a/sources/qetdiagrameditor.cpp b/sources/qetdiagrameditor.cpp index b4bbd335d..a13da9e07 100644 --- a/sources/qetdiagrameditor.cpp +++ b/sources/qetdiagrameditor.cpp @@ -412,7 +412,11 @@ void QETDiagramEditor::setUpActions() /*******ONLY FOR TEST DURING DEVEL*********/ auto model = new NomenclatureModel(this->currentProject(), this->currentProject()); - model->query("SELECT plant, location, label, pos, comment, description FROM element_info ORDER BY plant, location, label, comment, description"); + QString query("SELECT ei.plant AS plant, ei.location AS location, di.title AS title, ei.label AS label, ei.comment AS comment, e.pos AS pos" + " FROM element_info ei, element e, diagram_info di" + " WHERE ei.element_uuid = e.uuid AND e.diagram_uuid = di.diagram_uuid" + " ORDER BY plant, location, title, label, pos"); + model->query(query); model->setData(model->index(0,0), Qt::AlignLeft, Qt::TextAlignmentRole); model->setData(model->index(0,0), QETApp::diagramTextsFont(), Qt::FontRole); model->setHeaderData(0, Qt::Horizontal, Qt::AlignHCenter, Qt::TextAlignmentRole); diff --git a/sources/titleblockproperties.h b/sources/titleblockproperties.h index 83baa1850..d574b501c 100644 --- a/sources/titleblockproperties.h +++ b/sources/titleblockproperties.h @@ -20,6 +20,7 @@ #include #include "diagramcontext.h" #include "qet.h" + /** This class provides a container for the properties of a particular title block, i.e. title, author, date, filename, folio, template, custom @@ -60,7 +61,6 @@ class TitleBlockProperties { QString version; ///< Version (displayed by the default template) QString folio; ///< Folio information (displayed by the default template) QString auto_page_num; - QString location; DateManagement useDate; ///< Wheter to use the date attribute QString template_name; ///< Name of the template used to render the title block - an empty string means "the default template provided by the application" DiagramContext context; ///< Container for the additional, user-defined fields