Salome HOME
Issue #1489 Multi-rotation problem if there is a reference to copied objects
[modules/shaper.git] / src / ParametersPlugin / ParametersPlugin_WidgetParamsMgr.cpp
1 // Copyright (C) 2014-20xx CEA/DEN, EDF R&D -->
2
3 // File:        ParametersPlugin_WidgetParamsMgr.cpp
4 // Created:     11 Apr 2016
5 // Author:      Vitaly SMETANNIKOV
6
7 #include "ParametersPlugin_WidgetParamsMgr.h"
8 #include "ParametersPlugin_Parameter.h"
9 #include "ParametersPlugin_Validators.h"
10
11 #include <ModelAPI_ResultParameter.h>
12 #include <ModelAPI_AttributeString.h>
13 #include <ModelAPI_AttributeRefList.h>
14 #include <ModelAPI_AttributeDouble.h>
15 #include <ModelAPI_AttributeInteger.h>
16 #include <ModelAPI_Events.h>
17 #include <ModelAPI_Session.h>
18 #include <ModelAPI_Tools.h>
19
20 #include <ModuleBase_Tools.h>
21
22 #include <Events_Loop.h>
23
24 #include <QLayout>
25 #include <QPushButton>
26 #include <QToolButton>
27 #include <QStyledItemDelegate>
28 #include <QPainter>
29 #include <QMessageBox>
30 #include <QTimer>
31 #include <QEvent>
32 #include <QKeyEvent>
33
34 enum ColumnType {
35   Col_Name,
36   Col_Equation,
37   Col_Result,
38   Col_Comment
39 };
40
41 const char* NoName = "<NoName>";
42 const char* NoValue = "<NoValue>";
43 const char* NotValid = "<NotValid>";
44
45 /*!
46  * \ingroup GUI
47  * ItemDelegate object in order to redefine items behavior
48  */
49 class ParametersPlugin_ItemDelegate : public QStyledItemDelegate
50 {
51 public:
52   /// Constructor
53   /// \param thaParent a parent
54   ParametersPlugin_ItemDelegate(QObject* thaParent) : 
55       QStyledItemDelegate(thaParent) {}
56
57   /// Redefinition of virtual method
58   /// \param painter a painter object
59   /// \param option the item options
60   /// \param index the current index
61   virtual void paint(QPainter* painter, 
62     const QStyleOptionViewItem& option, 
63     const QModelIndex& index ) const;
64   
65   /// Redefinition of virtual method
66   /// \param parent a parent widget
67   /// \param option the item options
68   /// \param index the current index
69   virtual QWidget* createEditor(QWidget* parent, 
70                                 const QStyleOptionViewItem& option, 
71                                 const QModelIndex& index) const;
72
73   /// Returns True if the given index is editable item
74   /// \param theIndex an item index
75   bool isEditable(const QModelIndex& theIndex) const;
76
77   /// Returns currently editing index
78   QModelIndex editIndex() const { return myEditingIdx; }
79
80 private:
81   mutable QModelIndex myEditingIdx;
82 };
83
84 bool ParametersPlugin_ItemDelegate::isEditable(const QModelIndex& theIndex) const
85 {
86   QModelIndex aParent = theIndex.parent();
87   if (aParent.isValid() && (aParent.row() == 0)) {
88     if (theIndex.column() == 2)
89       return false;
90   } else
91     return false;
92   return true;
93 }
94
95 void ParametersPlugin_ItemDelegate::paint(QPainter* painter, 
96                                           const QStyleOptionViewItem& option, 
97                                           const QModelIndex& index ) const
98 {
99   QBrush aBrush = painter->brush();
100   QPen aPen = painter->pen();
101 //  if (!isEditable(index))
102   if (!index.parent().isValid())
103     painter->setBrush(Qt::lightGray);
104
105   painter->setPen(Qt::lightGray);
106   painter->drawRect(option.rect);
107   painter->setPen(aPen);
108
109   QStyledItemDelegate::paint(painter, option, index);
110   painter->setBrush(aBrush);
111 }
112
113 QWidget* ParametersPlugin_ItemDelegate::createEditor(QWidget* parent, 
114                                                      const QStyleOptionViewItem& option, 
115                                                      const QModelIndex& index) const
116 {
117   myEditingIdx = index;
118   return QStyledItemDelegate::createEditor(parent, option, index);
119 }
120
121 /////////////////////////////////////////////////////////////////////////////////////////////////
122 void ParametersPlugin_TreeWidget::closeEditor(QWidget* theEditor, QAbstractItemDelegate::EndEditHint theHint)
123 {
124   if (theHint == QAbstractItemDelegate::EditNextItem) {
125     QModelIndex aCurrent = currentIndex();
126     QModelIndex aParent = model()->index(0, 0);
127     int aNbRows = model()->rowCount(aParent);
128     QModelIndex aIdx;
129     switch (aCurrent.column()) {
130     case 0:
131       aIdx = model()->index(aCurrent.row(), 1, aParent);
132       break;
133     case 1:
134       if (aCurrent.row() < (aNbRows - 1))
135         aIdx = model()->index(aCurrent.row() + 1, 0, aParent);
136       else {
137         QTreeWidget::closeEditor(theEditor, QAbstractItemDelegate::NoHint);
138         return;
139       }
140       break;
141     case 3:
142       QTreeWidget::closeEditor(theEditor, theHint);
143       return;
144     }
145     if (aIdx.isValid()) {
146       QTreeWidget::closeEditor(theEditor, QAbstractItemDelegate::NoHint);
147       setCurrentIndex(aIdx);
148       edit(aIdx);
149       return;
150     }
151   }
152   QTreeWidget::closeEditor(theEditor, theHint);
153 }
154
155 /////////////////////////////////////////////////////////////////////////////////////////////////
156
157 ParametersPlugin_WidgetParamsMgr::ParametersPlugin_WidgetParamsMgr(QWidget* theParent, const Config_WidgetAPI* theData)
158   : ModuleBase_ModelWidget(theParent, theData)
159 {
160   QVBoxLayout* aLayout = new QVBoxLayout(this);
161
162   myTable = new ParametersPlugin_TreeWidget(this);
163   myTable->setColumnCount(4);
164   QStringList aHeaders;
165   aHeaders << tr("Name") << tr("Equation") << tr("Result") << tr("Comment");
166   myTable->setHeaderLabels(aHeaders);
167   myTable->setColumnWidth(Col_Name, 200);
168   myTable->setColumnWidth(Col_Equation, 100);
169   myTable->setColumnWidth(Col_Result, 80);
170   myTable->setColumnWidth(Col_Comment, 200);
171   myTable->setMinimumWidth(600);
172   myTable->setEditTriggers(QAbstractItemView::NoEditTriggers);
173   myTable->setSelectionMode(QAbstractItemView::SingleSelection);
174
175   connect(myTable, SIGNAL(doubleClicked(const QModelIndex&)),
176           SLOT(onDoubleClick(const QModelIndex&)));
177   connect(myTable, SIGNAL(itemSelectionChanged()), SLOT(onSelectionChanged()));
178
179   myDelegate = new ParametersPlugin_ItemDelegate(myTable);
180   connect(myDelegate, SIGNAL(closeEditor(QWidget*, QAbstractItemDelegate::EndEditHint)), 
181           SLOT(onCloseEditor(QWidget*, QAbstractItemDelegate::EndEditHint)));
182
183   myTable->setItemDelegate(myDelegate);
184   aLayout->addWidget(myTable);
185
186   // Define root nodes
187   QStringList aNames;
188   aNames<<tr("Parameters");
189   myParameters = new QTreeWidgetItem(aNames);
190   myParameters->setFlags(Qt::ItemIsEnabled);
191   myTable->addTopLevelItem(myParameters);
192
193   aNames.clear();
194   aNames<<tr("Features");
195   myFeatures = new QTreeWidgetItem(aNames);
196   myFeatures->setFlags(Qt::ItemIsEnabled);
197   myTable->addTopLevelItem(myFeatures);
198
199   QHBoxLayout* aBtnLayout = new QHBoxLayout(this);
200
201   myUpBtn = new QToolButton(this);
202   myUpBtn->setArrowType(Qt::UpArrow);
203   connect(myUpBtn, SIGNAL(clicked(bool)), SLOT(onUp()));
204   aBtnLayout->addWidget(myUpBtn);
205
206   myDownBtn = new QToolButton(this);
207   myDownBtn->setArrowType(Qt::DownArrow);
208   connect(myDownBtn, SIGNAL(clicked(bool)), SLOT(onDown()));
209   aBtnLayout->addWidget(myDownBtn);
210
211   aBtnLayout->addStretch();
212
213   myAddBtn = new QPushButton(tr("Add"), this);
214   connect(myAddBtn, SIGNAL(clicked(bool)), SLOT(onAdd()));
215   aBtnLayout->addWidget(myAddBtn);
216
217   myInsertBtn = new QPushButton(tr("Insert"), this);
218   connect(myInsertBtn, SIGNAL(clicked(bool)), SLOT(onInsert()));
219   aBtnLayout->addWidget(myInsertBtn);
220
221   myRemoveBtn = new QPushButton(tr("Remove"), this);
222   connect(myRemoveBtn, SIGNAL(clicked(bool)), SLOT(onRemove()));
223   aBtnLayout->addWidget(myRemoveBtn);
224
225   aLayout->addLayout(aBtnLayout);
226
227   onSelectionChanged();
228 }
229
230 QList<QWidget*> ParametersPlugin_WidgetParamsMgr::getControls() const
231 {
232   QList<QWidget*> aList;
233
234   return aList;
235 }
236
237 void ParametersPlugin_WidgetParamsMgr::selectItemScroll(QTreeWidgetItem* aItem)
238 {
239   myTable->clearSelection();
240   QModelIndex aParent = myTable->model()->index(0, 0);
241   int aChildIdx = myParameters->indexOfChild(aItem);
242   QModelIndex aIndex = myTable->model()->index(aChildIdx, Col_Name, aParent);
243   myTable->selectionModel()->select(aIndex, 
244     QItemSelectionModel::SelectCurrent | QItemSelectionModel::Rows);
245   myTable->scrollToItem(aItem);
246 }
247
248
249 bool ParametersPlugin_WidgetParamsMgr::storeValueCustom()
250 {
251   ParametersPlugin_ExpressionValidator aValidator;
252   std::list<std::string> aArgs;
253   std::string aAttrId = ParametersPlugin_Parameter::VARIABLE_ID();
254   std::string aErr;
255   int aId = 0;
256   foreach(FeaturePtr aFeature, myParametersList) {
257     if (!aValidator.isValid(aFeature->attribute(aAttrId), aArgs, aErr)) {
258       QMessageBox::warning(this, tr("Warning"), aErr.c_str());
259       selectItemScroll(myParameters->child(aId));
260       return false;
261     }
262     aId++;
263   }
264   return true;
265 }
266
267 bool ParametersPlugin_WidgetParamsMgr::restoreValueCustom()
268 {
269   return true;
270 }
271
272 void ParametersPlugin_WidgetParamsMgr::activateCustom()
273 {
274   updateParametersFeatures();
275   updateParametersPart();
276   updateFeaturesPart();
277
278   myFeatures->setExpanded(true);
279   myParameters->setExpanded(true);
280 }
281
282 void ParametersPlugin_WidgetParamsMgr::updateParametersFeatures()
283 {
284   myParametersList.clear();
285   FeaturePtr aFeature = feature();
286   DocumentPtr aDoc = aFeature->document();
287   ObjectPtr aObj;
288   FeaturePtr aParamFeature;
289   int aNbFeatures = aDoc->numInternalFeatures();
290   for (int i = 0; i < aNbFeatures; i++) {
291     aParamFeature = aDoc->internalFeature(i);
292     if (aParamFeature->getKind() == ParametersPlugin_Parameter::ID()) {
293       myParametersList.append(aParamFeature);
294     }
295   }
296 }
297
298 void ParametersPlugin_WidgetParamsMgr::updateFeaturesPart()
299 {
300   updateItem(myFeatures, featuresItems(myParametersList));
301 }
302
303 void ParametersPlugin_WidgetParamsMgr::updateParametersPart()
304 {
305   updateItem(myParameters, parametersItems(myParametersList));
306   bool aIsValid = checkIsValid();
307   enableButtons(aIsValid);
308 }
309
310
311 QList<QStringList> ParametersPlugin_WidgetParamsMgr::
312   featuresItems(const QList<FeaturePtr>& theFeatures) const
313 {
314   QList<QStringList> aItemsList;
315   ResultParameterPtr aParam;
316   QList<FeaturePtr> aFeatures;
317   foreach(FeaturePtr aParameter, theFeatures) {
318     aParam = std::dynamic_pointer_cast<ModelAPI_ResultParameter>(aParameter->firstResult());
319     const std::set<std::shared_ptr<ModelAPI_Attribute>>& aRefs = aParam->data()->refsToMe();
320     std::set<std::shared_ptr<ModelAPI_Attribute> >::const_iterator aIt;
321     for(aIt = aRefs.cbegin(); aIt != aRefs.cend(); aIt++) {
322       std::shared_ptr<ModelAPI_Attribute> aAttr = (*aIt);
323       FeaturePtr aReferenced = std::dynamic_pointer_cast<ModelAPI_Feature>(aAttr->owner());
324       if (aReferenced.get()) {
325         if (aReferenced->getKind() == ParametersPlugin_Parameter::ID()) {
326           // Find referenced feature Recursive
327           QList<FeaturePtr> aList;
328           aList.append(aReferenced);
329           QList<QStringList> aItems = featuresItems(aList);
330           aItemsList.append(aItems);
331         } else {
332           if (!aFeatures.contains(aReferenced)) {
333             QStringList aValNames;
334             aValNames << aReferenced->data()->name().c_str();
335
336             AttributeDoublePtr aDouble = std::dynamic_pointer_cast<ModelAPI_AttributeDouble>(aAttr);
337             if (aDouble.get()) {
338               aValNames << aDouble->text().c_str();
339               aValNames << QString::number(aDouble->value());
340             } else {
341               AttributeIntegerPtr aInt = std::dynamic_pointer_cast<ModelAPI_AttributeInteger>(aAttr);
342               if (aInt.get()) {
343                 aValNames << aInt->text().c_str();
344                 aValNames << QString::number(aInt->value());
345               }
346             }
347             aItemsList.append(aValNames);
348             aFeatures.append(aReferenced);
349           }
350         }
351       }
352     }
353   }
354   return aItemsList;
355 }
356
357
358 QList<QStringList> ParametersPlugin_WidgetParamsMgr::
359   parametersItems(const QList<FeaturePtr>& theFeatures) const
360 {
361   std::list<std::string> aArgs;
362   std::string aErr;
363   QList<QStringList> aItemsList;
364   foreach(FeaturePtr aParameter, theFeatures) {
365     ResultPtr aParam = aParameter->firstResult();
366     QStringList aValues;
367
368     std::string aName = aParameter->string(ParametersPlugin_Parameter::VARIABLE_ID())->value();
369     if (aName.empty()) {
370       aValues << NoName;
371     } else
372       aValues << aName.c_str();
373
374     std::string aExpr = aParameter->string(ParametersPlugin_Parameter::EXPRESSION_ID())->value();
375     if (aName.empty()) {
376       aValues << NoValue;
377     } else
378       aValues << aExpr.c_str();
379
380     std::string aErr = aParameter->data()->string(ParametersPlugin_Parameter::EXPRESSION_ERROR_ID())->value();
381     if (aErr.empty()) {
382       AttributeDoublePtr aValueAttribute = aParam->data()->real(ModelAPI_ResultParameter::VALUE());
383       aValues << QString::number(aValueAttribute->value());
384     } else {
385       aValues << aErr.c_str();
386     }
387     aValues << aParameter->string(ParametersPlugin_Parameter::COMMENT_ID())->value().c_str();
388     aItemsList.append(aValues);
389   }
390   return aItemsList;
391 }
392
393
394 void ParametersPlugin_WidgetParamsMgr::onDoubleClick(const QModelIndex& theIndex)
395 {
396   if (myDelegate->isEditable(theIndex)) {
397     myTable->setCurrentIndex(theIndex);
398     myTable->edit(theIndex);
399   }
400 }
401
402 void ParametersPlugin_WidgetParamsMgr::onCloseEditor(QWidget* theEditor, 
403                                                      QAbstractItemDelegate::EndEditHint theHint)
404 {
405   FeaturePtr aFeature = myParametersList.at(myDelegate->editIndex().row());
406   QTreeWidgetItem* aItem = myParameters->child(myDelegate->editIndex().row());
407   int aColumn = myDelegate->editIndex().column();
408   QString aText = aItem->text(aColumn);
409   bool isModified = false;
410
411   switch (aColumn) {
412   case Col_Name:
413     {
414       AttributeStringPtr aStringAttr = aFeature->string(ParametersPlugin_Parameter::VARIABLE_ID());
415       if (!aText.isEmpty()) {
416         while (aText.indexOf(" ") != -1) {
417           aText.replace(" ", "");
418         }
419         if (hasName(aText)) {
420           myMessage = tr("Name %1 already exists.").arg(aText);
421           QTimer::singleShot(50, this, SLOT(sendWarning()));
422           return;
423         }
424         aStringAttr->setValue(aText.toStdString());
425         isModified = true;
426       } 
427     }
428     break;
429   case Col_Equation:
430     {
431       AttributeStringPtr aStringAttr = aFeature->string(ParametersPlugin_Parameter::EXPRESSION_ID());
432       if (!aText.isEmpty()) {
433         if (aText != aStringAttr->value().c_str()) {
434           aStringAttr->setValue(aText.toStdString());
435           aFeature->execute();
436           isModified = true;
437         }
438       }
439     }
440     break;
441   case Col_Comment:
442     {
443       AttributeStringPtr aStringAttr = aFeature->string(ParametersPlugin_Parameter::COMMENT_ID());
444       aStringAttr->setValue(aText.toStdString());
445       isModified = true;
446     }
447     break;
448   }
449
450   if (!isModified)
451     return;
452   Events_Loop* aLoop = Events_Loop::loop();
453   aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_CREATED));
454   aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
455   aLoop->flush(Events_Loop::eventByName(EVENT_OBJECT_DELETED));
456
457   if (aColumn == Col_Equation)
458     updateParametersPart();
459   updateFeaturesPart();
460 }
461
462 void ParametersPlugin_WidgetParamsMgr::updateItem(QTreeWidgetItem* theItem, 
463                                                   const QList<QStringList>& theFeaturesList)
464 {
465   if (theFeaturesList.count() != theItem->childCount()) {
466     if (theItem->childCount()  < theFeaturesList.count()) {
467       while (theItem->childCount() != theFeaturesList.count()) 
468         theItem->addChild(createNewItem(theItem));
469     } else {
470       while (theItem->childCount() != theFeaturesList.count()) 
471         theItem->removeChild(theItem->child(theItem->childCount() - 1));
472     }
473   }
474   int i = 0;
475   foreach(QStringList aFeature, theFeaturesList) {
476     int aCol = 0;
477     foreach(QString aText, aFeature) {
478       if (aText.length() > 0) {
479         theItem->child(i)->setText(aCol, aText);
480         theItem->child(i)->setToolTip(aCol, aText);
481       }
482       aCol++;
483     }
484     i++;
485   }
486 }
487
488 FeaturePtr ParametersPlugin_WidgetParamsMgr::createParameter() const
489 {
490   SessionPtr aMgr = ModelAPI_Session::get();
491   std::shared_ptr<ModelAPI_Document> aDoc = aMgr->activeDocument();
492
493   FeaturePtr aFeature = aDoc->addFeature(ParametersPlugin_Parameter::ID());
494   if (aFeature.get()) {
495     Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_CREATED));
496     Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
497   }
498   return aFeature;
499 }
500
501
502 QTreeWidgetItem* ParametersPlugin_WidgetParamsMgr::createNewItem(QTreeWidgetItem* theParent) const
503 {
504   QStringList aValues;
505   aValues << NoName;
506   aValues << NoValue;
507
508   QTreeWidgetItem* aItem = new QTreeWidgetItem(aValues);
509   if (theParent == myParameters)
510     aItem->setFlags(Qt::ItemIsSelectable | Qt::ItemIsEditable | Qt::ItemIsEnabled);
511   else 
512     aItem->setFlags(Qt::NoItemFlags);
513   return aItem;
514 }
515
516
517 void ParametersPlugin_WidgetParamsMgr::onAdd()
518 {
519   FeaturePtr aFeature = createParameter();
520   if (!aFeature.get())
521     return;
522
523   myParametersList.append(aFeature);
524   updateParametersPart();    
525
526   QTreeWidgetItem* aItem = myParameters->child(myParameters->childCount() - 1);
527
528   myTable->scrollToItem(aItem);
529   myTable->setCurrentItem(aItem);
530   myTable->editItem(aItem);
531
532   enableButtons(false);
533 }
534
535 QTreeWidgetItem* ParametersPlugin_WidgetParamsMgr::selectedItem() const
536 {
537   QList<QTreeWidgetItem*> aItemsList = myTable->selectedItems();
538   if (aItemsList.count() == 0)
539     return 0;
540
541   QTreeWidgetItem* aCurrentItem = aItemsList.first();
542   if (aCurrentItem->parent() != myParameters)
543     return 0;
544
545   return aCurrentItem;
546 }
547
548
549 void ParametersPlugin_WidgetParamsMgr::onInsert()
550 {
551   QTreeWidgetItem* aCurrentItem = selectedItem();
552   if (!aCurrentItem)
553     return;
554
555   SessionPtr aMgr = ModelAPI_Session::get();
556   std::shared_ptr<ModelAPI_Document> aDoc = aMgr->activeDocument();
557
558   FeaturePtr aNewFeature = createParameter();
559   if (!aNewFeature.get())
560     return;
561
562   int aCurrentPos = myParameters->indexOfChild(aCurrentItem);
563   if (aCurrentPos == 0) {
564     aDoc->moveFeature(aNewFeature, FeaturePtr());
565   } else {
566     FeaturePtr aCurFeature = myParametersList.at(aCurrentPos - 1);
567     aDoc->moveFeature(aNewFeature, aCurFeature);
568   }
569   updateParametersFeatures();
570   updateParametersPart();
571
572   myTable->scrollToItem(aCurrentItem);
573   myTable->setCurrentItem(aCurrentItem);
574   myTable->editItem(aCurrentItem);
575 }
576
577 void ParametersPlugin_WidgetParamsMgr::onRemove()
578 {
579   QTreeWidgetItem* aCurrentItem = selectedItem();
580   if (!aCurrentItem)
581     return;
582
583   SessionPtr aMgr = ModelAPI_Session::get();
584   std::shared_ptr<ModelAPI_Document> aDoc = aMgr->activeDocument();
585
586   int aCurrentPos = myParameters->indexOfChild(aCurrentItem);
587   FeaturePtr aCurFeature = myParametersList.at(aCurrentPos);
588
589   QObjectPtrList anObjects;
590   anObjects.append(aCurFeature);
591
592   std::map<FeaturePtr, std::set<FeaturePtr> > aReferences;
593   std::set<FeaturePtr> aFeatures;
594   ModuleBase_Tools::convertToFeatures(anObjects, aFeatures);
595   ModelAPI_Tools::findAllReferences(aFeatures, aReferences);
596
597   std::set<FeaturePtr> aFeatureRefsToDelete;
598   if (ModuleBase_Tools::askToDelete(aFeatures, aReferences, this, aFeatureRefsToDelete)) {
599     if (!aFeatureRefsToDelete.empty())
600       aFeatures.insert(aFeatureRefsToDelete.begin(), aFeatureRefsToDelete.end());
601     ModelAPI_Tools::removeFeatures(aFeatures, false);
602
603     Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_DELETED));
604     Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_TO_REDISPLAY));
605     updateParametersFeatures();
606     updateFeaturesPart();
607     updateParametersPart();
608   }
609 }
610
611 void ParametersPlugin_WidgetParamsMgr::onUp()
612 {
613   QTreeWidgetItem* aCurrentItem = selectedItem();
614   if (!aCurrentItem)
615     return;
616
617   int aCurrentPos = myParameters->indexOfChild(aCurrentItem);
618   if (aCurrentPos == 0)
619     return;
620   FeaturePtr aCurFeature = myParametersList.at(aCurrentPos);
621
622   SessionPtr aMgr = ModelAPI_Session::get();
623   std::shared_ptr<ModelAPI_Document> aDoc = aMgr->activeDocument();
624
625   if (aCurrentPos == 1)
626     aDoc->moveFeature(aCurFeature, FeaturePtr());
627   else
628     aDoc->moveFeature(aCurFeature, myParametersList.at(aCurrentPos - 2));
629
630   // add the updated also the feature that goes down
631   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_CREATED));
632   static Events_ID EVENT_UPD = Events_Loop::loop()->eventByName(EVENT_OBJECT_UPDATED);
633   ModelAPI_EventCreator::get()->sendUpdated(myParametersList.at(aCurrentPos - 1), EVENT_UPD);
634   Events_Loop::loop()->flush(EVENT_UPD);
635   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_CREATED));
636   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_DELETED));
637   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_TO_REDISPLAY));
638   updateParametersFeatures();
639   updateParametersPart();
640   updateFeaturesPart();
641
642   if (aCurrentPos > 0) {
643     aCurrentItem = myParameters->child(aCurrentPos - 1);
644     myTable->setCurrentItem(aCurrentItem);
645     selectItemScroll(aCurrentItem);
646   }
647 }
648
649 void ParametersPlugin_WidgetParamsMgr::onDown()
650 {
651   QTreeWidgetItem* aCurrentItem = selectedItem();
652   if (!aCurrentItem)
653     return;
654
655   int aCurrentPos = myParameters->indexOfChild(aCurrentItem);
656   if (aCurrentPos == (myParametersList.count() - 1))
657     return;
658   FeaturePtr aCurFeature = myParametersList.at(aCurrentPos);
659
660   SessionPtr aMgr = ModelAPI_Session::get();
661   std::shared_ptr<ModelAPI_Document> aDoc = aMgr->activeDocument();
662   aDoc->moveFeature(aCurFeature, myParametersList.at(aCurrentPos + 1));
663   // add the updated also the feature that goes up
664   static Events_ID EVENT_UPD = Events_Loop::loop()->eventByName(EVENT_OBJECT_UPDATED);
665   ModelAPI_EventCreator::get()->sendUpdated(myParametersList.at(aCurrentPos + 1), EVENT_UPD);
666
667   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_CREATED));
668   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_UPDATED));
669   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_CREATED));
670   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_DELETED));
671   Events_Loop::loop()->flush(Events_Loop::loop()->eventByName(EVENT_OBJECT_TO_REDISPLAY));
672   updateParametersFeatures();
673   updateParametersPart();
674   updateFeaturesPart();
675
676   if (aCurrentPos < myParameters->childCount() - 1) {
677     aCurrentItem = myParameters->child(aCurrentPos + 1);
678     myTable->setCurrentItem(aCurrentItem);
679     selectItemScroll(aCurrentItem);
680   }
681 }
682
683
684 bool ParametersPlugin_WidgetParamsMgr::hasName(const QString& theName) const
685 {
686   int aCurrent = myDelegate->editIndex().row();
687   int i = 0;
688   foreach(FeaturePtr aFeature, myParametersList) {
689     if ((i != aCurrent) && (aFeature->data()->name() == theName.toStdString()))
690       return true;
691     i++;
692   }
693   return false;
694 }
695
696 void ParametersPlugin_WidgetParamsMgr::sendWarning()
697 {
698   QMessageBox::warning(this, tr("Warning"), myMessage);
699 }
700
701 void ParametersPlugin_WidgetParamsMgr::onSelectionChanged()
702 {
703   bool isValid = checkIsValid();
704   if (isValid) {
705     QList<QTreeWidgetItem*> aItemsList = myTable->selectedItems();
706     bool isParameter = false;
707     foreach(QTreeWidgetItem* aItem, aItemsList) {
708       if (aItem->parent() == myParameters) {
709         isParameter = true;
710         break;
711       }
712     }
713     myInsertBtn->setEnabled(isParameter);
714     myRemoveBtn->setEnabled(isParameter);
715     myUpBtn->setEnabled(isParameter);
716     myDownBtn->setEnabled(isParameter);
717   } else {
718     myInsertBtn->setEnabled(false);
719     myRemoveBtn->setEnabled(false);
720     myUpBtn->setEnabled(false);
721     myDownBtn->setEnabled(false);
722   }
723 }
724
725 void ParametersPlugin_WidgetParamsMgr::enableButtons(bool theEnable)
726 {
727   myAddBtn->setEnabled(theEnable);
728   if (theEnable) 
729     onSelectionChanged();
730   else {
731     myInsertBtn->setEnabled(theEnable);
732     myRemoveBtn->setEnabled(theEnable);
733     myUpBtn->setEnabled(theEnable);
734     myDownBtn->setEnabled(theEnable);
735   }
736 }
737
738 bool ParametersPlugin_WidgetParamsMgr::checkIsValid()
739 {
740   QTreeWidgetItem* aItem;
741   bool aIsValid = true;
742   for(int i = 0; i < myParameters->childCount(); i++) {
743     aItem = myParameters->child(i);
744     if ((aItem->text(Col_Name) == NoName) || (aItem->text(Col_Equation) == NoValue)) {
745       aIsValid = false;
746       break;
747     }
748   }
749   return aIsValid;
750 }
751