diff --git a/ChangeLog.txt b/ChangeLog.txt index ded5ebd21..95bd28892 100644 --- a/ChangeLog.txt +++ b/ChangeLog.txt @@ -29,6 +29,7 @@ - [#768] New feature. Custom curve approximation scale. - [#759] Add place label tool. - [#771] Improve tool Point at intersection of arc and line. +- [#772] New tool Duplicate detail. # Version 0.5.1 - [#683] Tool Seam allowance's dialog is off screen on small resolutions. diff --git a/src/app/valentina/core/vtooloptionspropertybrowser.cpp b/src/app/valentina/core/vtooloptionspropertybrowser.cpp index 0e6bfe0c7..f4bfc1d12 100644 --- a/src/app/valentina/core/vtooloptionspropertybrowser.cpp +++ b/src/app/valentina/core/vtooloptionspropertybrowser.cpp @@ -78,7 +78,7 @@ void VToolOptionsPropertyBrowser::ClearPropertyBrowser() void VToolOptionsPropertyBrowser::ShowItemOptions(QGraphicsItem *item) { // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were used in switch."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were used in switch."); switch (item->type()) { @@ -205,7 +205,7 @@ void VToolOptionsPropertyBrowser::UpdateOptions() } // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were used in switch."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were used in switch."); switch (currentItem->type()) { @@ -350,7 +350,7 @@ void VToolOptionsPropertyBrowser::userChangedData(VPE::VProperty *property) } // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were used in switch."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were used in switch."); switch (currentItem->type()) { diff --git a/src/app/valentina/dialogs/dialoghistory.cpp b/src/app/valentina/dialogs/dialoghistory.cpp index aa01d7f64..3a767a7cf 100644 --- a/src/app/valentina/dialogs/dialoghistory.cpp +++ b/src/app/valentina/dialogs/dialoghistory.cpp @@ -212,7 +212,7 @@ QT_WARNING_DISABLE_GCC("-Wswitch-default") QString DialogHistory::Record(const VToolRecord &tool) { // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were used in history."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were used in history."); const QDomElement domElem = doc->elementById(tool.getId()); if (domElem.isElement() == false) @@ -408,6 +408,7 @@ QString DialogHistory::Record(const VToolRecord &tool) case Tool::Pin: case Tool::PlaceLabel: case Tool::InsertNode: + case Tool::DuplicateDetail: return QString(); } } diff --git a/src/app/valentina/mainwindow.cpp b/src/app/valentina/mainwindow.cpp index ba1faff63..cae1e9574 100644 --- a/src/app/valentina/mainwindow.cpp +++ b/src/app/valentina/mainwindow.cpp @@ -260,7 +260,7 @@ void MainWindow::AddPP(const QString &PPName) comboBoxDraws->blockSignals(true); comboBoxDraws->addItem(PPName); - pattern->ClearGObjects(); + pattern->ClearCalculationGObjects(); //Create single point ui->view->itemClicked(nullptr);//hide options previous tool const QString label = doc->GenerateLabel(LabelType::NewPatternPiece); @@ -613,7 +613,7 @@ void MainWindow::SetToolButton(bool checked, Tool t, const QString &cursor, cons dialogTool = QSharedPointer(new Dialog(pattern, 0, this)); // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Check if need to extend."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Check if need to extend."); switch(t) { @@ -1107,8 +1107,31 @@ void MainWindow::ToolUnionDetails(bool checked) */ void MainWindow::ClosedDialogUnionDetails(int result) { - ClosedDialog(result); - doc->LiteParseTree(Document::LiteParse); + ClosedDialog(result);// Avoid error: Template function as signal or slot +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindow::ToolDuplicateDetail(bool checked) +{ + ToolSelectDetail(); + SetToolButton(checked, Tool::DuplicateDetail, ":/cursor/duplicate_detail_cursor.png", + tr("Select detail"), &MainWindow::ClosedDialogDuplicateDetail); +} + +//--------------------------------------------------------------------------------------------------------------------- +void MainWindow::ClosedDialogDuplicateDetail(int result) +{ + SCASSERT(not dialogTool.isNull()) + if (result == QDialog::Accepted) + { + VMainGraphicsScene *scene = qobject_cast(currentScene); + SCASSERT(scene != nullptr) + + QGraphicsItem *tool = dynamic_cast(VToolSeamAllowance::Duplicate(dialogTool, scene, doc)); + // Do not check for nullptr! See issue #719. + ui->view->itemClicked(tool); + } + ArrowTool(); } //--------------------------------------------------------------------------------------------------------------------- @@ -1985,7 +2008,7 @@ void MainWindow::InitToolButtons() } // This check helps to find missed tools - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Check if all tools were connected."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Check if all tools were connected."); connect(ui->toolButtonEndLine, &QToolButton::clicked, this, &MainWindow::ToolEndLine); connect(ui->toolButtonLine, &QToolButton::clicked, this, &MainWindow::ToolLine); @@ -2008,6 +2031,7 @@ void MainWindow::InitToolButtons() connect(ui->toolButtonSplineCutPoint, &QToolButton::clicked, this, &MainWindow::ToolCutSpline); connect(ui->toolButtonSplinePathCutPoint, &QToolButton::clicked, this, &MainWindow::ToolCutSplinePath); connect(ui->toolButtonUnionDetails, &QToolButton::clicked, this, &MainWindow::ToolUnionDetails); + connect(ui->toolButtonDuplicateDetail, &QToolButton::clicked, this, &MainWindow::ToolDuplicateDetail); connect(ui->toolButtonArcCutPoint, &QToolButton::clicked, this, &MainWindow::ToolCutArc); connect(ui->toolButtonLineIntersectAxis, &QToolButton::clicked, this, &MainWindow::ToolLineIntersectAxis); connect(ui->toolButtonCurveIntersectAxis, &QToolButton::clicked, this, &MainWindow::ToolCurveIntersectAxis); @@ -2062,7 +2086,7 @@ QT_WARNING_DISABLE_GCC("-Wswitch-default") void MainWindow::CancelTool() { // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were handled."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were handled."); qCDebug(vMainWindow, "Canceling tool."); dialogTool.clear(); @@ -2172,6 +2196,9 @@ void MainWindow::CancelTool() case Tool::UnionDetails: ui->toolButtonUnionDetails->setChecked(false); break; + case Tool::DuplicateDetail: + ui->toolButtonDuplicateDetail->setChecked(false); + break; case Tool::CutArc: ui->toolButtonArcCutPoint->setChecked(false); break; @@ -3424,7 +3451,7 @@ QT_WARNING_DISABLE_GCC("-Wswitch-default") QT_WARNING_POP // This check helps to find missed tools - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were handled."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were handled."); //Drawing Tools ui->toolButtonEndLine->setEnabled(drawTools); @@ -3480,6 +3507,7 @@ QT_WARNING_POP //Modeling Tools ui->toolButtonUnionDetails->setEnabled(modelingTools); ui->toolButtonDetailExportAs->setEnabled(modelingTools); + ui->toolButtonDuplicateDetail->setEnabled(modelingTools); //Layout tools ui->toolButtonLayoutSettings->setEnabled(layoutTools); @@ -3752,7 +3780,7 @@ QT_WARNING_DISABLE_GCC("-Wswitch-default") void MainWindow::LastUsedTool() { // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were handled."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were handled."); if (currentTool == lastUsedTool) { @@ -3875,6 +3903,10 @@ void MainWindow::LastUsedTool() ui->toolButtonUnionDetails->setChecked(true); ToolUnionDetails(true); break; + case Tool::DuplicateDetail: + ui->toolButtonDuplicateDetail->setChecked(true); + ToolDuplicateDetail(true); + break; case Tool::CutArc: ui->toolButtonArcCutPoint->setChecked(true); ToolCutArc(true); diff --git a/src/app/valentina/mainwindow.h b/src/app/valentina/mainwindow.h index 47e6a76a0..386f04058 100644 --- a/src/app/valentina/mainwindow.h +++ b/src/app/valentina/mainwindow.h @@ -150,6 +150,7 @@ private slots: void ToolTriangle(bool checked); void ToolPointOfIntersection(bool checked); void ToolUnionDetails(bool checked); + void ToolDuplicateDetail(bool checked); void ToolGroup(bool checked); void ToolRotation(bool checked); void ToolFlippingByLine(bool checked); @@ -178,6 +179,7 @@ private slots: void Open(); void ClosedDialogUnionDetails(int result); + void ClosedDialogDuplicateDetail(int result); void ClosedDialogGroup(int result); void ClosedDialogPiecePath(int result); void ClosedDialogPin(int result); diff --git a/src/app/valentina/mainwindow.ui b/src/app/valentina/mainwindow.ui index b81b324b6..f2ae0f667 100644 --- a/src/app/valentina/mainwindow.ui +++ b/src/app/valentina/mainwindow.ui @@ -48,7 +48,7 @@ Export details skiping the Layout stage - 7 + 6 @@ -1550,6 +1550,32 @@ + + + + false + + + Duplicate detail tool + + + ... + + + + :/toolicon/32x32/duplicate_detail.png:/toolicon/32x32/duplicate_detail.png + + + + 32 + 32 + + + + true + + + diff --git a/src/app/valentina/share/resources/cursor.qrc b/src/app/valentina/share/resources/cursor.qrc index 1ef61e19d..52afe1836 100644 --- a/src/app/valentina/share/resources/cursor.qrc +++ b/src/app/valentina/share/resources/cursor.qrc @@ -86,5 +86,7 @@ cursor/insert_node_cursor@2x.png cursor/place_label_cursor@2x.png cursor/place_label_cursor.png + cursor/duplicate_detail_cursor.png + cursor/duplicate_detail_cursor@2x.png diff --git a/src/app/valentina/share/resources/cursor/duplicate_detail_cursor.png b/src/app/valentina/share/resources/cursor/duplicate_detail_cursor.png new file mode 100644 index 000000000..9ce8097ec Binary files /dev/null and b/src/app/valentina/share/resources/cursor/duplicate_detail_cursor.png differ diff --git a/src/app/valentina/share/resources/cursor/duplicate_detail_cursor@2x.png b/src/app/valentina/share/resources/cursor/duplicate_detail_cursor@2x.png new file mode 100644 index 000000000..8bc268962 Binary files /dev/null and b/src/app/valentina/share/resources/cursor/duplicate_detail_cursor@2x.png differ diff --git a/src/app/valentina/share/resources/toolicon.qrc b/src/app/valentina/share/resources/toolicon.qrc index 85d04ac5c..a7b969906 100644 --- a/src/app/valentina/share/resources/toolicon.qrc +++ b/src/app/valentina/share/resources/toolicon.qrc @@ -84,5 +84,7 @@ toolicon/32x32/insert_node@2x.png toolicon/32x32/place_label@2x.png toolicon/32x32/place_label.png + toolicon/32x32/duplicate_detail.png + toolicon/32x32/duplicate_detail@2x.png diff --git a/src/app/valentina/share/resources/toolicon/32x32/duplicate_detail.png b/src/app/valentina/share/resources/toolicon/32x32/duplicate_detail.png new file mode 100644 index 000000000..ac021c364 Binary files /dev/null and b/src/app/valentina/share/resources/toolicon/32x32/duplicate_detail.png differ diff --git a/src/app/valentina/share/resources/toolicon/32x32/duplicate_detail@2x.png b/src/app/valentina/share/resources/toolicon/32x32/duplicate_detail@2x.png new file mode 100644 index 000000000..a4fc05ae0 Binary files /dev/null and b/src/app/valentina/share/resources/toolicon/32x32/duplicate_detail@2x.png differ diff --git a/src/app/valentina/share/resources/toolicon/svg/duplicate_detail.svg b/src/app/valentina/share/resources/toolicon/svg/duplicate_detail.svg new file mode 100644 index 000000000..585975a52 --- /dev/null +++ b/src/app/valentina/share/resources/toolicon/svg/duplicate_detail.svg @@ -0,0 +1,194 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + image/svg+xml + + + + + + + + + + + + + + + + diff --git a/src/app/valentina/xml/vpattern.cpp b/src/app/valentina/xml/vpattern.cpp index 4f6387df2..1a224c2e6 100644 --- a/src/app/valentina/xml/vpattern.cpp +++ b/src/app/valentina/xml/vpattern.cpp @@ -4166,7 +4166,7 @@ QT_WARNING_DISABLE_GCC("-Wswitch-default") QRectF VPattern::ActiveDrawBoundingRect() const { // This check helps to find missed tools in the switch - Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54, "Not all tools were used."); + Q_STATIC_ASSERT_X(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55, "Not all tools were used."); QRectF rec; @@ -4247,6 +4247,7 @@ QRectF VPattern::ActiveDrawBoundingRect() const case Tool::Pin: case Tool::InsertNode: case Tool::PlaceLabel: + case Tool::DuplicateDetail: break; } } diff --git a/src/libs/ifc/xml/vabstractpattern.cpp b/src/libs/ifc/xml/vabstractpattern.cpp index 170fdf218..86d190725 100644 --- a/src/libs/ifc/xml/vabstractpattern.cpp +++ b/src/libs/ifc/xml/vabstractpattern.cpp @@ -1771,7 +1771,7 @@ QVector VAbstractPattern::ListPointExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment a number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(TagPoint); @@ -1799,7 +1799,7 @@ QVector VAbstractPattern::ListArcExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(TagArc); @@ -1823,7 +1823,7 @@ QVector VAbstractPattern::ListElArcExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(TagElArc); @@ -1856,7 +1856,7 @@ QVector VAbstractPattern::ListPathPointExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(AttrPathPoint); @@ -1894,7 +1894,7 @@ QVector VAbstractPattern::ListOperationExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(TagOperation); @@ -1916,7 +1916,7 @@ QVector VAbstractPattern::ListNodesExpressions(const QDomElement // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; @@ -1939,7 +1939,7 @@ QVector VAbstractPattern::ListPathExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(TagPath); @@ -1977,7 +1977,7 @@ QVector VAbstractPattern::ListPieceExpressions() const // Check if new tool doesn't bring new attribute with a formula. // If no just increment number. // If new tool bring absolutely new type and has formula(s) create new method to cover it. - Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 54); + Q_STATIC_ASSERT(static_cast(Tool::LAST_ONE_DO_NOT_USE) == 55); QVector expressions; const QDomNodeList list = elementsByTagName(TagDetail); @@ -2420,3 +2420,21 @@ void VAbstractPattern::SetGroupVisivility(quint32 id, bool visible) qDebug("Can't get group by id = %u.", id); } } + +//--------------------------------------------------------------------------------------------------------------------- +QString VAbstractPattern::PieceDrawName(quint32 id) +{ + const QDomElement detail = elementById(id, VAbstractPattern::TagDetail); + if (detail.isNull()) + { + return QString(); + } + + const QDomElement draw = detail.parentNode().parentNode().toElement(); + if (draw.isNull() || not draw.hasAttribute(VAbstractPattern::AttrName)) + { + return QString(); + } + + return draw.attribute(VAbstractPattern::AttrName); +} diff --git a/src/libs/ifc/xml/vabstractpattern.h b/src/libs/ifc/xml/vabstractpattern.h index 920837731..d2ccf0d16 100644 --- a/src/libs/ifc/xml/vabstractpattern.h +++ b/src/libs/ifc/xml/vabstractpattern.h @@ -198,6 +198,8 @@ public: bool GetGroupVisivility(quint32 id); void SetGroupVisivility(quint32 id, bool visible); + QString PieceDrawName(quint32 id); + static const QString TagPattern; static const QString TagCalculation; static const QString TagModeling; diff --git a/src/libs/vmisc/def.h b/src/libs/vmisc/def.h index 4f67cd982..899ae9f63 100644 --- a/src/libs/vmisc/def.h +++ b/src/libs/vmisc/def.h @@ -171,6 +171,7 @@ enum class Tool : ToolVisHolderType Pin, InsertNode, PlaceLabel, + DuplicateDetail, LAST_ONE_DO_NOT_USE //add new stuffs above this, this constant must be last and never used }; @@ -222,6 +223,7 @@ enum class Vis : ToolVisHolderType ToolPiecePath, ToolSpecialPoint, ToolPlaceLabel, + ToolDuplicateDetail, PieceSpecialPoints, NoBrush, CurvePathItem, diff --git a/src/libs/vpatterndb/vcontainer.cpp b/src/libs/vpatterndb/vcontainer.cpp index 10caece95..1e2820220 100644 --- a/src/libs/vpatterndb/vcontainer.cpp +++ b/src/libs/vpatterndb/vcontainer.cpp @@ -103,10 +103,7 @@ VContainer::VContainer(const VContainer &data) //--------------------------------------------------------------------------------------------------------------------- VContainer::~VContainer() -{ - ClearGObjects(); - ClearVariables(); -} +{} //--------------------------------------------------------------------------------------------------------------------- /** @@ -115,9 +112,20 @@ VContainer::~VContainer() * @return point */ // cppcheck-suppress unusedFunction -const QSharedPointer VContainer::GetGObject(quint32 id)const +const QSharedPointer VContainer::GetGObject(quint32 id) const { - return GetObject(d->gObjects, id); + if (d->calculationObjects.contains(id)) + { + return d->calculationObjects.value(id); + } + else if (d->modelingObjects->contains(id)) + { + return d->modelingObjects->value(id); + } + else + { + throw VExceptionBadId(tr("Can't find object"), id); + } } //--------------------------------------------------------------------------------------------------------------------- @@ -129,26 +137,6 @@ const QSharedPointer VContainer::GetFakeGObject(quint32 id) return pointer; } -//--------------------------------------------------------------------------------------------------------------------- -/** - * @brief GetObject return object from container - * @param obj container - * @param id id of object - * @return Object - */ -template -const val VContainer::GetObject(const QHash &obj, key id) const -{ - if (obj.contains(id)) - { - return obj.value(id); - } - else - { - throw VExceptionBadId(tr("Can't find object"), id); - } -} - //--------------------------------------------------------------------------------------------------------------------- VPiece VContainer::GetPiece(quint32 id) const { @@ -192,8 +180,27 @@ quint32 VContainer::AddGObject(VGObject *obj) quint32 VContainer::AddGObject(const QSharedPointer &obj) { SCASSERT(not obj.isNull()) + + if (obj->getMode() == Draw::Layout) + { + qWarning("Can't add an object with mode 'Layout'"); + return NULL_ID; + } + uniqueNames.insert(obj->name()); - return AddObject(d->gObjects, obj); + const quint32 id = getNextId(); + obj->setId(id); + + if (obj->getMode() == Draw::Calculation) + { + d->calculationObjects.insert(id, obj); + } + else if (obj->getMode() == Draw::Modeling) + { + d->modelingObjects->insert(id, obj); + } + + return id; } //--------------------------------------------------------------------------------------------------------------------- @@ -290,33 +297,14 @@ void VContainer::ClearForFullParse() */ void VContainer::ClearGObjects() { - d->gObjects.clear(); + d->calculationObjects.clear(); + d->modelingObjects->clear(); } //--------------------------------------------------------------------------------------------------------------------- void VContainer::ClearCalculationGObjects() { - if (not d->gObjects.isEmpty()) //-V807 - { - QVector keys; - QHash >::iterator i; - for (i = d->gObjects.begin(); i != d->gObjects.end(); ++i) - { - if (i.value()->getMode() == Draw::Calculation) - { - i.value().clear(); - keys.append(i.key()); - } - } - // We can't delete objects in previous loop it will destroy the iterator. - if (not keys.isEmpty()) - { - for (int i = 0; i < keys.size(); ++i) - { - d->gObjects.remove(keys.at(i)); - } - } - } + d->calculationObjects.clear(); } //--------------------------------------------------------------------------------------------------------------------- @@ -464,23 +452,6 @@ void VContainer::RemovePiece(quint32 id) d->pieces->remove(id); } -//--------------------------------------------------------------------------------------------------------------------- -/** - * @brief AddObject add object to container - * @param obj container - * @param value object - * @return id of object in container - */ -template -quint32 VContainer::AddObject(QHash &obj, val value) -{ - SCASSERT(value != nullptr) - const quint32 id = getNextId(); - value->setId(id); - obj[id] = value; - return id; -} - //--------------------------------------------------------------------------------------------------------------------- void VContainer::UpdatePiece(quint32 id, const VPiece &detail) { @@ -678,9 +649,9 @@ qreal *VContainer::rheight() * @brief data container with datagObjects return container of gObjects * @return pointer on container of gObjects */ -const QHash > *VContainer::DataGObjects() const +const QHash > *VContainer::CalculationGObjects() const { - return &d->gObjects; + return &d->calculationObjects; } //--------------------------------------------------------------------------------------------------------------------- diff --git a/src/libs/vpatterndb/vcontainer.h b/src/libs/vpatterndb/vcontainer.h index 2837bbddd..65999883d 100644 --- a/src/libs/vpatterndb/vcontainer.h +++ b/src/libs/vpatterndb/vcontainer.h @@ -69,7 +69,8 @@ class VContainerData : public QSharedData //-V690 public: VContainerData(const VTranslateVars *trVars, const Unit *patternUnit) - : gObjects(QHash >()), + : calculationObjects(QHash >()), + modelingObjects(QSharedPointer>>::create()), variables(QHash > ()), pieces(QSharedPointer>::create()), piecePaths(QSharedPointer>::create()), @@ -79,7 +80,8 @@ public: VContainerData(const VContainerData &data) : QSharedData(data), - gObjects(data.gObjects), + calculationObjects(data.calculationObjects), + modelingObjects(data.modelingObjects), variables(data.variables), pieces(data.pieces), piecePaths(data.piecePaths), @@ -89,10 +91,8 @@ public: virtual ~VContainerData(); - /** - * @brief gObjects graphicals objects of pattern. - */ - QHash > gObjects; + QHash > calculationObjects; + QSharedPointer>> modelingObjects; /** * @brief variables container for measurements, increments, lines lengths, lines angles, arcs lengths, curve lengths @@ -184,7 +184,7 @@ public: void RemoveIncrement(const QString& name); - const QHash > *DataGObjects() const; + const QHash > *CalculationGObjects() const; const QHash *DataPieces() const; const QHash> *DataVariables() const; @@ -219,16 +219,9 @@ private: template uint qHash( const QSharedPointer &p ); - template - // cppcheck-suppress functionStatic - const val GetObject(const QHash &obj, key id) const; - template void UpdateObject(const quint32 &id, const QSharedPointer &point); - template - static quint32 AddObject(QHash &obj, val value); - template const QMap > DataVar(const VarType &type) const; }; @@ -248,25 +241,23 @@ const QSharedPointer VContainer::GeometricObject(const quint32 &id) const throw VExceptionBadId(tr("Can't find object"), id); } - QSharedPointer gObj = QSharedPointer(); - if (d->gObjects.contains(id)) + QSharedPointer gObj; + if (d->calculationObjects.contains(id)) { - gObj = d->gObjects.value(id); + gObj = d->calculationObjects.value(id); + } + else if (d->modelingObjects->contains(id)) + { + gObj = d->modelingObjects->value(id); } else { throw VExceptionBadId(tr("Can't find object"), id); } - try - { - QSharedPointer obj = qSharedPointerDynamicCast(gObj); - SCASSERT(obj.isNull() == false) - return obj; - } - catch (const std::bad_alloc &) - { - throw VExceptionBadId(tr("Can't cast object"), id); - } + + QSharedPointer obj = qSharedPointerDynamicCast(gObj); + SCASSERT(obj.isNull() == false) + return obj; } @@ -375,19 +366,39 @@ void VContainer::UpdateObject(const quint32 &id, const QSharedPointer &point) Q_ASSERT_X(id != NULL_ID, Q_FUNC_INFO, "id == 0"); //-V654 //-V712 SCASSERT(point.isNull() == false) point->setId(id); - if (d->gObjects.contains(id)) + + if (d->calculationObjects.contains(id) && point->getMode() == Draw::Calculation) { - QSharedPointer obj = qSharedPointerDynamicCast(d->gObjects.value(id)); + QSharedPointer obj = qSharedPointerDynamicCast(d->calculationObjects.value(id)); if (obj.isNull()) { throw VExceptionBadId(tr("Can't cast object"), id); } *obj = *point; } + else if (d->modelingObjects->contains(id) && point->getMode() == Draw::Modeling) + { + QSharedPointer obj = qSharedPointerDynamicCast(d->modelingObjects->value(id)); + if (obj.isNull()) + { + throw VExceptionBadId(tr("Can't cast object"), id); + } + *obj = *point; + } + else if (point->getMode() == Draw::Calculation) + { + d->calculationObjects.insert(id, point); + } + else if (point->getMode() == Draw::Modeling) + { + d->modelingObjects->insert(id, point); + } else { - d->gObjects.insert(id, point); + qWarning("Can't update an object with mode 'Layout'"); + return; } + UpdateId(id); } #endif // VCONTAINER_H diff --git a/src/libs/vtools/dialogs/dialogs.pri b/src/libs/vtools/dialogs/dialogs.pri index 9df554fc8..ddba6edce 100644 --- a/src/libs/vtools/dialogs/dialogs.pri +++ b/src/libs/vtools/dialogs/dialogs.pri @@ -47,7 +47,8 @@ HEADERS += \ $$PWD/tools/piece/dialogpin.h \ $$PWD/tools/piece/dialoginsertnode.h \ $$PWD/support/dialogeditlabel.h \ - $$PWD/tools/piece/dialogplacelabel.h + $$PWD/tools/piece/dialogplacelabel.h \ + $$PWD/tools/piece/dialogduplicatedetail.h SOURCES += \ $$PWD/tools/dialogalongline.cpp \ @@ -94,7 +95,8 @@ SOURCES += \ $$PWD/tools/piece/dialogpin.cpp \ $$PWD/tools/piece/dialoginsertnode.cpp \ $$PWD/support/dialogeditlabel.cpp \ - $$PWD/tools/piece/dialogplacelabel.cpp + $$PWD/tools/piece/dialogplacelabel.cpp \ + $$PWD/tools/piece/dialogduplicatedetail.cpp FORMS += \ $$PWD/tools/dialogalongline.ui \ @@ -146,4 +148,5 @@ FORMS += \ $$PWD/tools/piece/tabs/tabpassmarks.ui \ $$PWD/support/dialogeditlabel.ui \ $$PWD/tools/piece/dialogplacelabel.ui \ - $$PWD/tools/piece/tabs/tabplacelabels.ui + $$PWD/tools/piece/tabs/tabplacelabels.ui \ + $$PWD/tools/piece/dialogduplicatedetail.ui diff --git a/src/libs/vtools/dialogs/tooldialogs.h b/src/libs/vtools/dialogs/tooldialogs.h index 0db5a3721..58d46f9e5 100644 --- a/src/libs/vtools/dialogs/tooldialogs.h +++ b/src/libs/vtools/dialogs/tooldialogs.h @@ -70,6 +70,7 @@ #include "tools/piece/dialogpin.h" #include "tools/piece/dialoginsertnode.h" #include "tools/piece/dialogplacelabel.h" +#include "tools/piece/dialogduplicatedetail.h" #include "support/dialogeditwrongformula.h" #include "support/dialogundo.h" diff --git a/src/libs/vtools/dialogs/tools/dialogtool.cpp b/src/libs/vtools/dialogs/tools/dialogtool.cpp index 513e6709f..53f13eccc 100644 --- a/src/libs/vtools/dialogs/tools/dialogtool.cpp +++ b/src/libs/vtools/dialogs/tools/dialogtool.cpp @@ -215,7 +215,7 @@ void DialogTool::FillComboBoxSplines(QComboBox *box) const SCASSERT(box != nullptr) box->blockSignals(true); - const auto objs = data->DataGObjects(); + const auto objs = data->CalculationGObjects(); QHash >::const_iterator i; QMap list; for (i = objs->constBegin(); i != objs->constEnd(); ++i) @@ -239,7 +239,7 @@ void DialogTool::FillComboBoxSplinesPath(QComboBox *box) const SCASSERT(box != nullptr) box->blockSignals(true); - const auto objs = data->DataGObjects(); + const auto objs = data->CalculationGObjects(); QHash >::const_iterator i; QMap list; for (i = objs->constBegin(); i != objs->constEnd(); ++i) @@ -261,7 +261,7 @@ void DialogTool::FillComboBoxSplinesPath(QComboBox *box) const void DialogTool::FillComboBoxCurves(QComboBox *box) const { SCASSERT(box != nullptr) - const auto objs = data->DataGObjects(); + const auto objs = data->CalculationGObjects(); QMap list; QHash >::const_iterator i; for (i = objs->constBegin(); i != objs->constEnd(); ++i) @@ -269,12 +269,12 @@ void DialogTool::FillComboBoxCurves(QComboBox *box) const if (i.key() != toolId) { QSharedPointer obj = i.value(); - if ((obj->getType() == GOType::Arc - || obj->getType() == GOType::EllipticalArc - || obj->getType() == GOType::Spline - || obj->getType() == GOType::SplinePath - || obj->getType() == GOType::CubicBezier - || obj->getType() == GOType::CubicBezierPath) && obj->getMode() == Draw::Calculation) + if (obj->getType() == GOType::Arc + || obj->getType() == GOType::EllipticalArc + || obj->getType() == GOType::Spline + || obj->getType() == GOType::SplinePath + || obj->getType() == GOType::CubicBezier + || obj->getType() == GOType::CubicBezierPath) { PrepareList(list, i.key()); } @@ -683,8 +683,7 @@ void DialogTool::InitNodeAngles(QComboBox *box) //--------------------------------------------------------------------------------------------------------------------- bool DialogTool::IsSplinePath(const QSharedPointer &obj) const { - return (obj->getType() == GOType::SplinePath || obj->getType() == GOType::CubicBezierPath) && - obj->getMode() == Draw::Calculation; + return obj->getType() == GOType::SplinePath || obj->getType() == GOType::CubicBezierPath; } //--------------------------------------------------------------------------------------------------------------------- @@ -1010,8 +1009,7 @@ void DialogTool::PrepareList(QMap &list, quint32 id) const //--------------------------------------------------------------------------------------------------------------------- bool DialogTool::IsSpline(const QSharedPointer &obj) const { - return (obj->getType() == GOType::Spline || obj->getType() == GOType::CubicBezier) && - obj->getMode() == Draw::Calculation; + return obj->getType() == GOType::Spline || obj->getType() == GOType::CubicBezier; } //--------------------------------------------------------------------------------------------------------------------- @@ -1290,7 +1288,7 @@ void DialogTool::FillCombo(QComboBox *box, GOType gType, FillComboBox rule, cons SCASSERT(box != nullptr) box->blockSignals(true); - const QHash > *objs = data->DataGObjects(); + const QHash > *objs = data->CalculationGObjects(); QHash >::const_iterator i; QMap list; for (i = objs->constBegin(); i != objs->constEnd(); ++i) @@ -1300,7 +1298,7 @@ void DialogTool::FillCombo(QComboBox *box, GOType gType, FillComboBox rule, cons if (i.key() != toolId && i.key() != ch1 && i.key() != ch2) { QSharedPointer obj = i.value(); - if (obj->getType() == gType && obj->getMode() == Draw::Calculation) + if (obj->getType() == gType) { PrepareList(list, i.key()); } diff --git a/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.cpp b/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.cpp new file mode 100644 index 000000000..9a75421cb --- /dev/null +++ b/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.cpp @@ -0,0 +1,93 @@ +/************************************************************************ + ** + ** @file dialogduplicatedetail.cpp + ** @author Roman Telezhynskyi + ** @date 25 10, 2017 + ** + ** @brief + ** @copyright + ** This source code is part of the Valentina project, a pattern making + ** program, whose allow create and modeling patterns of clothing. + ** Copyright (C) 2017 Valentina project + ** All Rights Reserved. + ** + ** Valentina is free software: you can redistribute it and/or modify + ** it under the terms of the GNU General Public License as published by + ** the Free Software Foundation, either version 3 of the License, or + ** (at your option) any later version. + ** + ** Valentina is distributed in the hope that it will be useful, + ** but WITHOUT ANY WARRANTY; without even the implied warranty of + ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + ** GNU General Public License for more details. + ** + ** You should have received a copy of the GNU General Public License + ** along with Valentina. If not, see . + ** + *************************************************************************/ +#include "dialogduplicatedetail.h" +#include "ui_dialogduplicatedetail.h" +#include "../vwidgets/vabstractmainwindow.h" +#include "../../../visualization/path/vistoolduplicatedetail.h" + +//--------------------------------------------------------------------------------------------------------------------- +DialogDuplicateDetail::DialogDuplicateDetail(const VContainer *data, const quint32 &toolId, QWidget *parent) + : DialogTool(data, toolId, parent), + ui(new Ui::DialogDuplicateDetail), + m_idDetail(NULL_ID), + m_mx(0), + m_my(0), + m_firstRelease(false) +{ + ui->setupUi(this); + InitOkCancel(ui); + + vis = new VisToolDuplicateDetail(data); +} + +//--------------------------------------------------------------------------------------------------------------------- +DialogDuplicateDetail::~DialogDuplicateDetail() +{ + delete ui; +} + +//--------------------------------------------------------------------------------------------------------------------- +void DialogDuplicateDetail::ShowDialog(bool click) +{ + if (prepare) + { + if (click) + { + // The check need to ignore first release of mouse button. + // User should have chance to place piece. + if (not m_firstRelease) + { + m_firstRelease = true; + return; + } + + VisToolDuplicateDetail *piece = qobject_cast(vis); + SCASSERT(piece != nullptr) + + m_mx = piece->Mx(); + m_my = piece->My(); + emit ToolTip(""); + DialogAccepted(); + } + } +} + +//--------------------------------------------------------------------------------------------------------------------- +void DialogDuplicateDetail::ChosenObject(quint32 id, const SceneObject &type) +{ + if (prepare == false)// After first choose we ignore all objects + { + if (type == SceneObject::Detail && id > NULL_ID) + { + m_idDetail = id; + emit ToolTip(tr("Click to place duplicate")); + vis->VisualMode(id); + prepare = true; + } + } +} diff --git a/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.h b/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.h new file mode 100644 index 000000000..d36a0186b --- /dev/null +++ b/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.h @@ -0,0 +1,80 @@ +/************************************************************************ + ** + ** @file dialogduplicatedetail.h + ** @author Roman Telezhynskyi + ** @date 25 10, 2017 + ** + ** @brief + ** @copyright + ** This source code is part of the Valentina project, a pattern making + ** program, whose allow create and modeling patterns of clothing. + ** Copyright (C) 2017 Valentina project + ** All Rights Reserved. + ** + ** Valentina is free software: you can redistribute it and/or modify + ** it under the terms of the GNU General Public License as published by + ** the Free Software Foundation, either version 3 of the License, or + ** (at your option) any later version. + ** + ** Valentina is distributed in the hope that it will be useful, + ** but WITHOUT ANY WARRANTY; without even the implied warranty of + ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + ** GNU General Public License for more details. + ** + ** You should have received a copy of the GNU General Public License + ** along with Valentina. If not, see . + ** + *************************************************************************/ +#ifndef DIALOGDUPLICATEDETAIL_H +#define DIALOGDUPLICATEDETAIL_H + +#include "../dialogtool.h" + +namespace Ui +{ + class DialogDuplicateDetail; +} + +class DialogDuplicateDetail : public DialogTool +{ + Q_OBJECT + +public: + explicit DialogDuplicateDetail(const VContainer *data, const quint32 &toolId, QWidget *parent = nullptr); + virtual ~DialogDuplicateDetail(); + + quint32 Duplicate() const; + qreal MoveDuplicateX() const; + qreal MoveDuplicateY() const; + + virtual void ShowDialog(bool click) Q_DECL_OVERRIDE; +public slots: + virtual void ChosenObject(quint32 id, const SceneObject &type) Q_DECL_OVERRIDE; +private: + Q_DISABLE_COPY(DialogDuplicateDetail) + Ui::DialogDuplicateDetail *ui; + quint32 m_idDetail; + qreal m_mx; + qreal m_my; + bool m_firstRelease; +}; + +//--------------------------------------------------------------------------------------------------------------------- +inline quint32 DialogDuplicateDetail::Duplicate() const +{ + return m_idDetail; +} + +//--------------------------------------------------------------------------------------------------------------------- +inline qreal DialogDuplicateDetail::MoveDuplicateX() const +{ + return m_mx; +} + +//--------------------------------------------------------------------------------------------------------------------- +inline qreal DialogDuplicateDetail::MoveDuplicateY() const +{ + return m_my; +} + +#endif // DIALOGDUPLICATEDETAIL_H diff --git a/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.ui b/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.ui new file mode 100644 index 000000000..fa187e416 --- /dev/null +++ b/src/libs/vtools/dialogs/tools/piece/dialogduplicatedetail.ui @@ -0,0 +1,80 @@ + + + DialogDuplicateDetail + + + + 0 + 0 + 184 + 66 + + + + Dialog duplicate detail + + + + :/icon/64x64/icon64x64.png:/icon/64x64/icon64x64.png + + + + + + The dialog is never shown. + + + Qt::AlignCenter + + + + + + + Qt::Horizontal + + + QDialogButtonBox::Cancel|QDialogButtonBox::Ok + + + + + + + + + + + buttonBox + accepted() + DialogDuplicateDetail + accept() + + + 248 + 254 + + + 157 + 274 + + + + + buttonBox + rejected() + DialogDuplicateDetail + reject() + + + 316 + 260 + + + 286 + 274 + + + + + diff --git a/src/libs/vtools/tools/nodeDetails/vnodearc.cpp b/src/libs/vtools/tools/nodeDetails/vnodearc.cpp index 13ae8beb6..6832ef4e8 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodearc.cpp +++ b/src/libs/vtools/tools/nodeDetails/vnodearc.cpp @@ -59,7 +59,7 @@ VNodeArc::VNodeArc(const VAbstractNodeInitData &initData, QObject *qoParent) * @brief Create help create tool. * @param initData init data. */ -void VNodeArc::Create(VAbstractNodeInitData initData) +void VNodeArc::Create(const VAbstractNodeInitData &initData) { if (initData.parse == Document::FullParse) { diff --git a/src/libs/vtools/tools/nodeDetails/vnodearc.h b/src/libs/vtools/tools/nodeDetails/vnodearc.h index 1be22d12a..b12f7c9ef 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodearc.h +++ b/src/libs/vtools/tools/nodeDetails/vnodearc.h @@ -47,7 +47,7 @@ class VNodeArc :public VAbstractNode { Q_OBJECT public: - static void Create(VAbstractNodeInitData initData); + static void Create(const VAbstractNodeInitData &initData); static const QString ToolType; virtual QString getTagName() const Q_DECL_OVERRIDE; diff --git a/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.cpp b/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.cpp index f79d6a24b..9aa9d43a6 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.cpp +++ b/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.cpp @@ -42,7 +42,7 @@ const QString VNodeEllipticalArc::ToolType = QStringLiteral("modeling"); //--------------------------------------------------------------------------------------------------------------------- -void VNodeEllipticalArc::Create(VAbstractNodeInitData initData) +void VNodeEllipticalArc::Create(const VAbstractNodeInitData &initData) { if (initData.parse == Document::FullParse) { diff --git a/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.h b/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.h index e392f6192..31af86c22 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.h +++ b/src/libs/vtools/tools/nodeDetails/vnodeellipticalarc.h @@ -44,7 +44,7 @@ class VNodeEllipticalArc :public VAbstractNode { Q_OBJECT public: - static void Create(VAbstractNodeInitData initData); + static void Create(const VAbstractNodeInitData &initData); static const QString ToolType; virtual QString getTagName() const Q_DECL_OVERRIDE; diff --git a/src/libs/vtools/tools/nodeDetails/vnodepoint.cpp b/src/libs/vtools/tools/nodeDetails/vnodepoint.cpp index 721907088..864e89adf 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodepoint.cpp +++ b/src/libs/vtools/tools/nodeDetails/vnodepoint.cpp @@ -85,7 +85,7 @@ VNodePoint::VNodePoint(const VAbstractNodeInitData &initData, QObject *qoParent, * @brief Create help create tool. * @param initData init data. */ -void VNodePoint::Create(VAbstractNodeInitData initData) +void VNodePoint::Create(const VAbstractNodeInitData &initData) { if (initData.parse == Document::FullParse) { diff --git a/src/libs/vtools/tools/nodeDetails/vnodepoint.h b/src/libs/vtools/tools/nodeDetails/vnodepoint.h index 30ee4380d..ee550ab94 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodepoint.h +++ b/src/libs/vtools/tools/nodeDetails/vnodepoint.h @@ -50,7 +50,7 @@ class VNodePoint: public VAbstractNode, public VScenePoint { Q_OBJECT public: - static void Create(VAbstractNodeInitData initData); + static void Create(const VAbstractNodeInitData &initData); static const QString ToolType; virtual int type() const Q_DECL_OVERRIDE {return Type;} diff --git a/src/libs/vtools/tools/nodeDetails/vnodespline.cpp b/src/libs/vtools/tools/nodeDetails/vnodespline.cpp index ee75c99c7..6fa3c46f8 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodespline.cpp +++ b/src/libs/vtools/tools/nodeDetails/vnodespline.cpp @@ -60,7 +60,7 @@ VNodeSpline::VNodeSpline(const VAbstractNodeInitData &initData, QObject *qoParen * @param initData init data. * @return pointer to node. */ -VNodeSpline *VNodeSpline::Create(VAbstractNodeInitData initData) +VNodeSpline *VNodeSpline::Create(const VAbstractNodeInitData &initData) { VNodeSpline *spl = nullptr; if (initData.parse == Document::FullParse) diff --git a/src/libs/vtools/tools/nodeDetails/vnodespline.h b/src/libs/vtools/tools/nodeDetails/vnodespline.h index 5f2c82690..e7336936a 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodespline.h +++ b/src/libs/vtools/tools/nodeDetails/vnodespline.h @@ -47,7 +47,7 @@ class VNodeSpline:public VAbstractNode { Q_OBJECT public: - static VNodeSpline *Create(VAbstractNodeInitData initData); + static VNodeSpline *Create(const VAbstractNodeInitData &initData); static const QString ToolType; virtual QString getTagName() const Q_DECL_OVERRIDE; diff --git a/src/libs/vtools/tools/nodeDetails/vnodesplinepath.cpp b/src/libs/vtools/tools/nodeDetails/vnodesplinepath.cpp index 201f6eed5..d9b050d83 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodesplinepath.cpp +++ b/src/libs/vtools/tools/nodeDetails/vnodesplinepath.cpp @@ -59,7 +59,7 @@ VNodeSplinePath::VNodeSplinePath(const VAbstractNodeInitData &initData, QObject * @brief Create help create tool. * @param initData init data. */ -void VNodeSplinePath::Create(VAbstractNodeInitData initData) +void VNodeSplinePath::Create(const VAbstractNodeInitData &initData) { if (initData.parse == Document::FullParse) { diff --git a/src/libs/vtools/tools/nodeDetails/vnodesplinepath.h b/src/libs/vtools/tools/nodeDetails/vnodesplinepath.h index 2bbc0bc40..5b71f26fb 100644 --- a/src/libs/vtools/tools/nodeDetails/vnodesplinepath.h +++ b/src/libs/vtools/tools/nodeDetails/vnodesplinepath.h @@ -47,7 +47,7 @@ class VNodeSplinePath : public VAbstractNode { Q_OBJECT public: - static void Create(VAbstractNodeInitData initData); + static void Create(const VAbstractNodeInitData &initData); static const QString ToolType; virtual QString getTagName() const Q_DECL_OVERRIDE; diff --git a/src/libs/vtools/tools/vabstracttool.cpp b/src/libs/vtools/tools/vabstracttool.cpp index 07d94fffe..75d99cfa7 100644 --- a/src/libs/vtools/tools/vabstracttool.cpp +++ b/src/libs/vtools/tools/vabstracttool.cpp @@ -83,35 +83,6 @@ template class QSharedPointer; const QString VAbstractTool::AttrInUse = QStringLiteral("inUse"); -namespace -{ -//--------------------------------------------------------------------------------------------------------------------- -quint32 CreateNodeSpline(VContainer *data, quint32 id) -{ - if (data->GetGObject(id)->getType() == GOType::Spline) - { - return VAbstractTool::CreateNode(data, id); - } - else - { - return VAbstractTool::CreateNode(data, id); - } -} - -//--------------------------------------------------------------------------------------------------------------------- -quint32 CreateNodeSplinePath(VContainer *data, quint32 id) -{ - if (data->GetGObject(id)->getType() == GOType::SplinePath) - { - return VAbstractTool::CreateNode(data, id); - } - else - { - return VAbstractTool::CreateNode(data, id); - } -} -}//static functions - //--------------------------------------------------------------------------------------------------------------------- /** * @brief VAbstractTool container. @@ -379,7 +350,7 @@ QMap VAbstractTool::ColorsList() // cppcheck-suppress unusedFunction QMap VAbstractTool::PointsList() const { - const QHash > *objs = data.DataGObjects(); + const QHash > *objs = data.CalculationGObjects(); QMap list; QHash >::const_iterator i; for (i = objs->constBegin(); i != objs->constEnd(); ++i) @@ -387,7 +358,7 @@ QMap VAbstractTool::PointsList() const if (i.key() != m_id) { QSharedPointer obj = i.value(); - if (obj->getType() == GOType::Point && obj->getMode() == Draw::Calculation) + if (obj->getType() == GOType::Point) { const QSharedPointer point = data.GeometricObject(i.key()); list[point->name()] = i.key(); @@ -694,3 +665,29 @@ quint32 VAbstractTool::PrepareNode(const VPieceNode &node, VMainGraphicsScene *s } return initData.id; } + +//--------------------------------------------------------------------------------------------------------------------- +quint32 VAbstractTool::CreateNodeSpline(VContainer *data, quint32 id) +{ + if (data->GetGObject(id)->getType() == GOType::Spline) + { + return VAbstractTool::CreateNode(data, id); + } + else + { + return VAbstractTool::CreateNode(data, id); + } +} + +//--------------------------------------------------------------------------------------------------------------------- +quint32 VAbstractTool::CreateNodeSplinePath(VContainer *data, quint32 id) +{ + if (data->GetGObject(id)->getType() == GOType::SplinePath) + { + return VAbstractTool::CreateNode(data, id); + } + else + { + return VAbstractTool::CreateNode(data, id); + } +} diff --git a/src/libs/vtools/tools/vabstracttool.h b/src/libs/vtools/tools/vabstracttool.h index 585de3903..bb2c0fce1 100644 --- a/src/libs/vtools/tools/vabstracttool.h +++ b/src/libs/vtools/tools/vabstracttool.h @@ -110,8 +110,6 @@ public: virtual void ShowVisualization(bool show) =0; virtual void ChangeLabelPosition(quint32 id, const QPointF &pos); - template - static quint32 CreateNode(VContainer *data, quint32 id); public slots: /** * @brief FullUpdateFromFile update tool data form file. @@ -162,6 +160,11 @@ protected: virtual void DeleteToolWithConfirm(bool ask = true); static int ConfirmDeletion(); + template + static quint32 CreateNode(VContainer *data, quint32 id); + static quint32 CreateNodeSpline(VContainer *data, quint32 id); + static quint32 CreateNodeSplinePath(VContainer *data, quint32 id); + template void AddVisualization(); diff --git a/src/libs/vtools/tools/vtoolseamallowance.cpp b/src/libs/vtools/tools/vtoolseamallowance.cpp index 6791982e6..7188f5a61 100644 --- a/src/libs/vtools/tools/vtoolseamallowance.cpp +++ b/src/libs/vtools/tools/vtoolseamallowance.cpp @@ -28,17 +28,13 @@ #include "vtoolseamallowance.h" #include "../dialogs/tools/piece/dialogseamallowance.h" +#include "../dialogs/tools/piece/dialogduplicatedetail.h" #include "../vpatterndb/vpiecenode.h" #include "../vpatterndb/vpiecepath.h" #include "../vpatterndb/calculator.h" #include "../vpatterndb/floatItemData/vpatternlabeldata.h" #include "../vpatterndb/floatItemData/vpiecelabeldata.h" -#include "nodeDetails/vnodearc.h" -#include "nodeDetails/vnodeellipticalarc.h" -#include "nodeDetails/vnodepoint.h" -#include "nodeDetails/vnodespline.h" -#include "nodeDetails/vnodesplinepath.h" -#include "nodeDetails/vtoolpiecepath.h" +#include "nodeDetails/nodedetails.h" #include "../vgeometry/varc.h" #include "../vgeometry/vellipticalarc.h" #include "../vgeometry/vcubicbezier.h" @@ -46,6 +42,7 @@ #include "../vgeometry/vpointf.h" #include "../vgeometry/vspline.h" #include "../vgeometry/vsplinepath.h" +#include "../vgeometry/vplacelabelitem.h" #include "../ifc/xml/vpatternconverter.h" #include "../undocommands/addpiece.h" #include "../undocommands/deletepiece.h" @@ -151,6 +148,50 @@ VToolSeamAllowance *VToolSeamAllowance::Create(VToolSeamAllowanceInitData &initD return piece; } +//--------------------------------------------------------------------------------------------------------------------- +VToolSeamAllowance *VToolSeamAllowance::Duplicate(QSharedPointer dialog, VMainGraphicsScene *scene, + VAbstractPattern *doc) +{ + SCASSERT(not dialog.isNull()); + QSharedPointer dialogTool = dialog.objectCast(); + SCASSERT(not dialogTool.isNull()) + + VToolSeamAllowanceInitData initData; + initData.scene = scene; + initData.doc = doc; + initData.parse = Document::FullParse; + initData.typeCreation = Source::FromGui; + initData.drawName = doc->PieceDrawName(dialogTool->Duplicate()); + + VContainer toolData = VAbstractPattern::getTool(dialogTool->Duplicate())->getData(); + initData.data = &toolData; + + VPiece detail = initData.data->GetPiece(dialogTool->Duplicate()); + detail.SetMx(dialogTool->MoveDuplicateX()); + detail.SetMy(dialogTool->MoveDuplicateY()); + initData.detail = detail; + initData.width = initData.detail.GetFormulaSAWidth(); + + return Duplicate(initData); +} + +//--------------------------------------------------------------------------------------------------------------------- +VToolSeamAllowance *VToolSeamAllowance::Duplicate(VToolSeamAllowanceInitData &initData) +{ + VPiece dupDetail = initData.detail; + + QMap replacements; + dupDetail.GetPath().SetNodes(DuplicateNodes(initData.detail.GetPath(), initData, replacements)); + dupDetail.SetCustomSARecords(DuplicateCustomSARecords(initData.detail.GetCustomSARecords(), initData, + replacements)); + dupDetail.SetInternalPaths(DuplicateInternalPaths(initData.detail.GetInternalPaths(), initData)); + dupDetail.SetPins(DuplicatePins(initData.detail.GetPins(), initData)); + dupDetail.SetPlaceLabels(DuplicatePlaceLabels(initData.detail.GetPlaceLabels(), initData)); + + initData.detail = dupDetail; + return VToolSeamAllowance::Create(initData); +} + //--------------------------------------------------------------------------------------------------------------------- void VToolSeamAllowance::RemoveWithConfirm(bool ask) { @@ -1005,11 +1046,6 @@ QVariant VToolSeamAllowance::itemChange(QGraphicsItem::GraphicsItemChange change } } } - // Don't forget to update geometry, because first change never call full parse - VPiece detail = VAbstractTool::data.GetPiece(m_id); - detail.SetMx(newPos.x()); - detail.SetMy(newPos.y()); - VAbstractTool::data.UpdatePiece(m_id, detail); changeFinished = true; } @@ -1741,3 +1777,179 @@ void VToolSeamAllowance::AddPointRecords(VAbstractPattern *doc, QDomElement &dom domElement.appendChild(pinsElement); } } + +//--------------------------------------------------------------------------------------------------------------------- +quint32 VToolSeamAllowance::DuplicateNode(const VPieceNode &node, const VToolSeamAllowanceInitData &initData) +{ + SCASSERT(initData.scene != nullptr) + SCASSERT(initData.doc != nullptr) + SCASSERT(initData.data != nullptr) + + const QSharedPointer gobj = initData.data->GetGObject(node.GetId()); + + VAbstractNodeInitData initNodeData; + initNodeData.idObject = gobj->getIdObject(); + initNodeData.doc = initData.doc; + initNodeData.data = initData.data; + initNodeData.parse = Document::FullParse; + initNodeData.typeCreation = Source::FromGui; + initNodeData.scene = initData.scene; + initNodeData.drawName = initData.drawName; + + switch (node.GetTypeTool()) + { + case (Tool::NodePoint): + initNodeData.id = VAbstractTool::CreateNode(initData.data, gobj->getIdObject()); + VNodePoint::Create(initNodeData); + break; + case (Tool::NodeArc): + initNodeData.id = VAbstractTool::CreateNode(initData.data, gobj->getIdObject()); + VNodeArc::Create(initNodeData); + break; + case (Tool::NodeElArc): + initNodeData.id = VAbstractTool::CreateNode(initData.data, gobj->getIdObject()); + VNodeEllipticalArc::Create(initNodeData); + break; + case (Tool::NodeSpline): + initNodeData.id = VAbstractTool::CreateNodeSpline(initData.data, gobj->getIdObject()); + VNodeSpline::Create(initNodeData); + break; + case (Tool::NodeSplinePath): + initNodeData.id = VAbstractTool::CreateNodeSplinePath(initData.data, gobj->getIdObject()); + VNodeSplinePath::Create(initNodeData); + break; + default: + qDebug()<<"May be wrong tool type!!! Ignoring."<GetPiecePath(id); + VPiecePath newPath = path; + QMap recordReplacements; // Not used + newPath.SetNodes(DuplicateNodes(path, initData, recordReplacements)); + + const quint32 idPath = initData.data->AddPiecePath(newPath); + + VToolPiecePathInitData initNodeData; + initNodeData.id = idPath; + initNodeData.idObject = NULL_ID; // piece id + initNodeData.scene = initData.scene; + initNodeData.doc = initData.doc; + initNodeData.data = initData.data; + initNodeData.parse = Document::FullParse; + initNodeData.typeCreation = Source::FromTool; + initNodeData.drawName = initData.drawName; + initNodeData.path = newPath; + + VToolPiecePath::Create(initNodeData); + return idPath; +} + +//--------------------------------------------------------------------------------------------------------------------- +QVector VToolSeamAllowance::DuplicateCustomSARecords(const QVector &records, + const VToolSeamAllowanceInitData &initData, + const QMap &replacements) +{ + QVector newRecords; + for(int i=0; i < records.size(); ++i) + { + CustomSARecord record = records.at(i); + record.path = DuplicatePiecePath(record.path, initData); + record.startPoint = replacements.value(record.startPoint, NULL_ID); + record.endPoint = replacements.value(record.endPoint, NULL_ID); + newRecords.append(record); + } + return newRecords; +} + +//--------------------------------------------------------------------------------------------------------------------- +QVector VToolSeamAllowance::DuplicateInternalPaths(const QVector &iPaths, + const VToolSeamAllowanceInitData &initData) +{ + QVector newPaths; + for(int i=0; i < iPaths.size(); ++i) + { + newPaths.append(DuplicatePiecePath(iPaths.at(i), initData)); + } + return newPaths; +} + +//--------------------------------------------------------------------------------------------------------------------- +QVector VToolSeamAllowance::DuplicatePins(const QVector &pins, + const VToolSeamAllowanceInitData &initData) +{ + QVector newPins; + for(int i=0; i < pins.size(); ++i) + { + QSharedPointer pin = initData.data->GeometricObject(pins.at(i)); + + VToolPinInitData initNodeData; + initNodeData.id = initData.data->AddGObject(new VPointF(*pin)); + initNodeData.pointId = pin->getIdObject(); + initNodeData.idObject = NULL_ID; // piece id + initNodeData.doc = initData.doc; + initNodeData.data = initData.data; + initNodeData.parse = Document::FullParse; + initNodeData.typeCreation = Source::FromTool; + initNodeData.drawName = initData.drawName; + + VToolPin::Create(initNodeData); + newPins.append(initNodeData.id); + } + return newPins; +} + +//--------------------------------------------------------------------------------------------------------------------- +QVector VToolSeamAllowance::DuplicatePlaceLabels(const QVector &placeLabels, + const VToolSeamAllowanceInitData &initData) +{ + QVector newPlaceLabels; + for(int i=0; i < placeLabels.size(); ++i) + { + QSharedPointer label = initData.data->GeometricObject(placeLabels.at(i)); + + VToolPlaceLabelInitData initNodeData; + initNodeData.idObject = NULL_ID; // piece id + initNodeData.doc = initData.doc; + initNodeData.data = initData.data; + initNodeData.parse = Document::FullParse; + initNodeData.typeCreation = Source::FromTool; + initNodeData.drawName = initData.drawName; + initNodeData.width = label->GetWidthFormula(); + initNodeData.height = label->GetHeightFormula(); + initNodeData.angle = label->GetAngleFormula(); + initNodeData.type = label->GetLabelType(); + initNodeData.centerPoint = label->GetCenterPoint(); + initNodeData.id = initNodeData.data->AddGObject(new VPlaceLabelItem(*label)); + + VToolPlaceLabel::Create(initNodeData); + newPlaceLabels.append(initNodeData.id); + } + return newPlaceLabels; +} + +//--------------------------------------------------------------------------------------------------------------------- +QVector VToolSeamAllowance::DuplicateNodes(const VPiecePath &path, + const VToolSeamAllowanceInitData &initData, + QMap &replacements) +{ + QVector nodes; + for (int i = 0; i< path.CountNodes(); ++i) + { + VPieceNode nodeD = path.at(i); + const quint32 oldId = nodeD.GetId(); + const quint32 id = DuplicateNode(nodeD, initData); + if (id > NULL_ID) + { + nodeD.SetId(id); + nodes.append(nodeD); + replacements.insert(oldId, id); + } + } + return nodes; +} diff --git a/src/libs/vtools/tools/vtoolseamallowance.h b/src/libs/vtools/tools/vtoolseamallowance.h index 401c2971e..55aea4aae 100644 --- a/src/libs/vtools/tools/vtoolseamallowance.h +++ b/src/libs/vtools/tools/vtoolseamallowance.h @@ -64,6 +64,9 @@ public: static VToolSeamAllowance* Create(QSharedPointer dialog, VMainGraphicsScene *scene, VAbstractPattern *doc, VContainer *data); static VToolSeamAllowance* Create(VToolSeamAllowanceInitData &initData); + static VToolSeamAllowance* Duplicate(QSharedPointer dialog, VMainGraphicsScene *scene, + VAbstractPattern *doc); + static VToolSeamAllowance* Duplicate(VToolSeamAllowanceInitData &initData); static const quint8 pieceVersion; @@ -197,6 +200,22 @@ private: static void AddPointRecords(VAbstractPattern *doc, QDomElement &domElement, const QVector &records, const QString &tag); + + static QVector DuplicateNodes(const VPiecePath &path, const VToolSeamAllowanceInitData &initData, + QMap &replacements); + static quint32 DuplicateNode(const VPieceNode &node, const VToolSeamAllowanceInitData &initData); + + static quint32 DuplicatePiecePath(quint32 id, const VToolSeamAllowanceInitData &initData); + + static QVector DuplicateCustomSARecords(const QVector &records, + const VToolSeamAllowanceInitData &initData, + const QMap &replacements); + + static QVector DuplicateInternalPaths(const QVector &iPaths, + const VToolSeamAllowanceInitData &initData); + static QVector DuplicatePins(const QVector &pins, const VToolSeamAllowanceInitData &initData); + static QVector DuplicatePlaceLabels(const QVector &placeLabels, + const VToolSeamAllowanceInitData &initData); }; #endif // VTOOLSEAMALLOWANCE_H diff --git a/src/libs/vtools/tools/vtooluniondetails.cpp b/src/libs/vtools/tools/vtooluniondetails.cpp index 8eb89fb0d..bf3a395db 100644 --- a/src/libs/vtools/tools/vtooluniondetails.cpp +++ b/src/libs/vtools/tools/vtooluniondetails.cpp @@ -1538,19 +1538,38 @@ void CreateUnitedDetail(const VToolUnionDetailsInitData &initData, qreal dx, qre VToolSeamAllowance::Create(pieceInitData); - auto RemoveDetail = [initData](quint32 id) + auto DuplicateDetail = [initData](quint32 id) + { + VToolSeamAllowanceInitData initPieceData; + initPieceData.scene = initData.scene; + initPieceData.doc = initData.doc; + initPieceData.parse = Document::FullParse; + initPieceData.typeCreation = Source::FromGui; + initPieceData.drawName = initData.doc->PieceDrawName(id); + + VContainer toolData = VAbstractPattern::getTool(id)->getData(); + initPieceData.data = &toolData; + + initPieceData.detail = initData.data->GetPiece(id); + initPieceData.width = initPieceData.detail.GetFormulaSAWidth(); + VToolSeamAllowance::Duplicate(initPieceData); + }; + + if (initData.retainPieces) + { + DuplicateDetail(initData.d1id); + DuplicateDetail(initData.d2id); + } + + auto RemoveDetail = [](quint32 id) { VToolSeamAllowance *toolDet = qobject_cast(VAbstractPattern::getTool(id)); SCASSERT(toolDet != nullptr); - bool ask = false; - toolDet->RemoveWithConfirm(ask); + toolDet->RemoveWithConfirm(false); }; - if (not initData.retainPieces) - { - RemoveDetail(initData.d1id); - RemoveDetail(initData.d2id); - } + RemoveDetail(initData.d1id); + RemoveDetail(initData.d2id); } //--------------------------------------------------------------------------------------------------------------------- diff --git a/src/libs/vtools/visualization/path/vistoolduplicatedetail.cpp b/src/libs/vtools/visualization/path/vistoolduplicatedetail.cpp new file mode 100644 index 000000000..971eeaf90 --- /dev/null +++ b/src/libs/vtools/visualization/path/vistoolduplicatedetail.cpp @@ -0,0 +1,69 @@ +/************************************************************************ + ** + ** @file vistoolduplicatedetail.cpp + ** @author Roman Telezhynskyi + ** @date 25 10, 2017 + ** + ** @brief + ** @copyright + ** This source code is part of the Valentina project, a pattern making + ** program, whose allow create and modeling patterns of clothing. + ** Copyright (C) 2017 Valentina project + ** All Rights Reserved. + ** + ** Valentina is free software: you can redistribute it and/or modify + ** it under the terms of the GNU General Public License as published by + ** the Free Software Foundation, either version 3 of the License, or + ** (at your option) any later version. + ** + ** Valentina is distributed in the hope that it will be useful, + ** but WITHOUT ANY WARRANTY; without even the implied warranty of + ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + ** GNU General Public License for more details. + ** + ** You should have received a copy of the GNU General Public License + ** along with Valentina. If not, see . + ** + *************************************************************************/ +#include "vistoolduplicatedetail.h" +#include "../vpatterndb/vcontainer.h" + +//--------------------------------------------------------------------------------------------------------------------- +VisToolDuplicateDetail::VisToolDuplicateDetail(const VContainer *data, QGraphicsItem *parent) + : VisPath(data, parent), + m_start(), + m_started(false), + m_diff() +{} + +//--------------------------------------------------------------------------------------------------------------------- +void VisToolDuplicateDetail::RefreshGeometry() +{ + const VPiece piece = Visualization::data->GetPiece(object1Id); + + if (not m_started) + { + m_start = Visualization::scenePos; + m_started = true; + } + else + { + m_diff = Visualization::scenePos - m_start; + setPos(m_diff); + } + + DrawPath(this, PiecePath(piece), mainColor, Qt::SolidLine, Qt::RoundCap); +} + +//--------------------------------------------------------------------------------------------------------------------- +QPainterPath VisToolDuplicateDetail::PiecePath(const VPiece &piece) const +{ + if (not piece.IsHideMainPath() || not piece.IsSeamAllowance() || piece.IsSeamAllowanceBuiltIn()) + { + return piece.MainPathPath(Visualization::data); + } + else + { + return piece.SeamAllowancePath(Visualization::data); + } +} diff --git a/src/libs/vtools/visualization/path/vistoolduplicatedetail.h b/src/libs/vtools/visualization/path/vistoolduplicatedetail.h new file mode 100644 index 000000000..a306211c5 --- /dev/null +++ b/src/libs/vtools/visualization/path/vistoolduplicatedetail.h @@ -0,0 +1,68 @@ +/************************************************************************ + ** + ** @file vistoolduplicatedetail.h + ** @author Roman Telezhynskyi + ** @date 25 10, 2017 + ** + ** @brief + ** @copyright + ** This source code is part of the Valentina project, a pattern making + ** program, whose allow create and modeling patterns of clothing. + ** Copyright (C) 2017 Valentina project + ** All Rights Reserved. + ** + ** Valentina is free software: you can redistribute it and/or modify + ** it under the terms of the GNU General Public License as published by + ** the Free Software Foundation, either version 3 of the License, or + ** (at your option) any later version. + ** + ** Valentina is distributed in the hope that it will be useful, + ** but WITHOUT ANY WARRANTY; without even the implied warranty of + ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + ** GNU General Public License for more details. + ** + ** You should have received a copy of the GNU General Public License + ** along with Valentina. If not, see . + ** + *************************************************************************/ +#ifndef VISTOOLDUPLICATEDETAIL_H +#define VISTOOLDUPLICATEDETAIL_H + +#include "vispath.h" +#include "../vpatterndb/vpiece.h" + +class VisToolDuplicateDetail : public VisPath +{ + Q_OBJECT +public: + VisToolDuplicateDetail(const VContainer *data, QGraphicsItem *parent = nullptr); + virtual ~VisToolDuplicateDetail() = default; + + qreal Mx() const; + qreal My() const; + + virtual void RefreshGeometry() Q_DECL_OVERRIDE; + virtual int type() const Q_DECL_OVERRIDE {return Type;} + enum { Type = UserType + static_cast(Vis::ToolDuplicateDetail)}; +private: + Q_DISABLE_COPY(VisToolDuplicateDetail) + QPointF m_start; + bool m_started; + QPointF m_diff; + + QPainterPath PiecePath(const VPiece &piece) const; +}; + +//--------------------------------------------------------------------------------------------------------------------- +inline qreal VisToolDuplicateDetail::Mx() const +{ + return m_diff.x(); +} + +//--------------------------------------------------------------------------------------------------------------------- +inline qreal VisToolDuplicateDetail::My() const +{ + return m_diff.y(); +} + +#endif // VISTOOLDUPLICATEDETAIL_H diff --git a/src/libs/vtools/visualization/visualization.pri b/src/libs/vtools/visualization/visualization.pri index 5f9aac564..2eef73604 100644 --- a/src/libs/vtools/visualization/visualization.pri +++ b/src/libs/vtools/visualization/visualization.pri @@ -42,7 +42,8 @@ HEADERS += \ $$PWD/path/vistoolpiece.h \ $$PWD/path/vistoolpiecepath.h \ $$PWD/path/vispiecespecialpoints.h \ - $$PWD/line/vistoolspecialpoint.h + $$PWD/line/vistoolspecialpoint.h \ + $$PWD/path/vistoolduplicatedetail.h SOURCES += \ $$PWD/visualization.cpp \ @@ -85,4 +86,5 @@ SOURCES += \ $$PWD/path/vistoolpiece.cpp \ $$PWD/path/vistoolpiecepath.cpp \ $$PWD/path/vispiecespecialpoints.cpp \ - $$PWD/line/vistoolspecialpoint.cpp + $$PWD/line/vistoolspecialpoint.cpp \ + $$PWD/path/vistoolduplicatedetail.cpp