From 782c94b917f2eadab98b5b0b2aded3061a68de18 Mon Sep 17 00:00:00 2001 From: Ake Hedman Date: Tue, 12 Dec 2023 18:04:31 +0100 Subject: [PATCH] Added register value edit --- .vscode/settings.json | 4 +- CMakeLists.txt | 10 + src/cdlgmdfregisterbit.ui | 2 +- src/cdlgmdfregistervalue.cpp | 175 ++++++++++++++++ src/cdlgmdfregistervalue.h | 98 +++++++++ src/cdlgmdfregistervalue.ui | 79 +------ src/cdlgmdfregistervaluelist.cpp | 339 +++++++++++++++++++++++++++++++ src/cdlgmdfregistervaluelist.h | 117 +++++++++++ src/cdlgmdfregistervaluelist.ui | 19 +- src/cfrmmdf.cpp | 167 ++++++++++----- src/cfrmmdf.h | 11 +- 11 files changed, 883 insertions(+), 138 deletions(-) create mode 100644 src/cdlgmdfregistervalue.cpp create mode 100644 src/cdlgmdfregistervalue.h create mode 100644 src/cdlgmdfregistervaluelist.cpp create mode 100644 src/cdlgmdfregistervaluelist.h diff --git a/.vscode/settings.json b/.vscode/settings.json index 7c89d872..6d71cb06 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -75,7 +75,9 @@ "any": "cpp", "numbers": "cpp", "span": "cpp", - "bitset": "cpp" + "bitset": "cpp", + "complex": "cpp", + "format": "cpp" }, "python.pythonPath": "/usr/bin/python3", "files.exclude": { diff --git a/CMakeLists.txt b/CMakeLists.txt index b8497bae..7fb0e8c1 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -593,6 +593,16 @@ add_executable(${PROJECT_NAME} src/cdlgmdfregisterbitlist.cpp src/cdlgmdfregisterbitlist.h + build/ui_cdlgmdfregistervalue.h + src/cdlgmdfregistervalue.ui + src/cdlgmdfregistervalue.cpp + src/cdlgmdfregistervalue.h + + build/ui_cdlgmdfregistervaluelist.h + src/cdlgmdfregistervaluelist.ui + src/cdlgmdfregistervaluelist.cpp + src/cdlgmdfregistervaluelist.h + ${VSCP_PATH}/src/vscp/common/version.h ${VSCP_PATH}/src/vscp/common/vscp.h ${VSCP_PATH}/src/vscp/common/vscpremotetcpif.h diff --git a/src/cdlgmdfregisterbit.ui b/src/cdlgmdfregisterbit.ui index 191e6da7..9a541f79 100644 --- a/src/cdlgmdfregisterbit.ui +++ b/src/cdlgmdfregisterbit.ui @@ -11,7 +11,7 @@ - Dialog + Register Bit Definition diff --git a/src/cdlgmdfregistervalue.cpp b/src/cdlgmdfregistervalue.cpp new file mode 100644 index 00000000..257d6286 --- /dev/null +++ b/src/cdlgmdfregistervalue.cpp @@ -0,0 +1,175 @@ +// cdlgmdfregistervalue.cpp +// +// This file is part of the VSCP (https://www.vscp.org) +// +// The MIT License (MIT) +// +// Copyright © 2000-2023 Ake Hedman, Grodans Paradis AB +// +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. +// + +#ifdef WIN32 +#include +#endif + +#include +#include + +#include + +#include "cdlgmdfregistervalue.h" +#include "ui_cdlgmdfregistervalue.h" + +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +const char CDlgMdfRegisterValue::pre_str_registerbit[] = "Register value: "; + +/////////////////////////////////////////////////////////////////////////////// +// CTor +// + +CDlgMdfRegisterValue::CDlgMdfRegisterValue(QWidget* parent) + : QDialog(parent) + , ui(new Ui::CDlgMdfRegisterValue) +{ + ui->setupUi(this); + + // m_type = mdf_type_unknown; + m_pvalue = nullptr; + + vscpworks* pworks = (vscpworks*)QCoreApplication::instance(); + + setInitialFocus(); + this->setFixedSize(this->size()); +} + +/////////////////////////////////////////////////////////////////////////////// +// DTor +// + +CDlgMdfRegisterValue::~CDlgMdfRegisterValue() +{ + delete ui; +} + +/////////////////////////////////////////////////////////////////////////////// +// initDialogData +// + +void +CDlgMdfRegisterValue::initDialogData(CMDF_Value* pvalue, int index) +{ + QString str; + + if (nullptr == pvalue) { + spdlog::error("MDF register value information - Invalid MDF register value object (initDialogData)"); + return; + } + + m_pvalue = pvalue; + + setName(pvalue->getName().c_str()); + str = pvalue->getValue().c_str(); + setValue(str); + + switch (index) { + case index_name: + ui->editName->setFocus(); + break; + + case index_value: + ui->editValue->setFocus(); + break; + + default: + ui->editName->setFocus(); + break; + } +} + +/////////////////////////////////////////////////////////////////////////////// +// setInitialFocus +// + +void +CDlgMdfRegisterValue::setInitialFocus(void) +{ + // ui->editName->setFocus(); +} + +// ---------------------------------------------------------------------------- +// Getters & Setters +// ---------------------------------------------------------------------------- + +QString +CDlgMdfRegisterValue::getName(void) +{ + return ui->editName->text(); +}; + +void +CDlgMdfRegisterValue::setName(const QString& name) +{ + ui->editName->setText(name); +}; + +// ----------------------------------------------------------------------- + +QString +CDlgMdfRegisterValue::getValue(void) +{ + return ui->editValue->text(); +}; + +void +CDlgMdfRegisterValue::setValue(const QString& name) +{ + ui->editValue->setText(name); +}; + + +/////////////////////////////////////////////////////////////////////////////// +// accept +// + +void +CDlgMdfRegisterValue::accept() +{ + std::string str; + if (nullptr != m_pvalue) { + m_pvalue->setName(getName().toStdString()); + m_pvalue->setValue(getValue().toStdString()); + } + else { + spdlog::error("MDF module information - Invalid MDF object (accept)"); + } + + QDialog::accept(); +} diff --git a/src/cdlgmdfregistervalue.h b/src/cdlgmdfregistervalue.h new file mode 100644 index 00000000..6a7c7b02 --- /dev/null +++ b/src/cdlgmdfregistervalue.h @@ -0,0 +1,98 @@ +// cdlgmdfregistervalue.h +// +// This file is part of the VSCP (https://www.vscp.org) +// +// The MIT License (MIT) +// +// Copyright © 2000-2023 Ake Hedman, Grodans Paradis AB +// +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. +// + +#ifndef CDLGMDFREGISTERVALUE_H +#define CDLGMDFREGISTERVALUE_H + +#include +#include + +#include + +namespace Ui { +class CDlgMdfRegisterValue; +} + +class CDlgMdfRegisterValue : public QDialog { + Q_OBJECT + +public: +public: + explicit CDlgMdfRegisterValue(QWidget* parent = nullptr); + ~CDlgMdfRegisterValue(); + + static const int index_name = 0; + static const int index_value = 1; + + + static const char pre_str_registerbit[]; + + /*! + Set inital focus to description + */ + void setInitialFocus(void); + + /*! + Init dialog data + @param CMDF *pmdf Pointer to MDF + @param pbit Pointer to MDF bit object + @param index Selected file item + + */ + void initDialogData(CMDF_Value* pvalue, int index = 0); + + // ---------------------------------------------------------------------------- + // Getters & Setters + // ---------------------------------------------------------------------------- + + // name + QString getName(void); + void setName(const QString& name); + + // value + QString getValue(void); + void setValue(const QString& value); + +public slots: + + /*! + Accept dialog data and write to register + */ + void accept(void); + +private: + Ui::CDlgMdfRegisterValue* ui; + + /// Pointer to MDF + CMDF* m_pmdf; + + /// Pointer to bit information + CMDF_Value* m_pvalue; +}; + +#endif // CDlgMdfRegisterValue_H diff --git a/src/cdlgmdfregistervalue.ui b/src/cdlgmdfregistervalue.ui index 90a06e23..5f6ddfae 100644 --- a/src/cdlgmdfregistervalue.ui +++ b/src/cdlgmdfregistervalue.ui @@ -7,17 +7,17 @@ 0 0 692 - 293 + 126 - Dialog + Register Value 10 - 250 + 90 671 32 @@ -35,7 +35,7 @@ 10 10 671 - 231 + 71 @@ -64,76 +64,7 @@ - - - - - - Default: - - - - - - - - - - Width - - - - - - - Min - - - - - - - Max - - - - - - - Access - - - - - - - Access right for register - - - - Read/Write - - - - - Read Only - - - - - Write Only - - - - - - - - - - - - + diff --git a/src/cdlgmdfregistervaluelist.cpp b/src/cdlgmdfregistervaluelist.cpp new file mode 100644 index 00000000..71f81482 --- /dev/null +++ b/src/cdlgmdfregistervaluelist.cpp @@ -0,0 +1,339 @@ +// cdlgmdfregistervaluelist.cpp +// +// This file is part of the VSCP (https://www.vscp.org) +// +// The MIT License (MIT) +// +// Copyright © 2000-2023 Ake Hedman, Grodans Paradis AB +// +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. +// + +#ifdef WIN32 +#include +#endif + +#include +#include + +#include + +#include "cdlgmdfregistervalue.h" +#include "cdlgmdfregistervaluelist.h" +#include "ui_cdlgmdfregistervaluelist.h" + +#include +#include +#include +#include + +#include +#include +#include +#include + +/////////////////////////////////////////////////////////////////////////////// +// CTor +// + +CDlgMdfRegisterValueList::CDlgMdfRegisterValueList(QWidget* parent) + : QDialog(parent) + , ui(new Ui::CDlgMdfRegisterValueList) +{ + m_preg = nullptr; + + ui->setupUi(this); + + vscpworks* pworks = (vscpworks*)QCoreApplication::instance(); + + connect(ui->btnAddRegisterValue, &QToolButton::clicked, this, &CDlgMdfRegisterValueList::addRegisterValue); + connect(ui->btnEditRegisterValue, &QToolButton::clicked, this, &CDlgMdfRegisterValueList::editRegisterValue); + connect(ui->btnDupRegisterValue, &QToolButton::clicked, this, &CDlgMdfRegisterValueList::dupRegisterValue); + connect(ui->btnDelRegisterValue, &QToolButton::clicked, this, &CDlgMdfRegisterValueList::deleteRegisterValue); + + connect(ui->listRegisterValues, &QListWidget::doubleClicked, this, &CDlgMdfRegisterValueList::editRegisterValue); + + this->setFixedSize(this->size()); +} + +/////////////////////////////////////////////////////////////////////////////// +// DTor +// + +CDlgMdfRegisterValueList::~CDlgMdfRegisterValueList() +{ + delete ui; +} + +/////////////////////////////////////////////////////////////////////////////// +// initDialogData +// + +void +CDlgMdfRegisterValueList::initDialogData(CMDF_Register* preg) +{ + QString str; + + if (nullptr == preg) { + QMessageBox::critical(this, tr("MDF register value information"), tr("Invalid MDF register object")); + spdlog::error("MDF register value information - Invalid MDF register object"); + return; + } + + // Save register pointer and page + m_preg = preg; + + // m_pmdf->getRegisterMap(m_page, pages); + renderValueItems(); +} + +/////////////////////////////////////////////////////////////////////////////// +// renderValueItems +// + +void +CDlgMdfRegisterValueList::renderValueItems(void) +{ + std::map pages; + + if (nullptr == m_preg) { + return; + } + + ui->listRegisterValues->clear(); + std::deque* pvalues = m_preg->getListValues(); + + int idx = 0; + for (auto it = pvalues->cbegin(); it != pvalues->cend(); ++it) { + CMDF_Value* pvalue = *it; + if (nullptr != pvalue) { + QString str = QString("Value: %1").arg(pvalue->getName().c_str()); + ui->listRegisterValues->addItem(str); + // Set data to register index + ui->listRegisterValues->item(ui->listRegisterValues->count() - 1)->setData(Qt::UserRole, idx); + } + idx++; + } +} + +/////////////////////////////////////////////////////////////////////////////// +// addRegisterValue +// + +void +CDlgMdfRegisterValueList::addRegisterValue(void) +{ + bool ok; + CMDF_Value* pvaluenew = new CMDF_Value(); + if (nullptr == pvaluenew) { + QMessageBox::critical(this, tr("MDF register bit information"), tr("Memory problem")); + spdlog::error("MDF register information - Memory problem"); + return; + } + + // Save the selected row + int idx = ui->listRegisterValues->currentRow(); + + CDlgMdfRegisterValue dlg(this); + dlg.initDialogData(pvaluenew); + dlg.setWindowTitle(tr("Add register value")); + +addbitdlg: + + if (QDialog::Accepted == dlg.exec()) { + + uint8_t mask; + // if ((mask = checkIfBitsOverlap(pvaluenew))) { + // QMessageBox::warning(this, tr("Add new bit definition"), tr("Can not add bit definition. Bits overlap with already defined bits 0b%1").arg(mask, 8, 2, QChar('0'))); + // goto addbitdlg; + // } + std::deque* pvalues = m_preg->getListValues(); + pvalues->push_back(pvaluenew); + renderValueItems(); + } + else { + delete pvaluenew; + } +} + +/////////////////////////////////////////////////////////////////////////////// +// editRegisterValue +// + +void +CDlgMdfRegisterValueList::editRegisterValue(void) +{ + bool ok; + + if (-1 != ui->listRegisterValues->currentRow()) { + + // Save the selected row + int idx = ui->listRegisterValues->currentRow(); + + QListWidgetItem* pitem = ui->listRegisterValues->currentItem(); + CMDF_Value* pvalue = m_preg->getListValues()->at(pitem->data(Qt::UserRole).toUInt()); + + CDlgMdfRegisterValue dlg(this); + dlg.initDialogData(pvalue); + + editvaluedlg: + + if (QDialog::Accepted == dlg.exec()) { + uint8_t mask; + // if ((mask = checkIfBitsOverlap(pvalue, true))) { + // QMessageBox::warning(this, tr("Edit register value"), tr("Can not add register value. Bits overlap with already defined bits 0b%1").arg(mask, 8, 2, QChar('0'))); + // goto editvaluedlg; + // } + ui->listRegisterValues->clear(); + renderValueItems(); + ui->listRegisterValues->setCurrentRow(idx); + } + } + else { + QMessageBox::warning(this, tr(APPNAME), tr("An item must be selected"), QMessageBox::Ok); + } +} + +/////////////////////////////////////////////////////////////////////////////// +// dupRegisterValue +// + +void +CDlgMdfRegisterValueList::dupRegisterValue(void) +{ + if (-1 != ui->listRegisterValues->currentRow()) { + + // Save the selected row + int idx = ui->listRegisterValues->currentRow(); + + // QListWidgetItem* pitem = ui->listRegisterBit->currentItem(); + // CMDF_Bit* preg = m_pmdf->getRegister(pitem->data(Qt::UserRole).toUInt(), m_page); + + // CMDF_Bit* pregnew = new CMDF_Bit(); + // pregnew->setPage(m_page); + + // // Make copy + // *pregnew = *preg; + + // CDlgMdfRegisterBit dlg(this); + // dlg.initDialogData(m_pmdf, pregnew); + // dupregdlg: + // if (QDialog::Accepted == dlg.exec()) { + // // Check if register is already defined + // CMDF_Bit* pregold = m_pmdf->getRegister(pregnew->getOffset(), pregnew->getPage()); + // if (nullptr != pregold) { + // QMessageBox::warning(this, tr("MDF duplicate register"), tr("Register page=%1 offset=%2 is already define. Must be unique.").arg(pregnew->getPage()).arg(pregnew->getOffset())); + // goto dupregdlg; + // } + // qDebug() << "Page=" << pregnew->getPage() << " Offset=" << pregnew->getOffset(); + // m_pmdf->getRegisterObjList()->push_back(pregnew); + // if (m_page == pregnew->getPage()) { + // m_registersSet.insert(pregnew->getOffset()); + // } + // ui->listRegisterBit->clear(); + // renderRegisterItems(); + // if (-1 != idx) { + // ui->listRegisterBit->setCurrentRow(idx); + // } + // // Warn if page is not the same as for dialog + // if (pregnew->getPage() != m_page) { + // QMessageBox::information(this, + // tr("MDF duplicate register"), + // tr("Register page=%1 offset=%2 is not on same page [%3] as registers and will be added but not shown.").arg(pregnew->getPage()).arg(pregnew->getOffset()).arg(m_page)); + // } + // } + // else { + // delete pregnew; + // } + } + else { + QMessageBox::warning(this, tr(APPNAME), tr("An item must be selected"), QMessageBox::Ok); + } +} + +/////////////////////////////////////////////////////////////////////////////// +// deleteRegisterValue +// + +void +CDlgMdfRegisterValueList::deleteRegisterValue(void) +{ + if (-1 != ui->listRegisterValues->currentRow()) { + + // Save the row + int idx = ui->listRegisterValues->currentRow(); + + QListWidgetItem* pitem = ui->listRegisterValues->currentItem(); + CMDF_Value* pvalue = m_preg->getListValues()->at(pitem->data(Qt::UserRole).toUInt()); + + std::deque::iterator it = m_preg->getListValues()->begin() + pitem->data(Qt::UserRole).toUInt(); + m_preg->getListValues()->erase(it); + + ui->listRegisterValues->clear(); + renderValueItems(); + int sel = idx; + if (0 == idx) { + sel = 0; + } + else if (m_preg->getListValues()->size() == idx) { + sel = m_preg->getListValues()->size() - 1; + } + else { + sel = idx + 1; + } + ui->listRegisterValues->setCurrentRow(sel); + } +} + +/////////////////////////////////////////////////////////////////////////////// +// accept +// + +void +CDlgMdfRegisterValueList::accept() +{ + std::string str; + if (nullptr != m_preg) { + + // str = ui->editName->text().toStdString(); + // m_pmdf->setName(str); + + // str = ui->editModel->text().toStdString(); + // m_pmdf->setModuleModel(str); + + // m_pmdf->setModuleLevel(ui->comboModuleLevel->currentIndex()); + + // str = ui->editVersion->text().toStdString(); + // m_pmdf->setModuleVersion(str); + + // str = ui->editDate->text().toStdString(); + // m_pmdf->setModuleChangeDate(str); + + // m_pmdf->setModuleBufferSize(ui->editBufferSize->value()); + + // str = ui->editCopyright->text().toStdString(); + // m_pmdf->setModuleCopyright(str); + } + else { + spdlog::error("MDF module information - Invalid MDF object (accept)"); + } + + QDialog::accept(); +} diff --git a/src/cdlgmdfregistervaluelist.h b/src/cdlgmdfregistervaluelist.h new file mode 100644 index 00000000..14accd7f --- /dev/null +++ b/src/cdlgmdfregistervaluelist.h @@ -0,0 +1,117 @@ +// cdlgmdfregistervaluelist.h +// +// This file is part of the VSCP (https://www.vscp.org) +// +// The MIT License (MIT) +// +// Copyright © 2000-2023 Ake Hedman, Grodans Paradis AB +// +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE +// SOFTWARE. +// + +#ifndef CDLGMDFREGISTERVALUELIST_H +#define CDLGMDFREGISTERVALUELIST_H + +#include +#include + +#include "cdlgmdfregister.h" + +#include + +namespace Ui { +class CDlgMdfRegisterValueList; +} + +class CDlgMdfRegisterValueList : public QDialog { + Q_OBJECT + +public: + explicit CDlgMdfRegisterValueList(QWidget* parent = nullptr); + ~CDlgMdfRegisterValueList(); + + /*! + Set edit mode. + GUID will be READ ONLY + */ + void setEditMode(); + + /*! + Init dialog data + @param pmdf Pointer to MDF object + */ + void initDialogData(CMDF_Register* preg); + + /*! + Fill in register bit items + */ + void renderValueItems(void); + + /*! + Check if bits overlap + @param pbit2test pointer to bit to test + @param bEdit Edit mode. The bit is already in the list. + @return Overlapping bits or zero iof no bits overlap + */ + uint8_t checkIfBitsOverlap(CMDF_Bit* pbit2test, bool bEdit = false) + { + uint8_t result = 0; + std::deque* pbits = m_preg->getListBits(); + for (auto it = pbits->cbegin(); it != pbits->cend(); ++it) { + CMDF_Bit* pbit = *it; + // Don't test the edited bit of in edit mode + if (bEdit && (pbit2test == pbit)) { + continue; + } + if (nullptr != pbit) { + result |= pbit->getMask(); + } + } + + return (result & pbit2test->getMask()); + }; + + // ---------------------------------------------------------------------------- + // Getters & Setters + // ---------------------------------------------------------------------------- + + /*! + Name getter/setters + */ + // void setValue(const QString& name); + // QString getValue(void); + +public slots: + void accept(void); + + // Description buttons + void addRegisterValue(void); + void editRegisterValue(void); + void dupRegisterValue(void); + void deleteRegisterValue(void); + +private: + Ui::CDlgMdfRegisterValueList* ui; + + // MDF + CMDF_Register* m_preg; +}; + +#endif // CDLGMDFREGISTERVALUELIST_H diff --git a/src/cdlgmdfregistervaluelist.ui b/src/cdlgmdfregistervaluelist.ui index 2c06bc21..ff9b456f 100644 --- a/src/cdlgmdfregistervaluelist.ui +++ b/src/cdlgmdfregistervaluelist.ui @@ -11,7 +11,7 @@ - Contacts + Register values @@ -42,24 +42,17 @@ - - - - Contact items - - - - + - + Add description item @@ -76,7 +69,7 @@ - + Edit description item @@ -93,7 +86,7 @@ - + Duplicate description item @@ -110,7 +103,7 @@ - + Delete Description item diff --git a/src/cfrmmdf.cpp b/src/cfrmmdf.cpp index 5a13be3d..caf4dcf1 100644 --- a/src/cfrmmdf.cpp +++ b/src/cfrmmdf.cpp @@ -65,6 +65,8 @@ #include "cdlgmdfregisterbit.h" #include "cdlgmdfregisterbitlist.h" #include "cdlgmdfregisterlist.h" +#include "cdlgmdfregistervalue.h" +#include "cdlgmdfregistervaluelist.h" #include #include @@ -355,31 +357,31 @@ CFrmMdf::showMdfContextMenu(const QPoint& pos) break; case mdf_type_value: - menu->addAction(QString(tr("Open list of register bits")), this, SLOT(editRegisterValue())); + menu->addAction(QString(tr("Edit register values")), this, SLOT(editRegisterValue())); break; case mdf_type_value_item: - menu->addAction(QString(tr("Edit register value item")), this, SLOT(editRegisterValue())); - menu->addAction(QString(tr("Delete register value item")), this, SLOT(deleteRegisterValue())); + menu->addAction(QString(tr("Edit register value")), this, SLOT(editRegisterValue())); + menu->addAction(QString(tr("Delete register value")), this, SLOT(deleteRegisterValue())); break; case mdf_type_value_sub_item: - menu->addAction(QString(tr("Edit register value item")), this, SLOT(editRegisterValue())); - menu->addAction(QString(tr("Delete register value item")), this, SLOT(deleteRegisterValue())); + menu->addAction(QString(tr("Edit register value")), this, SLOT(editRegisterValue())); + menu->addAction(QString(tr("Delete register value")), this, SLOT(deleteRegisterValue())); break; case mdf_type_bit: - menu->addAction(QString(tr("Open list of register bits")), this, SLOT(editRegisterBit())); + menu->addAction(QString(tr("Edit register bits")), this, SLOT(editRegisterBit())); break; case mdf_type_bit_item: - menu->addAction(QString(tr("Edit register bit item")), this, SLOT(editRegisterBit())); - menu->addAction(QString(tr("Delete register bit item")), this, SLOT(deleteRegisterBit())); + menu->addAction(QString(tr("Edit register bit definition")), this, SLOT(editRegisterBit())); + menu->addAction(QString(tr("Delete register bit definition")), this, SLOT(deleteRegisterBit())); break; case mdf_type_bit_sub_item: - menu->addAction(QString(tr("Edit register bit item")), this, SLOT(editRegisterBit())); - menu->addAction(QString(tr("Delete register bit item")), this, SLOT(deleteRegisterBit())); + menu->addAction(QString(tr("Edit register bit definition")), this, SLOT(editRegisterBit())); + menu->addAction(QString(tr("Delete register bit definition")), this, SLOT(deleteRegisterBit())); break; case mdf_type_remotevar: @@ -840,7 +842,7 @@ CFrmMdf::renderBitInfo(QMdfTreeWidgetItem* pItemParent, CMDF_Bit* pbit) pItemParent->addChild(pItem); // Valid values - renderValueInfo(pItemParent, *pbit->getListValues()); + renderValues(pItemParent, *pbit->getListValues()); // Descriptions renderDescriptionItems(pItemParent, pbit, pbit->getMapDescription()); @@ -850,11 +852,11 @@ CFrmMdf::renderBitInfo(QMdfTreeWidgetItem* pItemParent, CMDF_Bit* pbit) } /////////////////////////////////////////////////////////////////////////////// -// renderValueInfo +// renderValues // void -CFrmMdf::renderValueInfo(QTreeWidgetItem* pParent, std::deque& dequevalues) +CFrmMdf::renderValues(QTreeWidgetItem* pParent, std::deque& dequevalues, bool bParentKnown) { QString str; QMdfTreeWidgetItem* pItem; @@ -864,9 +866,16 @@ CFrmMdf::renderValueInfo(QTreeWidgetItem* pParent, std::deque& dequ return; } - QMdfTreeWidgetItem* pItemValue = new QMdfTreeWidgetItem(pParent, mdf_type_value); - pItemValue->setText(0, "Valid values"); - pParent->addChild(pItemValue); + QMdfTreeWidgetItem* pItemValueDefs; + + if (bParentKnown) { + pItemValueDefs = (QMdfTreeWidgetItem*)pParent; + } + else { + pItemValueDefs = new QMdfTreeWidgetItem(pParent, ((QMdfTreeWidgetItem*)pParent)->getObject(), mdf_type_value); + pItemValueDefs->setText(0, "Values"); + pParent->addChild(pItemValueDefs); + } // Must be items to fill in childs if (!dequevalues.size()) { @@ -877,31 +886,40 @@ CFrmMdf::renderValueInfo(QTreeWidgetItem* pParent, std::deque& dequ CMDF_Value* pvalue = dequevalues[i]; - str = QString("Value %1 (%2)").arg(i).arg(pvalue->getValue().c_str()); - // for (int j = pvalue->getPos(); j < qMin(8, pvalue->getPos() + pvalue->getWidth()); j++) { - // str += QString(" %1 ").arg(j); - // } - // str += "}"; - QMdfTreeWidgetItem* pItemParent = new QMdfTreeWidgetItem(pItemValue, pvalue, mdf_type_value_item); + str = QString("Value: %1").arg(pvalue->getName().c_str()); + QMdfTreeWidgetItem* pItemParent = new QMdfTreeWidgetItem(pItemValueDefs, pvalue, mdf_type_value_item); pItemParent->setText(0, str); - pItemValue->addChild(pItemParent); + pItemValueDefs->addChild(pItemParent); - str = QString("Name: %1").arg(pvalue->getName().c_str()); - pItem = new QMdfTreeWidgetItem(pItemParent, pvalue, mdf_type_value_sub_item); - pItem->setText(0, str); - pItemValue->addChild(pItem); + renderValueInfo(pItemParent, pvalue); + } +} - str = QString("Value: %1").arg(pvalue->getValue().c_str()); - pItem = new QMdfTreeWidgetItem(pItemParent, pvalue, mdf_type_value_sub_item); - pItem->setText(0, str); - pItemValue->addChild(pItem); +/////////////////////////////////////////////////////////////////////////////// +// renderValueInfo +// + +void +CFrmMdf::renderValueInfo(QMdfTreeWidgetItem* pParent, CMDF_Value* pvalue) +{ + QString str; + QMdfTreeWidgetItem* pItem; - // Descriptions - renderDescriptionItems(pItemParent, pvalue, pvalue->getMapDescription()); + str = QString("Name: %1").arg(pvalue->getName().c_str()); + pItem = new QMdfTreeWidgetItem(pParent, pvalue, mdf_type_value_sub_item, CDlgMdfRegisterValue::index_name); + pItem->setText(0, str); + pParent->addChild(pItem); - // Info URL's - renderInfoUrlItems(pItemParent, pvalue, pvalue->getMapDescription()); - } + str = QString("Value: %1").arg(pvalue->getValue().c_str()); + pItem = new QMdfTreeWidgetItem(pParent, pvalue, mdf_type_value_sub_item, CDlgMdfRegisterValue::index_value); + pItem->setText(0, str); + pParent->addChild(pItem); + + // Descriptions + renderDescriptionItems(pParent, pvalue, pvalue->getMapDescription()); + + // Info URL's + renderInfoUrlItems(pParent, pvalue, pvalue->getMapDescription()); } /////////////////////////////////////////////////////////////////////////////// @@ -1036,7 +1054,7 @@ CFrmMdf::renderRegisterInfo(QTreeWidgetItem* pParent, CMDF_Register* preg) renderBits(pParent, *preg->getListBits()); // Fill in valid values - renderValueInfo(pParent, *preg->getListValues()); + renderValues(pParent, *preg->getListValues()); // Descriptions renderDescriptionItems(pParent, preg, preg->getMapDescription()); @@ -2317,7 +2335,7 @@ CFrmMdf::loadMdf(void) renderBits(pSubItem, *pvar->getListBits()); // Fill in valid values - renderValueInfo(pSubItem, *pvar->getListValues()); + renderValues(pSubItem, *pvar->getListValues()); // Descriptions renderDescriptionItems(pSubItem, pvar, pvar->getMapDescription()); @@ -2475,7 +2493,7 @@ CFrmMdf::loadMdf(void) renderBits(pActionParamItem, *pactionparam->getListBits()); // Fill in valid values - renderValueInfo(pActionParamItem, *pactionparam->getListValues()); + renderValues(pActionParamItem, *pactionparam->getListValues()); // Descriptions renderDescriptionItems(pActionParamItem, pactionparam, pactionparam->getMapDescription()); @@ -2599,7 +2617,7 @@ CFrmMdf::loadMdf(void) renderBits(pEventSubItem, *pEventData->getListBits()); // Fill in valid values - renderValueInfo(pEventSubItem, *pEventData->getListValues()); + renderValues(pEventSubItem, *pEventData->getListValues()); // Descriptions renderDescriptionItems(pEventSubItem, pEventData, pEventData->getMapDescription()); @@ -5443,7 +5461,7 @@ CFrmMdf::editRegisterBit(void) switch (pItem->getObjectType()) { case mdf_type_bit: { - CMDF_Register *preg = (CMDF_Register *)pItem->getObject(); + CMDF_Register* preg = (CMDF_Register*)pItem->getObject(); CDlgMdfRegisterBitList dlg(this); dlg.initDialogData(preg); if (QDialog::Accepted == dlg.exec()) { @@ -5455,8 +5473,7 @@ CFrmMdf::editRegisterBit(void) delete item; } childrenList.clear(); - renderBits(pItem/*->parent()*/, *preg->getListBits(), true); - //pParent, *preg->getListBits() + renderBits(pItem, *preg->getListBits(), true); } } break; @@ -5585,21 +5602,75 @@ CFrmMdf::editRegisterValue(void) switch (pItem->getObjectType()) { - case mdf_type_register_page: { - CDlgMdfRegisterList dlg(this); - dlg.initDialogData(&m_mdf, selectedIndex); + case mdf_type_value: { + CMDF_Register* preg = (CMDF_Register*)pItem->getObject(); + CDlgMdfRegisterValueList dlg(this); + dlg.initDialogData(preg); if (QDialog::Accepted == dlg.exec()) { // Redraw all register items - We do not know changes - QList childrenList = m_headRegister->takeChildren(); + QList childrenList = pItem->takeChildren(); // Remove children for (qsizetype i = 0; i < childrenList.size(); ++i) { QMdfTreeWidgetItem* item = (QMdfTreeWidgetItem*)childrenList.at(i); delete item; } childrenList.clear(); - renderRegisters(m_headRegister); + renderValues(pItem, *preg->getListValues(), true); + } + } break; + + case mdf_type_value_item: { + CMDF_Value* pvalue = (CMDF_Value*)pItem->getObject(); + if (nullptr == pvalue) { + int ret = QMessageBox::critical(this, tr("APPNAME"), tr("Internal error: Invalid firmware object")); + spdlog::error("MDF register value edit - object has nullptr"); + return; + } + CDlgMdfRegisterValue dlg(this); + dlg.initDialogData(pvalue, 0); + if (QDialog::Accepted == dlg.exec()) { + pItemHead->setExpanded(true); + QList childrenList = pItem->takeChildren(); + // Remove children + for (qsizetype i = 0; i < childrenList.size(); ++i) { + QMdfTreeWidgetItem* item = (QMdfTreeWidgetItem*)childrenList.at(i); + // qDebug() << item->text(0); + delete item; + } + childrenList.clear(); + QString str = QString("Value: %1").arg(pvalue->getName().c_str()); + pItem->setText(0, str); + renderValueInfo(pItem, pvalue); + } + } break; + + case mdf_type_value_sub_item: { + CMDF_Value* pvalue = (CMDF_Value*)pItem->getObject(); + if (nullptr == pvalue) { + int ret = QMessageBox::critical(this, tr("APPNAME"), tr("Internal error: Invalid firmware object")); + spdlog::error("MDF register value edit - object has nullptr"); + return; + } + CDlgMdfRegisterValue dlg(this); + dlg.initDialogData(pvalue, selectedIndex); + if (QDialog::Accepted == dlg.exec()) { + pItemHead->setExpanded(true); + QList childrenList = pItemHead->takeChildren(); + // Remove children + for (qsizetype i = 0; i < childrenList.size(); ++i) { + QMdfTreeWidgetItem* item = (QMdfTreeWidgetItem*)childrenList.at(i); + // qDebug() << item->text(0); + delete item; + } + childrenList.clear(); + QString str = QString("Value: %1").arg(pvalue->getName().c_str()); + pItemHead->setText(0, str); + renderValueInfo(pItemHead, pvalue); } } break; + + default: + break; } } diff --git a/src/cfrmmdf.h b/src/cfrmmdf.h index 38520cac..3476b743 100644 --- a/src/cfrmmdf.h +++ b/src/cfrmmdf.h @@ -301,9 +301,18 @@ public slots: @param parent Pointer to parent treewidget @param dequevalues Reference for std:deque holding bit infor objects + @param bParentKnown If pParent is the head of the bit definitions this should be set to true + */ + void + renderValues(QTreeWidgetItem* pParent, std::deque& dequevalues, bool bParentKnown = false); + + /*! + Render info for one value + @param pItemParent Pointer to parent item for bit + @param pvalue Object holding value info */ void - renderValueInfo(QTreeWidgetItem* pParent, std::deque& dequevalues); + renderValueInfo(QMdfTreeWidgetItem* pItemParent, CMDF_Value* pvalue); /*! Fill in register info