Salome HOME
Transfer Part data from Part result sub-tree to Part feature sub-tree
[modules/shaper.git] / src / PartSet / PartSet_PartDataModel.cpp
1 // Copyright (C) 2014-20xx CEA/DEN, EDF R&D -->
2
3 #include "PartSet_PartDataModel.h"
4 #include "PartSet_Module.h"
5 #include "PartSet_DocumentDataModel.h"
6
7 #include <ModelAPI_Session.h>
8 #include <ModelAPI_Document.h>
9 #include <ModelAPI_Feature.h>
10 #include <ModelAPI_Result.h>
11 #include <ModelAPI_Data.h>
12 #include <ModelAPI_AttributeDocRef.h>
13 #include <ModelAPI_Object.h>
14 #include <ModelAPI_ResultPart.h>
15 #include <ModelAPI_ResultConstruction.h>
16 #include <ModelAPI_ResultParameter.h>
17 #include <ModelAPI_ResultBody.h>
18 #include <ModelAPI_ResultGroup.h>
19 #include <ModelAPI_AttributeDouble.h>
20
21 #include <QIcon>
22 #include <QBrush>
23
24
25 PartSet_TopDataModel::PartSet_TopDataModel(QObject* theParent)
26     : PartSet_FeaturesModel(theParent)
27 {
28 }
29
30 PartSet_TopDataModel::~PartSet_TopDataModel()
31 {
32 }
33
34 QVariant PartSet_TopDataModel::data(const QModelIndex& theIndex, int theRole) const
35 {
36   switch (theRole) {
37     case Qt::DisplayRole:
38       // return a name
39       switch (theIndex.internalId()) {
40         case ParamsFolder:
41           return tr("Parameters") + QString(" (%1)").arg(rowCount(theIndex));
42         case ParamObject: {
43           DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
44           ObjectPtr aObject = aRootDoc->object(ModelAPI_ResultParameter::group(), theIndex.row());
45           if (aObject) {
46             ResultParameterPtr aParam = std::dynamic_pointer_cast<ModelAPI_ResultParameter>(aObject);
47             AttributeDoublePtr aValueAttribute = aParam->data()->real(ModelAPI_ResultParameter::VALUE());
48             QString aVal = QString::number(aValueAttribute->value());
49             QString aTitle = QString(aObject->data()->name().c_str());
50             return aTitle + " = " + aVal;
51           }
52         }
53           break;
54         case ConstructFolder:
55           return tr("Constructions") + QString(" (%1)").arg(rowCount(theIndex));
56         case ConstructObject: {
57           DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
58           ObjectPtr aObject = aRootDoc->object(ModelAPI_ResultConstruction::group(),
59                                                theIndex.row());
60           if (aObject)
61             return aObject->data()->name().c_str();
62         }
63           break;
64         //case GroupsFolder:
65         //  return tr("Groups") + QString(" (%1)").arg(rowCount(theIndex));
66         //case GroupObject: {
67         //  DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
68         //  ObjectPtr aObject = aRootDoc->object(ModelAPI_ResultGroup::group(),
69         //                                       theIndex.row());
70         //  if (aObject)
71         //    return aObject->data()->name().c_str();
72         //}
73         //  break;
74       }
75       break;
76
77     case Qt::DecorationRole:
78       {
79       // return an Icon
80       switch (theIndex.internalId()) {
81         case ParamsFolder:
82           return QIcon(":pictures/params_folder.png");
83         case ConstructFolder:
84           return QIcon(":pictures/constr_folder.png");
85         case ConstructObject:
86           return QIcon(":pictures/constr_object.png");
87         //case GroupsFolder:
88         //  return QIcon(":pictures/constr_folder.png");
89         }
90       }
91       break;
92
93     case Qt::ToolTipRole:
94       // return Tooltip
95       break;
96     case Qt::ForegroundRole:
97       return QBrush(myItemsColor);
98       break;
99   }
100   return QVariant();
101 }
102
103 QVariant PartSet_TopDataModel::headerData(int section, Qt::Orientation orientation, int role) const
104 {
105   return QVariant();
106 }
107
108 int PartSet_TopDataModel::rowCount(const QModelIndex& theParent) const
109 {
110   if (!theParent.isValid())
111     return 2;  // In case of groups using it has to be +1
112
113   DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
114   if (theParent.internalId() == ParamsFolder)
115     return aRootDoc->size(ModelAPI_ResultParameter::group());
116
117   if (theParent.internalId() == ConstructFolder)
118     return aRootDoc->size(ModelAPI_ResultConstruction::group());
119
120   //if (theParent.internalId() == GroupsFolder)
121   //  return aRootDoc->size(ModelAPI_ResultGroup::group());
122
123   return 0;
124 }
125
126 int PartSet_TopDataModel::columnCount(const QModelIndex &parent) const
127 {
128   return 1;
129 }
130
131 QModelIndex PartSet_TopDataModel::index(int theRow, int theColumn, const QModelIndex& theParent) const
132 {
133   if (!theParent.isValid()) {
134     switch (theRow) {
135       case 0:
136         return createIndex(theRow, theColumn, (qint32) ParamsFolder);
137       case 1:
138         return createIndex(theRow, theColumn, (qint32) ConstructFolder);
139       //case 2:
140       //  return createIndex(theRow, theColumn, (qint32) GroupsFolder);
141     }
142   } else {
143     if (theParent.internalId() == ParamsFolder)
144       return createIndex(theRow, theColumn, (qint32) ParamObject);
145
146     if (theParent.internalId() == ConstructFolder)
147       return createIndex(theRow, theColumn, (qint32) ConstructObject);
148
149     //if (theParent.internalId() == GroupsFolder)
150     //  return createIndex(theRow, theColumn, (qint32) GroupObject);
151   }
152   return QModelIndex();
153 }
154
155 QModelIndex PartSet_TopDataModel::parent(const QModelIndex& theIndex) const
156 {
157   int aId = (int) theIndex.internalId();
158   switch (aId) {
159     case ParamsFolder:
160     case ConstructFolder:
161     //case GroupsFolder:
162       return QModelIndex();
163     case ParamObject:
164       return createIndex(0, 0, (qint32) ParamsFolder);
165     case ConstructObject:
166       return createIndex(1, 0, (qint32) ConstructFolder);
167     //case GroupObject:
168     //  return createIndex(2, 0, (qint32) GroupsFolder);
169   }
170   return QModelIndex();
171 }
172
173 bool PartSet_TopDataModel::hasChildren(const QModelIndex& theParent) const
174 {
175   return rowCount(theParent) > 0;
176 }
177
178 ObjectPtr PartSet_TopDataModel::object(const QModelIndex& theIndex) const
179 {
180   switch (theIndex.internalId()) {
181     case ParamsFolder:
182     case ConstructFolder:
183       return ObjectPtr();
184     case ParamObject: {
185       DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
186       return aRootDoc->object(ModelAPI_ResultParameter::group(), theIndex.row());
187     }
188     case ConstructObject: {
189       DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
190       return aRootDoc->object(ModelAPI_ResultConstruction::group(), theIndex.row());
191     }
192     //case GroupObject: {
193     //  DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
194     //  return aRootDoc->object(ModelAPI_ResultGroup::group(), theIndex.row());
195     //}
196   }
197   return ObjectPtr();
198 }
199
200 QModelIndex PartSet_TopDataModel::findParent(const ObjectPtr& theObject) const
201 {
202   return findGroup(theObject->groupName().c_str());
203 }
204
205 QModelIndex PartSet_TopDataModel::findGroup(const std::string& theGroup) const
206 {
207   if (theGroup == ModelAPI_ResultParameter::group())
208     return createIndex(0, 0, (qint32) ParamsFolder);
209   if (theGroup == ModelAPI_ResultConstruction::group())
210     return createIndex(1, 0, (qint32) ConstructFolder);
211   //if (theGroup == ModelAPI_ResultGroup::group())
212   //  return createIndex(2, 0, (qint32) ConstructFolder);
213   return QModelIndex();
214 }
215
216 QModelIndex PartSet_TopDataModel::objectIndex(const ObjectPtr& theObject) const
217 {
218   QModelIndex aIndex;
219   if (theObject) {
220     DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
221     std::string aGroup = theObject->groupName();
222     int aNb = aRootDoc->size(aGroup);
223     int aRow = -1;
224     for (int i = 0; i < aNb; i++) {
225       if (aRootDoc->object(aGroup, i) == theObject) {
226         aRow = i;
227         break;
228       }
229     }
230     if (aRow != -1) {
231       if (aGroup == ModelAPI_ResultParameter::group())
232         return createIndex(aRow, 0, (qint32) ParamObject);
233       if (aGroup == ModelAPI_ResultConstruction::group())
234         return createIndex(aRow, 0, (qint32) ConstructObject);
235       //if (aGroup == ModelAPI_ResultGroup::group())
236       //  return createIndex(aRow, 0, (qint32) GroupObject);
237     }
238   }
239   return aIndex;
240 }
241
242 //******************************************************************
243 //******************************************************************
244 //******************************************************************
245 PartSet_PartDataModel::PartSet_PartDataModel(QObject* theParent)
246     : PartSet_PartModel(theParent)
247 {
248 }
249
250 PartSet_PartDataModel::~PartSet_PartDataModel()
251 {
252 }
253
254 QVariant PartSet_PartDataModel::data(const QModelIndex& theIndex, int theRole) const
255 {
256   switch (theRole) {
257     case Qt::DisplayRole:
258       // return a name
259       switch (theIndex.internalId()) {
260         //case MyRoot: {
261         //  DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
262         //  ObjectPtr aObject = aRootDoc->object(ModelAPI_ResultPart::group(), myId);
263         //  if (aObject)
264         //    return std::dynamic_pointer_cast<ModelAPI_Object>(aObject)->data()->name().c_str();
265         //}
266         case ParamsFolder:
267           return tr("Parameters") + QString(" (%1)").arg(rowCount(theIndex));
268         case ConstructFolder:
269           return tr("Constructions") + QString(" (%1)").arg(rowCount(theIndex));
270         case BodiesFolder:
271           return tr("Bodies") + QString(" (%1)").arg(rowCount(theIndex));
272         case GroupsFolder:
273           return tr("Groups") + QString(" (%1)").arg(rowCount(theIndex));
274         case ParamObject: {
275           ObjectPtr aObject = partDocument()->object(ModelAPI_ResultParameter::group(),
276                                                      theIndex.row());
277           if (aObject) {
278             ResultParameterPtr aParam = std::dynamic_pointer_cast<ModelAPI_ResultParameter>(aObject);
279             AttributeDoublePtr aValueAttribute = aParam->data()->real(ModelAPI_ResultParameter::VALUE());
280             QString aVal = QString::number(aValueAttribute->value());
281             QString aTitle = QString(aObject->data()->name().c_str());
282             return aTitle + " = " + aVal;
283           }
284         }
285           break;
286         case ConstructObject: {
287           ObjectPtr aObject = partDocument()->object(ModelAPI_ResultConstruction::group(),
288                                                      theIndex.row());
289           if (aObject)
290             return std::dynamic_pointer_cast<ModelAPI_Object>(aObject)->data()->name().c_str();
291         }
292           break;
293         case BodiesObject: {
294           ObjectPtr aObject = partDocument()->object(ModelAPI_ResultBody::group(), theIndex.row());
295           if (aObject)
296             return aObject->data()->name().c_str();
297         }
298           break;
299         case GroupObject: {
300           ObjectPtr aObject = partDocument()->object(ModelAPI_ResultGroup::group(), theIndex.row());
301           if (aObject)
302             return aObject->data()->name().c_str();
303         }
304         case HistoryObject: {
305           ObjectPtr aObject = partDocument()->object(ModelAPI_Feature::group(), theIndex.row() - getRowsNumber());
306           if (aObject)
307             return aObject->data()->name().c_str();
308         }
309       }
310       break;
311     case Qt::DecorationRole:
312       // return an Icon
313       switch (theIndex.internalId()) {
314         //case MyRoot:
315         //  return QIcon(":pictures/part_ico.png");
316         case ParamsFolder:
317           return QIcon(":pictures/params_folder.png");
318         case ConstructFolder:
319         case BodiesFolder:
320           return QIcon(":pictures/constr_folder.png");
321         case GroupsFolder:
322           return QIcon(":pictures/constr_folder.png");
323         case ConstructObject:
324         case GroupObject:
325         case BodiesObject: {
326           std::string aGroup = theIndex.internalId() == ConstructObject ?
327             ModelAPI_ResultConstruction::group() : ModelAPI_ResultBody::group();
328           ObjectPtr anObject = partDocument()->object(aGroup, theIndex.row());
329           if (anObject && anObject->data() && 
330               anObject->data()->execState() == ModelAPI_StateMustBeUpdated) {
331             return QIcon(":pictures/constr_object_modified.png");
332           }
333           return QIcon(":pictures/constr_object.png");
334         }
335         case HistoryObject: {
336           ObjectPtr aObject = partDocument()->object(ModelAPI_Feature::group(), theIndex.row() - getRowsNumber());
337           FeaturePtr aFeature = std::dynamic_pointer_cast<ModelAPI_Feature>(aObject);
338           if (aFeature)
339             return PartSet_DocumentDataModel::featureIcon(aFeature);
340         }
341       }
342       break;
343     case Qt::ToolTipRole:
344       // return Tooltip
345       break;
346     case Qt::ForegroundRole:
347       return QBrush(myItemsColor);
348       break;
349   }
350   return QVariant();
351 }
352
353 QVariant PartSet_PartDataModel::headerData(int section, Qt::Orientation orientation, int role) const
354 {
355   return QVariant();
356 }
357
358 int PartSet_PartDataModel::rowCount(const QModelIndex& parent) const
359 {
360   if (!parent.isValid()) {
361     //DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
362     //if (aRootDoc->object(ModelAPI_ResultPart::group(), myId))
363     //  return 1;
364     //else
365     //  return 0;
366     DocumentPtr aDoc = partDocument();
367     if (aDoc.get()) {
368       return getRowsNumber() + aDoc->size(ModelAPI_Feature::group());
369     } else 
370       return 0;
371   }
372   switch (parent.internalId()) {
373     //case MyRoot:
374     //  {
375     //    DocumentPtr aDoc = partDocument();
376     //    if (aDoc) {
377     //      return getRowsNumber() + aDoc->size(ModelAPI_Feature::group());
378     //    } else 
379     //      return 0;
380     //  }
381     case ParamsFolder:
382       return partDocument()->size(ModelAPI_ResultParameter::group());
383     case ConstructFolder:
384       return partDocument()->size(ModelAPI_ResultConstruction::group());
385     case BodiesFolder:
386       return partDocument()->size(ModelAPI_ResultBody::group());
387     case GroupsFolder:
388       return partDocument()->size(ModelAPI_ResultGroup::group());
389   }
390   return 0;
391 }
392
393 int PartSet_PartDataModel::columnCount(const QModelIndex &parent) const
394 {
395   return 1;
396 }
397
398 QModelIndex PartSet_PartDataModel::index(int theRow, int theColumn, const QModelIndex &theParent) const
399 {
400   if (!theParent.isValid()) {
401   //  return createIndex(theRow, 0, (qint32) MyRoot);
402     switch (theRow) {
403       case 0:
404         return createIndex(theRow, theColumn, (qint32) ParamsFolder);
405       case 1:
406         return createIndex(theRow, theColumn, (qint32) ConstructFolder);
407       case 2:
408         return createIndex(theRow, theColumn, (qint32) BodiesFolder);
409       case 3:
410         {
411         int aSize = partDocument()->size(ModelAPI_ResultGroup::group());
412         if (aSize > 0)
413           return createIndex(theRow, theColumn, (qint32) GroupsFolder);
414         else
415           return createIndex(theRow, theColumn, (qint32) HistoryObject);
416         }
417       default:
418         return createIndex(theRow, theColumn, (qint32) HistoryObject);
419     }
420   } else {
421     int aId = (int) theParent.internalId();
422     switch (aId) {
423       //case MyRoot:
424       //  switch (theRow) {
425       //    case 0:
426       //      return createIndex(theRow, 0, (qint32) ParamsFolder);
427       //    case 1:
428       //      return createIndex(theRow, 0, (qint32) ConstructFolder);
429       //    case 2:
430       //      return createIndex(theRow, 0, (qint32) BodiesFolder);
431       //    case 3:
432       //      {
433       //      int aSize = partDocument()->size(ModelAPI_ResultGroup::group());
434       //      if (aSize > 0)
435       //        return createIndex(theRow, 0, (qint32) GroupsFolder);
436       //      else
437       //        return createIndex(theRow, theColumn, (qint32) HistoryObject);
438       //      }
439       //    default:
440       //      return createIndex(theRow, theColumn, (qint32) HistoryObject);
441       //  }
442       case ParamsFolder:
443         return createIndex(theRow, theColumn, (qint32) ParamObject);
444       case ConstructFolder:
445         return createIndex(theRow, theColumn, (qint32) ConstructObject);
446       case BodiesFolder:
447         return createIndex(theRow, theColumn, (qint32) BodiesObject);
448       case GroupsFolder:
449         return createIndex(theRow, theColumn, (qint32) GroupObject);
450     }
451   }
452   return QModelIndex();
453 }
454
455 QModelIndex PartSet_PartDataModel::parent(const QModelIndex& theIndex) const
456 {
457   switch (theIndex.internalId()) {
458     //case MyRoot:
459     //  return QModelIndex();
460     case ParamsFolder:
461     case ConstructFolder:
462     case BodiesFolder:
463     case GroupsFolder:
464     case HistoryObject:
465       return QModelIndex();
466       //return createIndex(0, 0, (qint32) MyRoot);
467
468     case ParamObject:
469       return createIndex(0, theIndex.column(), (qint32) ParamsFolder);
470     case ConstructObject:
471       return createIndex(1, theIndex.column(), (qint32) ConstructFolder);
472     case BodiesObject:
473       return createIndex(2, theIndex.column(), (qint32) BodiesFolder);
474     case GroupObject:
475       return createIndex(3, theIndex.column(), (qint32) GroupsFolder);
476   }
477   return QModelIndex();
478 }
479
480 bool PartSet_PartDataModel::hasChildren(const QModelIndex& theParent) const
481 {
482   return rowCount(theParent) > 0;
483 }
484
485 DocumentPtr PartSet_PartDataModel::partDocument() const
486 {
487   DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
488   //ObjectPtr aObject = aRootDoc->object(ModelAPI_ResultPart::group(), myId);
489   ObjectPtr aObject = aRootDoc->object(ModelAPI_Feature::group(), myId);
490   FeaturePtr aFeature = ModelAPI_Feature::feature(aObject);
491   ResultPartPtr aPart = std::dynamic_pointer_cast<ModelAPI_ResultPart>(aFeature->firstResult()); 
492   //std::dynamic_pointer_cast<ModelAPI_ResultPart>(aObject);
493   return aPart->partDoc();
494 }
495
496 ObjectPtr PartSet_PartDataModel::object(const QModelIndex& theIndex) const
497 {
498   switch (theIndex.internalId()) {
499     //case MyRoot: {
500     //  DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
501     //  return aRootDoc->object(ModelAPI_ResultPart::group(), myId);
502     //}
503     case ParamsFolder:
504     case ConstructFolder:
505     case BodiesFolder:
506     case GroupsFolder:
507       return ObjectPtr();
508
509     case ParamObject:
510       return partDocument()->object(ModelAPI_ResultParameter::group(), theIndex.row());
511     case ConstructObject:
512       return partDocument()->object(ModelAPI_ResultConstruction::group(), theIndex.row());
513     case BodiesObject:
514       return partDocument()->object(ModelAPI_ResultBody::group(), theIndex.row());
515     case GroupObject:
516       return partDocument()->object(ModelAPI_ResultGroup::group(), theIndex.row());
517     case HistoryObject:
518       return partDocument()->object(ModelAPI_Feature::group(), theIndex.row() - getRowsNumber());
519   }
520   return ObjectPtr();
521 }
522
523 bool PartSet_PartDataModel::hasDocument(const DocumentPtr& theDoc) const
524 {
525   return (partDocument() == theDoc);
526 }
527
528 QModelIndex PartSet_PartDataModel::findParent(const ObjectPtr& theObject) const
529 {
530   return findGroup(theObject->groupName().c_str());
531 }
532
533 QModelIndex PartSet_PartDataModel::findGroup(const std::string& theGroup) const
534 {
535   if (theGroup == ModelAPI_ResultParameter::group())
536     return createIndex(0, 0, (qint32) ParamsFolder);
537   if (theGroup == ModelAPI_ResultConstruction::group())
538     return createIndex(1, 0, (qint32) ConstructFolder);
539   if (theGroup == ModelAPI_ResultBody::group())
540     return createIndex(2, 0, (qint32) BodiesFolder);
541   if (theGroup == ModelAPI_ResultGroup::group())
542     return createIndex(3, 0, (qint32) GroupsFolder);
543   return QModelIndex();
544 }
545
546 ResultPartPtr PartSet_PartDataModel::part() const
547 {
548   DocumentPtr aRootDoc = ModelAPI_Session::get()->moduleDocument();
549   ObjectPtr aObj = aRootDoc->object(ModelAPI_ResultPart::group(), myId);
550   return std::dynamic_pointer_cast<ModelAPI_ResultPart>(aObj);
551 }
552
553 QModelIndex PartSet_PartDataModel::objectIndex(const ObjectPtr& theObject) const
554 {
555   QModelIndex aIndex;
556   if (theObject) {
557     if (part() == theObject)
558       return aIndex;
559
560     std::string aGroup = theObject->groupName();
561     DocumentPtr aDoc = theObject->document();
562     int aNb = aDoc->size(aGroup);
563     int aRow = -1;
564     for (int i = 0; i < aNb; i++) {
565       if (aDoc->object(aGroup, i) == theObject) {
566         aRow = i;
567         break;
568       }
569     }
570     if (aRow == -1)
571       return aIndex;
572     if (aGroup == ModelAPI_ResultParameter::group())
573       return createIndex(aRow, 0, (qint32) ParamObject);
574     else if (aGroup == ModelAPI_ResultConstruction::group())
575       return createIndex(aRow, 0, (qint32) ConstructObject);
576     else if (aGroup == ModelAPI_ResultBody::group())
577       return createIndex(aRow, 0, (qint32) BodiesObject);
578     else if (aGroup == ModelAPI_ResultGroup::group())
579       return createIndex(aRow, 0, (qint32) GroupObject);
580     else
581       return createIndex(aRow + getRowsNumber(), 0, (qint32) HistoryObject);
582   }
583   return aIndex;
584 }
585
586
587 int PartSet_PartDataModel::getRowsNumber() const
588 {
589   int aSize = partDocument()->size(ModelAPI_ResultGroup::group());
590   if (aSize == 0) // If there are no groups then do not show group folder
591     return 3;
592   return 4;
593 }