Salome HOME
36bc9f6f3cc2fca75a21fcc5bc9911a018728a66
[modules/shaper.git] / src / ModuleBase / ModuleBase_Operation.cpp
1 /*
2  * ModuleBase_Operation.cpp
3  *
4  *  Created on: Apr 2, 2014
5  *      Author: sbh
6  */
7
8 #include "ModuleBase_Operation.h"
9
10 #include "ModuleBase_OperationDescription.h"
11 #include "ModuleBase_ModelWidget.h"
12 #include "ModuleBase_WidgetValueFeature.h"
13 #include "ModuleBase_ViewerPrs.h"
14 #include "ModuleBase_IPropertyPanel.h"
15
16 #include <ModelAPI_AttributeDouble.h>
17 #include <ModelAPI_Document.h>
18 #include <ModelAPI_Feature.h>
19 #include <ModelAPI_Data.h>
20 #include <ModelAPI_Document.h>
21 #include <ModelAPI_Events.h>
22 #include <ModelAPI_Result.h>
23 #include <ModelAPI_Validator.h>
24
25 #include <GeomAPI_Pnt2d.h>
26
27 #include <Events_Loop.h>
28
29 #ifdef _DEBUG
30 #include <QDebug>
31 #endif
32
33 ModuleBase_Operation::ModuleBase_Operation(const QString& theId, QObject* theParent)
34     : QObject(theParent),
35       myIsEditing(false),
36       myIsModified(false),
37       myPropertyPanel(NULL)
38 {
39   myDescription = new ModuleBase_OperationDescription(theId);
40 }
41
42 ModuleBase_Operation::~ModuleBase_Operation()
43 {
44   delete myDescription;
45 }
46
47 QString ModuleBase_Operation::id() const
48 {
49   return getDescription()->operationId();
50 }
51
52 FeaturePtr ModuleBase_Operation::feature() const
53 {
54   return myFeature;
55 }
56
57 bool ModuleBase_Operation::isValid() const
58 {
59   if (!myFeature)
60     return true; // rename operation
61   //Get validators for the Id
62   SessionPtr aMgr = ModelAPI_Session::get();
63   ModelAPI_ValidatorsFactory* aFactory = aMgr->validators();
64   return aFactory->validate(myFeature);
65 }
66
67 bool ModuleBase_Operation::isNestedOperationsEnabled() const
68 {
69   return true;
70 }
71
72 void ModuleBase_Operation::storeCustomValue()
73 {
74   if (!myFeature) {
75 #ifdef _DEBUG
76     qDebug() << "ModuleBase_Operation::storeCustom: " <<
77     "trying to store value without opening a transaction.";
78 #endif
79     return;
80   }
81
82   ModuleBase_ModelWidget* aCustom = dynamic_cast<ModuleBase_ModelWidget*>(sender());
83   if (aCustom)
84     aCustom->storeValue();
85 }
86
87 void ModuleBase_Operation::startOperation()
88 {
89   if (!myIsEditing)
90     createFeature();
91 }
92
93 void ModuleBase_Operation::stopOperation()
94 {
95 }
96
97 void ModuleBase_Operation::abortOperation()
98 {
99 }
100
101 void ModuleBase_Operation::commitOperation()
102 {
103 }
104
105 void ModuleBase_Operation::afterCommitOperation()
106 {
107 }
108
109 bool ModuleBase_Operation::canBeCommitted() const
110 {
111   return true;
112 }
113
114 void ModuleBase_Operation::flushUpdated()
115 {
116   Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_UPDATED));
117 }
118
119 void ModuleBase_Operation::flushCreated()
120 {
121   Events_Loop::loop()->flush(Events_Loop::eventByName(EVENT_OBJECT_CREATED));
122 }
123
124 FeaturePtr ModuleBase_Operation::createFeature(
125   const bool theFlushMessage, CompositeFeaturePtr theCompositeFeature)
126 {
127   if (theCompositeFeature) {
128     myFeature = theCompositeFeature->addFeature(getDescription()->operationId().toStdString());
129   } else {
130     boost::shared_ptr<ModelAPI_Document> aDoc = document();
131     myFeature = aDoc->addFeature(getDescription()->operationId().toStdString());
132   }
133   if (myFeature) {  // TODO: generate an error if feature was not created
134     myIsModified = true;
135     // Model update should call "execute" of a feature.
136     //myFeature->execute();
137     // Init default values
138     /*QList<ModuleBase_ModelWidget*> aWidgets = getDescription()->modelWidgets();
139      QList<ModuleBase_ModelWidget*>::const_iterator anIt = aWidgets.begin(), aLast = aWidgets.end();
140      for (; anIt != aLast; anIt++) {
141      (*anIt)->storeValue(aFeature);
142      }*/
143   }
144
145   if (theFlushMessage)
146     flushCreated();
147   return myFeature;
148 }
149
150 void ModuleBase_Operation::setFeature(FeaturePtr theFeature)
151 {
152   myFeature = theFeature;
153   myIsEditing = true;
154 }
155
156 bool ModuleBase_Operation::hasObject(ObjectPtr theObj) const
157 {
158   FeaturePtr aFeature = feature();
159   if (aFeature) {
160     if (aFeature == theObj)
161       return true;
162     std::list<ResultPtr> aResults = aFeature->results();
163     std::list<ResultPtr>::const_iterator aIt;
164     for (aIt = aResults.cbegin(); aIt != aResults.cend(); ++aIt) {
165       if ((*aIt) == theObj)
166         return true;
167     }
168   }
169   return false;
170 }
171
172
173 boost::shared_ptr<ModelAPI_Document> ModuleBase_Operation::document() const
174 {
175   return ModelAPI_Session::get()->moduleDocument();
176 }
177
178
179 void ModuleBase_Operation::start()
180 {
181   ModelAPI_Session::get()->startOperation();
182
183   startOperation();
184   emit started();
185 }
186
187 void ModuleBase_Operation::resume()
188 {
189   if (myPropertyPanel)
190     connect(myPropertyPanel, SIGNAL(widgetActivated(ModuleBase_ModelWidget*)),
191             this,            SLOT(onWidgetActivated(ModuleBase_ModelWidget*)));
192   emit resumed();
193 }
194
195 void ModuleBase_Operation::abort()
196 {
197   abortOperation();
198   emit aborted();
199   if (myPropertyPanel)
200     disconnect(myPropertyPanel, 0, this, 0);
201
202   stopOperation();
203
204   ModelAPI_Session::get()->abortOperation();
205   emit stopped();
206 }
207
208 bool ModuleBase_Operation::commit()
209 {
210   if (canBeCommitted()) {
211     commitOperation();
212     emit committed();
213
214   if (myPropertyPanel)
215     disconnect(myPropertyPanel, 0, this, 0);
216
217     stopOperation();
218     ModelAPI_Session::get()->finishOperation();
219
220     emit stopped();
221
222     afterCommitOperation();
223     return true;
224   }
225   return false;
226 }
227
228 void ModuleBase_Operation::setRunning(bool theState)
229 {
230   if (!theState) {
231     abort();
232   }
233 }
234
235 void ModuleBase_Operation::activateByPreselection()
236 {
237   if (!myPropertyPanel)
238     return;
239   ModuleBase_ModelWidget* aActiveWgt = myPropertyPanel->activeWidget();
240   if ((myPreSelection.size() > 0) && aActiveWgt) {
241     const ModuleBase_ViewerPrs& aPrs = myPreSelection.front();
242     ModuleBase_WidgetValueFeature aValue;
243     aValue.setObject(aPrs.object());
244     if (aActiveWgt->setValue(&aValue)) {
245       myPreSelection.remove(aPrs);
246       myPropertyPanel->activateNextWidget();
247     }
248     // If preselection is enough to make a valid feature - apply it immediately
249   }
250 }
251
252 void ModuleBase_Operation::initSelection(
253     const std::list<ModuleBase_ViewerPrs>& theSelected,
254     const std::list<ModuleBase_ViewerPrs>& /*theHighlighted*/)
255 {
256   myPreSelection = theSelected;
257 }
258
259 void ModuleBase_Operation::onWidgetActivated(ModuleBase_ModelWidget* theWidget)
260 {
261   activateByPreselection();
262   //if (theWidget && myPropertyPanel) {
263   //  myPropertyPanel->activateNextWidget();
264   ////  //emit activateNextWidget(myActiveWidget);
265   //}
266 }
267
268 bool ModuleBase_Operation::setWidgetValue(ObjectPtr theFeature, double theX, double theY)
269 {
270   ModuleBase_ModelWidget* aActiveWgt = myPropertyPanel->activeWidget();
271   if (!aActiveWgt)
272     return false;
273   ModuleBase_WidgetValueFeature* aValue = new ModuleBase_WidgetValueFeature();
274   aValue->setObject(theFeature);
275   aValue->setPoint(boost::shared_ptr<GeomAPI_Pnt2d>(new GeomAPI_Pnt2d(theX, theY)));
276   bool isApplyed = aActiveWgt->setValue(aValue);
277
278   delete aValue;
279   myIsModified = (myIsModified || isApplyed);
280   return isApplyed;
281 }
282
283
284 void ModuleBase_Operation::setPropertyPanel(ModuleBase_IPropertyPanel* theProp) 
285
286   myPropertyPanel = theProp; 
287   connect(myPropertyPanel, SIGNAL(widgetActivated(ModuleBase_ModelWidget*)), this,
288           SLOT(onWidgetActivated(ModuleBase_ModelWidget*)));
289 }