Block wrong formula and don't write to file.

--HG--
branch : feature
This commit is contained in:
Roman Telezhynskyi 2015-07-24 13:06:39 +03:00
parent c2c64921ab
commit 7e25a27a0c
9 changed files with 275 additions and 28 deletions

View file

@ -1,4 +1,4 @@
/************************************************************************
/************************************************************************
**
** @file tmainwindow.cpp
** @author Roman Telezhynskyi <dismine(at)gmail.com>
@ -444,11 +444,11 @@ void TMainWindow::AddCustom()
VMeasurement *meash;
if (mType == MeasurementsType::Standard)
{
meash = new VMeasurement(name, 0, 0, 0);
meash = new VMeasurement(currentRow, name, 0, 0, 0);
}
else
{
meash = new VMeasurement(data, currentRow, name, 0, "0");
meash = new VMeasurement(data, currentRow, name, 0, "0", true);
}
data->AddVariable(name, meash);
@ -507,7 +507,11 @@ void TMainWindow::ShowMData()
QTableWidgetItem *nameField = ui->tableWidget->item(ui->tableWidget->currentRow(), 0);
QSharedPointer<VMeasurement> meash = data->GetVariable<VMeasurement>(nameField->text());
ui->lineEditName->blockSignals(true);
ui->lineEditName->setText(ClearCustomName(meash->GetName()));
ui->lineEditName->blockSignals(false);
ui->plainTextEditDescription->blockSignals(true);
if (meash->IsCustom())
{
ui->plainTextEditDescription->setPlainText(meash->GetDescription());
@ -517,19 +521,44 @@ void TMainWindow::ShowMData()
//Show from known description
ui->plainTextEditDescription->setPlainText("");
}
ui->plainTextEditDescription->blockSignals(false);
if (mType == MeasurementsType::Standard)
{
ui->labelCalculatedValue->blockSignals(true);
ui->spinBoxBaseValue->blockSignals(true);
ui->spinBoxInSizes->blockSignals(true);
ui->spinBoxInHeights->blockSignals(true);
ui->labelCalculatedValue->setText(QString().setNum(data->GetTableValue(nameField->text(), mType)));
ui->spinBoxBaseValue->setValue(static_cast<int>(meash->GetBase()));
ui->spinBoxInSizes->setValue(static_cast<int>(meash->GetKsize()));
ui->spinBoxInHeights->setValue(static_cast<int>(meash->GetKheight()));
ui->labelCalculatedValue->blockSignals(false);
ui->spinBoxBaseValue->blockSignals(false);
ui->spinBoxInSizes->blockSignals(false);
ui->spinBoxInHeights->blockSignals(false);
}
else
{
this->formulaBaseHeight = ui->plainTextEditFormula->height();
EvalFormula(meash->GetFormula(), meash->GetData(), ui->labelCalculatedValue);
ui->plainTextEditFormula->setPlainText(qApp->TrVars()->FormulaToUser(meash->GetFormula()));
ui->plainTextEditFormula->blockSignals(true);
QString formula;
try
{
formula = qApp->TrVars()->FormulaToUser(meash->GetFormula());
}
catch (qmu::QmuParserError &e)
{
Q_UNUSED(e);
formula = meash->GetFormula();
}
ui->plainTextEditFormula->setPlainText(formula);
ui->plainTextEditFormula->blockSignals(false);
}
if (m->ReadOnly())
@ -540,10 +569,15 @@ void TMainWindow::ShowMData()
{
MFields(true);
if (not meash->IsCustom())
if (meash->IsCustom())
{
ui->plainTextEditDescription->setEnabled(false);
ui->lineEditName->setEnabled(false);
ui->plainTextEditDescription->setReadOnly(false);
ui->lineEditName->setReadOnly(false);
}
else
{
ui->plainTextEditDescription->setReadOnly(false);
ui->lineEditName->setReadOnly(false);
}
}
}
@ -601,10 +635,12 @@ void TMainWindow::SaveMName()
MeasurementsWasSaved(false);
RefreshData();
ui->tableWidget->blockSignals(true);
ui->tableWidget->selectRow(row);
ui->tableWidget->resizeColumnsToContents();
ui->tableWidget->resizeRowsToContents();
ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
ui->tableWidget->blockSignals(false);
}
else
{
@ -623,16 +659,56 @@ void TMainWindow::SaveMValue()
}
QTableWidgetItem *nameField = ui->tableWidget->item(ui->tableWidget->currentRow(), 0);
m->SetMValue(nameField->text(), ui->plainTextEditFormula->toPlainText());
// Replace line return character with spaces for calc if exist
QString text = ui->plainTextEditFormula->toPlainText();
text.replace("\n", " ");
QTableWidgetItem *formulaField = ui->tableWidget->item(ui->tableWidget->currentRow(), 2);
if (formulaField->text() == text)
{
return;
}
if (text.isEmpty())
{
const QString postfix = VDomDocument::UnitsToStr(mUnit);//Show unit in dialog lable (cm, mm or inch)
ui->labelCalculatedValue->setText(tr("Error") + " (" + postfix + "). " + tr("Empty field."));
return;
}
QString formula;
try
{
// Translate to internal look.
formula = qApp->TrVars()->FormulaFromUser(text, true);
QSharedPointer<VMeasurement> meash = data->GetVariable<VMeasurement>(nameField->text());
EvalFormula(formula, meash->GetData(), ui->labelCalculatedValue);
}
catch (qmu::QmuParserError &e)
{
const QString postfix = VDomDocument::UnitsToStr(mUnit);//Show unit in dialog lable (cm, mm or inch)
ui->labelCalculatedValue->setText(tr("Error") + " (" + postfix + "). " +
tr("Parser error: %1").arg(e.GetMsg()));
return;
}
m->SetMValue(nameField->text(), formula);
MeasurementsWasSaved(false);
const QTextCursor cursor = ui->plainTextEditFormula->textCursor();
RefreshData();
ui->tableWidget->blockSignals(true);
ui->tableWidget->selectRow(row);
ui->tableWidget->resizeColumnsToContents();
ui->tableWidget->resizeRowsToContents();
ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
ui->tableWidget->blockSignals(false);
ui->plainTextEditFormula->setTextCursor(cursor);
}
//---------------------------------------------------------------------------------------------------------------------
@ -719,12 +795,18 @@ void TMainWindow::SaveMDescription()
MeasurementsWasSaved(false);
const QTextCursor cursor = ui->plainTextEditDescription->textCursor();
RefreshData();
ui->tableWidget->blockSignals(true);
ui->tableWidget->selectRow(row);
ui->tableWidget->resizeColumnsToContents();
ui->tableWidget->resizeRowsToContents();
ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
ui->tableWidget->blockSignals(false);
ui->plainTextEditDescription->setTextCursor(cursor);
}
//---------------------------------------------------------------------------------------------------------------------
@ -863,7 +945,9 @@ void TMainWindow::InitWindow()
connect(ui->plainTextEditNotes, &QPlainTextEdit::textChanged, this, &TMainWindow::SaveNotes);
connect(ui->pushButtonGrow, &QPushButton::clicked, this, &TMainWindow::DeployFormula);
connect(ui->plainTextEditFormula, &QPlainTextEdit::textChanged, this, &TMainWindow::SaveMValue);
this->formulaBaseHeight = ui->plainTextEditFormula->height();
connect(ui->plainTextEditFormula, &QPlainTextEdit::textChanged, this, &TMainWindow::SaveMValue,
Qt::UniqueConnection);
}
ui->actionAddCustom->setEnabled(true);
@ -995,7 +1079,7 @@ bool TMainWindow::MaybeSave()
}
//---------------------------------------------------------------------------------------------------------------------
void TMainWindow::AddCell(const QString &text, int row, int column)
void TMainWindow::AddCell(const QString &text, int row, int column, bool ok)
{
QTableWidgetItem *item = new QTableWidgetItem(text);
item->setTextAlignment(Qt::AlignHCenter | Qt::AlignVCenter);
@ -1005,6 +1089,13 @@ void TMainWindow::AddCell(const QString &text, int row, int column)
flags &= ~(Qt::ItemIsEditable); // reset/clear the flag
item->setFlags(flags);
if (not ok)
{
QBrush brush = item->foreground();
brush.setColor(Qt::red);
item->setForeground(brush);
}
ui->tableWidget->setItem(row, column, item);
}
@ -1051,7 +1142,68 @@ void TMainWindow::SetDefaultSize(int value)
//---------------------------------------------------------------------------------------------------------------------
void TMainWindow::RefreshData()
{
data->ClearVariables(VarType::Measurement);
m->ReadMeasurements();
RefreshTable();
}
//---------------------------------------------------------------------------------------------------------------------
void TMainWindow::RefreshTable()
{
ui->tableWidget->blockSignals(true);
ui->tableWidget->clearContents();
const QMap<QString, QSharedPointer<VMeasurement> > table = data->DataMeasurements();
QMap<int, QSharedPointer<VMeasurement> > orderedTable;
QMap<QString, QSharedPointer<VMeasurement> >::const_iterator iterMap;
for (iterMap = table.constBegin(); iterMap != table.constEnd(); ++iterMap)
{
QSharedPointer<VMeasurement> meash = iterMap.value();
orderedTable.insert(meash->Index(), meash);
}
qint32 currentRow = -1;
QMap<int, QSharedPointer<VMeasurement> >::const_iterator iMap;
ui->tableWidget->setRowCount ( orderedTable.size() );
for (iMap = orderedTable.constBegin(); iMap != orderedTable.constEnd(); ++iMap)
{
QSharedPointer<VMeasurement> meash = iMap.value();
currentRow++;
if (mType == MeasurementsType::Individual)
{
AddCell(meash->GetName(), currentRow, 0); // name
AddCell(QString().setNum(*meash->GetValue()), currentRow, 1, meash->IsFormulaOk()); // calculated value
QString formula;
try
{
formula = qApp->TrVars()->FormulaToUser(meash->GetFormula());
}
catch (qmu::QmuParserError &e)
{
Q_UNUSED(e);
formula = meash->GetFormula();
}
AddCell(formula, currentRow, 2); // formula
}
else
{
AddCell(meash->GetName(), currentRow, 0); // name
AddCell(QString().setNum(data->GetTableValue(meash->GetName(), mType)), currentRow, 1,
meash->IsFormulaOk()); // calculated value
AddCell(QString().setNum(meash->GetBase()), currentRow, 3); // base value
AddCell(QString().setNum(meash->GetKsize()), currentRow, 4); // in sizes
AddCell(QString().setNum(meash->GetKheight()), currentRow, 5); // in heights
}
}
ui->tableWidget->resizeColumnsToContents();
ui->tableWidget->resizeRowsToContents();
ui->tableWidget->horizontalHeader()->setStretchLastSection(true);
ui->tableWidget->blockSignals(false);
}
//---------------------------------------------------------------------------------------------------------------------

View file

@ -40,6 +40,7 @@ namespace Ui
}
class QComboBox;
class QTableWidgetItem;
class TMainWindow : public QMainWindow
{
@ -117,13 +118,14 @@ private:
bool MaybeSave();
void AddCell(const QString &text, int row, int column);
void AddCell(const QString &text, int row, int column, bool ok = true);
QComboBox *SetGradationList(const QString &label, const QStringList &list);
void SetDefaultHeight(int value);
void SetDefaultSize(int value);
void RefreshData();
void RefreshTable();
void Controls();
void MFields(bool enabled);

View file

@ -70,7 +70,7 @@ void VIndividualMeasurements::ReadMeasurement(const QDomElement &domElement, con
{
qreal value = GetParametrDouble(domElement, AttrValue, "0.0");
value = UnitConvertor(value, MUnit(), qApp->patternUnit());
data->AddVariable(tag, new VMeasurement(data, 0, tag, value, qApp->TrVars()->GuiText(tag),
data->AddVariable(tag, new VMeasurement(data, 0, tag, value, "", true, qApp->TrVars()->GuiText(tag),
qApp->TrVars()->Description(tag), tag));
}

View file

@ -116,7 +116,7 @@ void VStandardMeasurements::ReadMeasurement(const QDomElement &domElement, const
qWarning()<<"Standard table can't use inch unit.";
}
data->AddVariable(tag, new VMeasurement(tag, value, size_increase, height_increase,
data->AddVariable(tag, new VMeasurement(0, tag, value, size_increase, height_increase,
qApp->TrVars()->GuiText(tag), qApp->TrVars()->Description(tag), tag));
}

View file

@ -29,6 +29,8 @@
#include "vmeasurements.h"
#include "../ifc/xml/vvstconverter.h"
#include "../ifc/xml/vvitconverter.h"
#include "../ifc/exception/vexceptionemptyparameter.h"
#include "../vpatterndb/calculator.h"
const QString VMeasurements::TagVST = QStringLiteral("vst");
const QString VMeasurements::TagVIT = QStringLiteral("vit");
@ -157,6 +159,46 @@ void VMeasurements::MoveDown(const QString &name)
}
}
//---------------------------------------------------------------------------------------------------------------------
void VMeasurements::ReadMeasurements() const
{
const QDomNodeList list = elementsByTagName(TagMeasurement);
for (int i=0; i < list.size(); ++i)
{
const QDomElement dom = list.at(i).toElement();
const QString name = GetParametrString(dom, AttrName);
QString description;
try
{
description = GetParametrString(dom, AttrDescription);
}
catch (VExceptionEmptyParameter &e)
{
Q_UNUSED(e)
}
VMeasurement *meash;
if (type == MeasurementsType::Standard)
{
const quint32 base = GetParametrUInt(dom, AttrBase, "0");
const quint32 ksize = GetParametrUInt(dom, AttrSizeIncrease, "0");
const quint32 kheight = GetParametrUInt(dom, AttrHeightIncrease, "0");
meash = new VMeasurement(i, name, base, ksize, kheight, "", description);
}
else
{
QString formula = GetParametrString(dom, AttrValue, "0");
bool ok = false;
const qreal value = EvalFormula(data, formula, &ok);
meash = new VMeasurement(data, i, name, value, formula, ok, "", description);
}
data->AddVariable(name, meash);
}
}
//---------------------------------------------------------------------------------------------------------------------
MeasurementsType VMeasurements::Type() const
{
@ -549,3 +591,33 @@ QDomElement VMeasurements::FindM(const QString &name) const
return QDomElement();
}
//---------------------------------------------------------------------------------------------------------------------
qreal VMeasurements::EvalFormula(VContainer *data, const QString &formula, bool *ok) const
{
if (formula.isEmpty())
{
*ok = true;
return 0;
}
else
{
try
{
// Replace line return character with spaces for calc if exist
QString f = formula;
f.replace("\n", " ");
Calculator *cal = new Calculator(data, type);
const qreal result = cal->EvalFormula(f);
delete cal;
*ok = true;
return result;
}
catch (qmu::QmuParserError &e)
{
*ok = false;
return 0;
}
}
}

View file

@ -49,6 +49,8 @@ public:
void MoveUp(const QString &name);
void MoveDown(const QString &name);
void ReadMeasurements() const;
MeasurementsType Type() const;
Unit MUnit() const;
int BaseSize() const;
@ -126,6 +128,8 @@ private:
QDomElement MakeEmpty(const QString &name);
QDomElement FindM(const QString &name) const;
qreal EvalFormula(VContainer *data, const QString &formula, bool *ok) const;
};
#endif // VMEASUREMENTS_H

View file

@ -40,10 +40,10 @@
* @param description measurement full description
* @param tagName measurement's tag name in file
*/
VMeasurement::VMeasurement(const QString &name, const qreal &base, const qreal &ksize,
VMeasurement::VMeasurement(quint32 index, const QString &name, const qreal &base, const qreal &ksize,
const qreal &kheight,
const QString &gui_text, const QString &description, const QString &tagName)
:VVariable(name, base, ksize, kheight, description), d(new VMeasurementData(gui_text, tagName))
:VVariable(name, base, ksize, kheight, description), d(new VMeasurementData(index, gui_text, tagName))
{
SetType(VarType::Measurement);
}
@ -57,10 +57,10 @@ VMeasurement::VMeasurement(const QString &name, const qreal &base, const qreal &
* @param description measurement full description
* @param tagName measurement's tag name in file
*/
VMeasurement::VMeasurement(VContainer *data, quint32 id, const QString &name, const qreal &base,
const QString &formula, const QString &gui_text, const QString &description,
VMeasurement::VMeasurement(VContainer *data, quint32 index, const QString &name, const qreal &base,
const QString &formula, bool ok, const QString &gui_text, const QString &description,
const QString &tagName)
:VVariable(name, base, description), d(new VMeasurementData(data, id, formula, gui_text, tagName))
:VVariable(name, base, description), d(new VMeasurementData(data, index, formula, ok, gui_text, tagName))
{
SetType(VarType::Measurement);
}
@ -228,6 +228,18 @@ bool VMeasurement::IsCustom() const
}
}
//---------------------------------------------------------------------------------------------------------------------
int VMeasurement::Index() const
{
return d->index;
}
//---------------------------------------------------------------------------------------------------------------------
bool VMeasurement::IsFormulaOk() const
{
return d->formulaOk;
}
//---------------------------------------------------------------------------------------------------------------------
VContainer *VMeasurement::GetData()
{

View file

@ -43,11 +43,11 @@ class VContainer;
class VMeasurement :public VVariable
{
public:
VMeasurement(const QString &name, const qreal &base, const qreal &ksize,
VMeasurement(quint32 index, const QString &name, const qreal &base, const qreal &ksize,
const qreal &kheight, const QString &gui_text = QString(), const QString &description = QString(),
const QString &TagName = QString());
VMeasurement(VContainer *data, quint32 id, const QString &name, const qreal &base, const QString &formula,
const QString &gui_text = QString(), const QString &description = QString(),
VMeasurement(VContainer *data, quint32 index, const QString &name, const qreal &base, const QString &formula,
bool ok, const QString &gui_text = QString(), const QString &description = QString(),
const QString &TagName = QString());
VMeasurement(const VMeasurement &m);
VMeasurement &operator=(const VMeasurement &m);
@ -62,6 +62,9 @@ public:
bool IsCustom() const;
int Index() const;
bool IsFormulaOk() const;
VContainer *GetData();
static QStringList ListHeights(QMap<GHeights, bool> heights, Unit patternUnit);

View file

@ -42,27 +42,29 @@ class VMeasurementData : public QSharedData
{
public:
VMeasurementData(const QString &gui_text, const QString &tagName)
:data(VContainer(nullptr, nullptr)), id(0), gui_text(gui_text), _tagName(tagName)
VMeasurementData(quint32 index, const QString &gui_text, const QString &tagName)
:data(VContainer(nullptr, nullptr)), index(index), gui_text(gui_text), _tagName(tagName), formulaOk(true)
{}
VMeasurementData(VContainer *data, quint32 id, const QString &formula, const QString &gui_text,
VMeasurementData(VContainer *data, quint32 index, const QString &formula, bool ok, const QString &gui_text,
const QString &tagName)
:data(*data), id(id), formula(formula), gui_text(gui_text), _tagName(tagName)
:data(*data), index(index), formula(formula), gui_text(gui_text), _tagName(tagName), formulaOk(ok)
{}
VMeasurementData(const VMeasurementData &m)
:QSharedData(m), data(m.data), id(m.id), formula(m.formula), gui_text(m.gui_text), _tagName(m._tagName)
:QSharedData(m), data(m.data), index(m.index), formula(m.formula), gui_text(m.gui_text), _tagName(m._tagName),
formulaOk(m.formulaOk)
{}
virtual ~VMeasurementData();
/** @brief description description measurement */
VContainer data;
quint32 id;
quint32 index;
QString formula;
QString gui_text;
QString _tagName;
bool formulaOk;
};
VMeasurementData::~VMeasurementData()