Salome HOME
Merge from V6_main 01/04/2013
[modules/kernel.git] / src / SALOMEDSImpl / SALOMEDSImpl_AttributeStudyProperties.cxx
1 // Copyright (C) 2007-2013  CEA/DEN, EDF R&D, OPEN CASCADE
2 //
3 // Copyright (C) 2003-2007  OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
4 // CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
5 //
6 // This library is free software; you can redistribute it and/or
7 // modify it under the terms of the GNU Lesser General Public
8 // License as published by the Free Software Foundation; either
9 // version 2.1 of the License.
10 //
11 // This library is distributed in the hope that it will be useful,
12 // but WITHOUT ANY WARRANTY; without even the implied warranty of
13 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 // Lesser General Public License for more details.
15 //
16 // You should have received a copy of the GNU Lesser General Public
17 // License along with this library; if not, write to the Free Software
18 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
19 //
20 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
21 //
22
23 //  File   : SALOMEDSImpl_AttributeStudyProperties.cxx
24 //  Author : Sergey RUIN
25 //  Module : SALOME
26 //
27 #include "SALOMEDSImpl_AttributeStudyProperties.hxx"
28 #include <string.h>
29
30 const std::string& SALOMEDSImpl_AttributeStudyProperties::GetID()
31 {
32   static std::string SALOMEDSImpl_AttributeStudyPropertiesID ("128371A2-8F52-11d6-A8A3-0001021E8C7F");
33   return SALOMEDSImpl_AttributeStudyPropertiesID;
34 }
35
36 SALOMEDSImpl_AttributeStudyProperties* SALOMEDSImpl_AttributeStudyProperties::Set(const DF_Label& label)
37 {
38   SALOMEDSImpl_AttributeStudyProperties* A = NULL;
39   if (!(A=(SALOMEDSImpl_AttributeStudyProperties*)label.FindAttribute(SALOMEDSImpl_AttributeStudyProperties::GetID()))) {
40     A = new SALOMEDSImpl_AttributeStudyProperties();
41     label.AddAttribute(A);
42   }
43   return A;
44 }
45
46 SALOMEDSImpl_AttributeStudyProperties::SALOMEDSImpl_AttributeStudyProperties()
47 :SALOMEDSImpl_GenericAttribute("AttributeStudyProperties")
48 {
49   myLocked = false;
50   myLockChanged = false;
51   Init();
52 }
53
54 void SALOMEDSImpl_AttributeStudyProperties::Init()
55 {
56   myUserName.clear();
57   myMinute.clear();
58   myHour.clear();
59   myDay.clear();
60   myMonth.clear();
61   myYear.clear();
62   myMode = 0; // none
63   myComponentVersions.clear();
64 }
65
66 void SALOMEDSImpl_AttributeStudyProperties::SetModification(const std::string& theUserName,
67                                                             const int            theMinute,
68                                                             const int            theHour,
69                                                             const int            theDay,
70                                                             const int            theMonth,
71                                                             const int            theYear)
72 {
73   if (theMinute<0 || theMinute>60 || theHour<0 || theHour>24 ||
74       theDay<0 || theDay>31 || theMonth<0 || theMonth>12)
75     return;
76
77   CheckLocked();
78   Backup();
79
80   myUserName.push_back(theUserName);
81   myMinute.push_back(theMinute);
82   myHour.push_back(theHour);
83   myDay.push_back(theDay);
84   myMonth.push_back(theMonth);
85   myYear.push_back(theYear);
86 }
87
88 void SALOMEDSImpl_AttributeStudyProperties::GetModifications
89                   (std::vector<std::string>& theUserNames,
90                    std::vector<int>&    theMinutes,
91                    std::vector<int>&    theHours,
92                    std::vector<int>&    theDays,
93                    std::vector<int>&    theMonths,
94                    std::vector<int>&    theYears) const
95 {
96   theUserNames = myUserName;
97   theMinutes = myMinute;
98   theHours = myHour;
99   theDays = myDay;
100   theMonths = myMonth;
101   theYears = myYear;
102 }
103
104 std::string SALOMEDSImpl_AttributeStudyProperties::GetCreatorName() const
105 {
106   return myUserName.empty() ? std::string("") : myUserName[0];
107 }
108
109 bool SALOMEDSImpl_AttributeStudyProperties::GetCreationDate
110                               (int&           theMinute,
111                                int&           theHour,
112                                int&           theDay,
113                                int&           theMonth,
114                                int&           theYear) const
115 {
116   if (myMinute.size() != 0) {
117     theMinute = myMinute[0];
118     theHour = myHour[0];
119     theDay = myDay[0];
120     theMonth = myMonth[0];
121     theYear = myYear[0];
122     return true;
123   }
124   return false;
125 }
126
127 void SALOMEDSImpl_AttributeStudyProperties::ChangeCreatorName(const std::string& theName)
128 {
129   if (myUserName.size() > 0) {
130     CheckLocked();
131     Backup();
132     myUserName[0] = theName;
133   }
134 }
135
136 void SALOMEDSImpl_AttributeStudyProperties::SetCreationMode(const int theMode)
137 {
138   if (theMode == myMode) return;
139   CheckLocked();
140   Backup();
141   myMode = theMode;
142 }
143
144 int SALOMEDSImpl_AttributeStudyProperties::GetCreationMode() const
145 {
146   return myMode;
147 }
148
149 void SALOMEDSImpl_AttributeStudyProperties::SetModified(const int theModified)
150 {
151   myModified = theModified;
152 }
153
154 bool SALOMEDSImpl_AttributeStudyProperties::IsModified() const
155 {
156   return (myModified != 0);
157 }
158
159 int SALOMEDSImpl_AttributeStudyProperties::GetModified() const
160 {
161   return myModified;
162 }
163
164 void SALOMEDSImpl_AttributeStudyProperties::SetLocked(const bool theLocked)
165 {
166 //  Backup();
167   if (myLocked != theLocked) {
168     myLockChanged = true;
169     myLocked = theLocked;
170   }
171 }
172
173 bool SALOMEDSImpl_AttributeStudyProperties::IsLocked() const
174 {
175   return myLocked;
176 }
177
178 bool SALOMEDSImpl_AttributeStudyProperties::IsLockChanged(const bool theErase)
179 {
180   if (!myLockChanged) return false;
181   if (theErase) myLockChanged = false;
182   return true;
183 }
184
185 const std::string& SALOMEDSImpl_AttributeStudyProperties::ID() const
186 {
187   return GetID();
188 }
189
190 void SALOMEDSImpl_AttributeStudyProperties::Restore(DF_Attribute* with)
191 {
192   SALOMEDSImpl_AttributeStudyProperties* aProp =
193     dynamic_cast<SALOMEDSImpl_AttributeStudyProperties*>(with);
194
195   Init();
196   std::vector<std::string> aNames;
197   std::vector<int> aMinutes, aHours, aDays, aMonths, aYears;
198   aProp->GetModifications(aNames, aMinutes, aHours, aDays, aMonths, aYears);
199   for (int i = 0, len = aNames.size(); i < len; i++) {
200     myUserName.push_back(aNames[i]);
201     myMinute.push_back(aMinutes[i]);
202     myHour.push_back(aHours[i]);
203     myDay.push_back(aDays[i]);
204     myMonth.push_back(aMonths[i]);
205     myYear.push_back(aYears[i]);
206   }
207   myMode = aProp->GetCreationMode();
208   myComponentVersions = aProp->GetComponentsVersions();
209 //  myModified = aProp->GetModified();
210 //  myLocked = aProp->IsLocked();
211 }
212
213 DF_Attribute* SALOMEDSImpl_AttributeStudyProperties::NewEmpty() const
214 {
215   return new SALOMEDSImpl_AttributeStudyProperties();
216 }
217
218 void SALOMEDSImpl_AttributeStudyProperties::Paste(DF_Attribute* into)
219 {
220   SALOMEDSImpl_AttributeStudyProperties* aProp =
221     dynamic_cast<SALOMEDSImpl_AttributeStudyProperties*>(into);
222   aProp->Init();
223
224   int i;
225   for(i = 0; i < myUserName.size(); i++) {
226     aProp->SetModification(myUserName[i],
227                            myMinute[i], myHour[i],
228                            myDay[i], myMonth[i], myYear[i]);
229   }
230
231   aProp->SetCreationMode(myMode);
232   aProp->SetComponentsVersions( myComponentVersions );
233 //  aProp->SetModified(myModified);
234 //  aProp->SetLocked(myLocked);
235 }
236
237
238 std::string SALOMEDSImpl_AttributeStudyProperties::Save()
239 {
240   std::vector<std::string> aNames;
241   std::vector<int> aMinutes, aHours, aDays, aMonths, aYears;
242   GetModifications(aNames, aMinutes, aHours, aDays, aMonths, aYears);
243
244   int aLength, anIndex, unitsSize = 0, commentSize = 0;;
245   for (aLength = 0, anIndex = aNames.size()-1; anIndex >= 0; anIndex--)
246     aLength += aNames[anIndex].size() + 1;
247
248   std::string units = GetUnits();
249   std::string comment = GetComment();
250
251   int aLength1 = 0;
252   std::map<std::string, std::string> versions;
253   versionMap::const_iterator it;
254   for (aLength1 = 0, it = myComponentVersions.begin(); it != myComponentVersions.end(); ++it ) {
255     std::string vlist = "";
256     versionList vl = it->second;
257     versionList::const_iterator vlit;
258     for ( vlit = vl.begin(); vlit != vl.end(); ++vlit ) {
259       if ( vlist != "" ) vlist += ";";
260       vlist += *vlit;
261     }
262     versions[ it->first ] = vlist;
263     aLength1 += it->first.size() + vlist.size() + 2;
264   }
265   
266   unitsSize = units.size();
267   commentSize = comment.size();
268
269   char* aProperty = new char[3 + aLength + 12 * aNames.size() + 1 + unitsSize + 1 + commentSize + 1 + aLength1 ];
270
271   char crMode = (char)GetCreationMode();
272
273   sprintf(aProperty,"%c%c", crMode, IsLocked()?'l':'u');
274
275   aLength = aNames.size();
276   int a = 2;
277   for (anIndex = 0; anIndex  < aLength; anIndex++) {
278     sprintf(&(aProperty[a]),"%2d%2d%2d%2d%4d%s",
279             (int)(aMinutes[anIndex]),
280             (int)(aHours[anIndex]),
281             (int)(aDays[anIndex]),
282             (int)(aMonths[anIndex]),
283             (int)(aYears[anIndex]),
284             (char*)(aNames[anIndex].c_str()));
285     a = strlen(aProperty);
286     aProperty[a++] = 1;
287   }
288
289   //Write delimeter of the section to define end of the modifications section
290   aProperty[a++] = 30;
291
292   //Write units if need
293   if(units.size() > 0) {
294     sprintf(&(aProperty[a]),"%s",units.c_str());
295     a = strlen(aProperty);
296   }
297
298   aProperty[a++] = 1; //delimeter of the units and comments
299
300   //Write comments if need
301   if(comment.size() > 0) {
302     sprintf(&(aProperty[a]),"%s",comment.c_str());
303     a = strlen(aProperty);
304   }
305   
306   aProperty[a++] = 30; //delimeter of the component versions
307
308   std::map<std::string, std::string>::const_iterator versionsIt;
309   for ( versionsIt = versions.begin(); versionsIt != versions.end(); ++versionsIt ) {
310     sprintf(&(aProperty[a]),"%s=%s",
311             (char*)(versionsIt->first.c_str()),
312             (char*)(versionsIt->second.c_str()));
313     a = strlen(aProperty);
314     aProperty[a++] = 1;
315   }
316
317   aProperty[a] = 0;
318   std::string prop(aProperty);
319   delete aProperty;
320
321   return prop;
322 }
323
324 void SALOMEDSImpl_AttributeStudyProperties::SetUnits(const std::string& theUnits)
325 {
326   if(myUnits == theUnits)
327     return;
328
329   CheckLocked();
330   Backup();
331
332   myUnits = theUnits;
333 }
334
335 std::string SALOMEDSImpl_AttributeStudyProperties::GetUnits() const
336 {
337   return myUnits;
338 }
339
340 void SALOMEDSImpl_AttributeStudyProperties::SetComment(const std::string& theComment)
341 {
342   if(myComment == theComment)
343     return;
344
345   CheckLocked();
346   Backup();
347
348   myComment = theComment;
349 }
350
351 std::string SALOMEDSImpl_AttributeStudyProperties::GetComment() const 
352 {
353   return myComment;
354 }
355
356 void SALOMEDSImpl_AttributeStudyProperties::SetComponentVersion(const std::string& theComponent, const std::string& theVersion)
357 {
358   if (!theComponent.empty()) {
359     CheckLocked();
360     Backup();
361     if (myComponentVersions.find(theComponent) == myComponentVersions.end()) myComponentVersions[theComponent] = versionList();
362     if (myComponentVersions[theComponent].empty() || myComponentVersions[theComponent].back() != theVersion)
363       myComponentVersions[theComponent].push_back(theVersion);
364   }
365 }
366
367 std::vector<std::string> SALOMEDSImpl_AttributeStudyProperties::GetStoredComponents() const
368 {
369   std::vector<std::string> components;
370   versionMap::const_iterator it;  
371   for (it = myComponentVersions.begin(); it != myComponentVersions.end(); ++it)
372     components.push_back(it->first);
373   return components;
374 }
375
376 std::string SALOMEDSImpl_AttributeStudyProperties::GetComponentVersion(const std::string& theComponent) const
377 {
378   versionList versions = GetComponentVersions(theComponent);
379   return versions.size() > 0 ? versions[0] : std::string("");
380 }
381
382 std::vector<std::string> SALOMEDSImpl_AttributeStudyProperties::GetComponentVersions(const std::string& theComponent) const
383 {
384   versionList versions;
385   versionMap::const_iterator it = myComponentVersions.find(theComponent);
386   if ( it != myComponentVersions.end() ) versions = it->second;
387   return versions;
388 }
389
390 std::map< std::string, std::vector<std::string> > SALOMEDSImpl_AttributeStudyProperties::GetComponentsVersions() const
391 {
392   return myComponentVersions;
393 }
394
395 void SALOMEDSImpl_AttributeStudyProperties::SetComponentsVersions( const std::map< std::string, std::vector<std::string> >& theVersions )
396 {
397   myComponentVersions = theVersions;
398 }
399
400 void SALOMEDSImpl_AttributeStudyProperties::Load(const std::string& value)
401 {
402   char* aCopy = (char*)value.c_str();
403
404   int crMode = (int)aCopy[0];
405   SetCreationMode(crMode);
406
407   int anIndex;
408   // number 13 below is minimal size of modification data record, which has form:
409   // mmhhddMMyyyyname1, where
410   // - mm:   minute = 2 bytes
411   // - hh:   hour   = 2 bytes
412   // - dd:   day    = 2 bytes
413   // - MM:   month  = 2 bytes
414   // - yyyy: year   = 4 bytes
415   // - name: user's name = arbitrary value, minimal length is 0 bytes
416   // - 1   : records delimiter = 1 byte  
417   for (anIndex = 2; anIndex + 13 < value.size() ;) {
418     char str[10];
419     int aMinute, aHour, aDay, aMonth, aYear;
420     str[0] = aCopy[anIndex++];
421     str[1] = aCopy[anIndex++];
422     str[2] = 0;
423     aMinute = atoi(str);
424     str[0] = aCopy[anIndex++];
425     str[1] = aCopy[anIndex++];
426     aHour =  atoi(str);
427     str[0] = aCopy[anIndex++];
428     str[1] = aCopy[anIndex++];
429     aDay =  atoi(str);
430     str[0] = aCopy[anIndex++];
431     str[1] = aCopy[anIndex++];
432     aMonth =  atoi(str);
433     str[0] = aCopy[anIndex++];
434     str[1] = aCopy[anIndex++];
435     str[2] = aCopy[anIndex++];
436     str[3] = aCopy[anIndex++];
437     str[4] = 0;
438     aYear = atoi(str);
439
440     int aNameSize;
441     for(aNameSize = 0; aCopy[anIndex+aNameSize]!=1; aNameSize++);
442     char *aName = new char[aNameSize+1];
443     strncpy(aName, &(aCopy[anIndex]), aNameSize);
444     aName[aNameSize] = 0;
445     SetModification(aName,aMinute,aHour,aDay,aMonth,aYear);
446     delete [] (aName);
447     anIndex += aNameSize + 1;
448     
449     //Check end of the modifications section
450     if(anIndex < value.size() && aCopy[anIndex] == 30)
451       break;
452   }
453   
454   //Case when study contains units and comment properties
455   if( anIndex < value.size() ) {
456     anIndex++; //skip the delimeter of the sections: char(30)
457     int unitsSize;
458     for(unitsSize = 0; aCopy[anIndex+unitsSize] != 1; unitsSize++);
459
460     if(unitsSize > 0) {
461       char *anUnits = new char[unitsSize+1];
462       strncpy(anUnits, &(aCopy[anIndex]), unitsSize);
463       anUnits[unitsSize] = 0;
464       SetUnits(anUnits);
465       delete [] (anUnits);
466     }
467     anIndex += unitsSize + 1;
468
469     int commentSize;
470     for(commentSize = 0; aCopy[anIndex+commentSize] != 0 && aCopy[anIndex+commentSize] != 30; commentSize++);
471
472     if(commentSize > 0) {
473       char *aComment = new char[commentSize+1];
474       strncpy(aComment, &(aCopy[anIndex]), commentSize);
475       aComment[commentSize] = 0;
476       SetComment(aComment);
477       delete [] (aComment);
478     }
479     anIndex += commentSize + 1;
480   }
481
482   //Case when study contains components versions
483   if( anIndex < value.size() ) {
484     while ( anIndex < value.size() && aCopy[anIndex] != 0 ) {
485       int modSize;
486       for(modSize = 0; aCopy[anIndex+modSize] != '='; modSize++);
487       int verSize;
488       for(verSize = 0; aCopy[anIndex+modSize+1+verSize] != 1; verSize++);
489
490       if(modSize > 0) {
491         char *aModule = new char[modSize+1];
492         strncpy(aModule, &(aCopy[anIndex]), modSize);
493         aModule[modSize] = 0;
494         char *aVersions = new char[verSize+1];
495         if ( verSize > 0 )
496           strncpy(aVersions, &(aCopy[anIndex+modSize+1]), verSize);
497         aVersions[verSize] = 0;
498         
499         std::string mVersions = aVersions;
500         int start = 0, idx = mVersions.find( ';', start );
501         while ( idx != std::string::npos ) {
502           SetComponentVersion( aModule, mVersions.substr( start, idx-start ) );
503           start = idx + 1;
504           idx = mVersions.find( ';', start );
505         }
506         SetComponentVersion( aModule, mVersions.substr( start ) );
507
508         delete [] (aModule);
509         delete [] (aVersions);
510         anIndex += modSize + 1 + verSize + 1;
511       }
512     }
513   }
514   
515   if (aCopy[1] == 'l') {
516     SetLocked(true);
517   }
518   SetModified(0);  
519 }