Salome HOME
Merge from V6_main (04/10/2012)
[modules/paravis.git] / src / Plugins / MedReader / IO / vtkMedField.cxx
1 // Copyright (C) 2010-2012  CEA/DEN, EDF R&D
2 //
3 // This library is free software; you can redistribute it and/or
4 // modify it under the terms of the GNU Lesser General Public
5 // License as published by the Free Software Foundation; either
6 // version 2.1 of the License.
7 //
8 // This library is distributed in the hope that it will be useful,
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 // Lesser General Public License for more details.
12 //
13 // You should have received a copy of the GNU Lesser General Public
14 // License along with this library; if not, write to the Free Software
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 // See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19
20 #include "vtkMedField.h"
21
22 #include "vtkObjectFactory.h"
23 #include "vtkSmartPointer.h"
24 #include "vtkStringArray.h"
25 #include "vtkMedFieldOverEntity.h"
26 #include "vtkMedFieldStep.h"
27 #include "vtkMedUtilities.h"
28 #include "vtkMedFieldOnProfile.h"
29 #include "vtkMedInterpolation.h"
30 #include "vtkMedFile.h"
31
32 #include <string>
33 #include <map>
34 using namespace std;
35
36 vtkCxxGetObjectVectorMacro(vtkMedField, Interpolation, vtkMedInterpolation);
37 vtkCxxSetObjectVectorMacro(vtkMedField, Interpolation, vtkMedInterpolation);
38
39 vtkCxxSetObjectMacro(vtkMedField, ParentFile, vtkMedFile);
40
41 vtkCxxRevisionMacro(vtkMedField, "$Revision$")
42 vtkStandardNewMacro(vtkMedField)
43
44 vtkMedField::vtkMedField()
45 {
46   this->NumberOfComponent = -1;
47   this->DataType = MED_FLOAT64;
48   this->Name = NULL;
49   this->MeshName = NULL;
50   this->TimeUnit = NULL;
51   this->FieldStep = new vtkMedComputeStepMap<vtkMedFieldStep> ();
52   this->Unit = vtkStringArray::New();
53   this->ComponentName = vtkStringArray::New();
54   this->Interpolation = new vtkObjectVector<vtkMedInterpolation> ();
55   this->MedIterator = -1;
56   this->FieldType = UnknownFieldType;
57   this->ParentFile = NULL;
58   this->Local = 1;
59 }
60
61 vtkMedField::~vtkMedField()
62 {
63   this->SetName(NULL);
64   this->SetMeshName(NULL);
65   this->SetTimeUnit(NULL);
66   delete this->FieldStep;
67   this->Unit->Delete();
68   this->ComponentName->Delete();
69 }
70
71 void vtkMedField::ComputeFieldType()
72 {
73   this->FieldType = UnknownFieldType;
74
75   // look for the med_entity_type
76   // on which this field is.
77   for(int sid = 0; sid < this->GetNumberOfFieldStep(); sid++)
78     {
79     vtkMedFieldStep* step = this->GetFieldStep(sid);
80   
81     for(int eid = 0; eid < step->GetNumberOfFieldOverEntity(); eid++)
82       {
83       vtkMedFieldOverEntity* fieldOverEntity = step->GetFieldOverEntity(eid);
84       med_entity_type type = fieldOverEntity->GetEntity().EntityType;
85
86       if (type == MED_NODE)
87         {
88         this->FieldType |= PointField;
89         }
90       else if(type == MED_NODE_ELEMENT )
91         {
92         this->FieldType |= ElnoField;
93         }
94       else
95         {
96         for(int pid=0; pid<fieldOverEntity->GetNumberOfFieldOnProfile(); pid++)
97           {
98           vtkMedFieldOnProfile* fop = fieldOverEntity->GetFieldOnProfile(pid);
99           const char* locname = fop->GetLocalizationName();
100           if(strcmp(locname, MED_GAUSS_ELNO) == 0 )
101             {
102             this->FieldType = ElnoField;
103             }
104           else if(strcmp(locname, MED_NO_LOCALIZATION) != 0 )
105             {
106             this->FieldType |= QuadratureField;
107             }
108           else
109             {
110             this->FieldType |= CellField;
111             }
112           }
113         }
114       }
115     }
116     
117   if(this->FieldType == UnknownFieldType) 
118     this->FieldType = PointField;
119 }
120
121 int vtkMedField::HasManyFieldTypes()
122 {
123   int numberOfTypes = 0;
124   numberOfTypes += (this->FieldType & vtkMedField::PointField) != 0;
125   numberOfTypes += (this->FieldType & vtkMedField::CellField) != 0;
126   numberOfTypes += (this->FieldType & vtkMedField::QuadratureField) != 0;
127   numberOfTypes += (this->FieldType & vtkMedField::ElnoField) != 0;
128
129   return numberOfTypes > 1;
130 }
131
132 int vtkMedField::GetFirstType()
133 {
134   if((this->FieldType & vtkMedField::PointField) != 0)
135     return vtkMedField::PointField;
136
137   if((this->FieldType & vtkMedField::CellField) != 0)
138     return vtkMedField::CellField;
139
140   if((this->FieldType & vtkMedField::QuadratureField) != 0)
141     return vtkMedField::QuadratureField;
142
143   if((this->FieldType & vtkMedField::ElnoField) != 0)
144     return vtkMedField::ElnoField;
145 }
146
147 void  vtkMedField::ExtractFieldType(vtkMedField* otherfield, int type)
148 {
149   this->SetName(otherfield->GetName());
150   this->SetLocal(otherfield->GetLocal());
151   this->SetMedIterator(otherfield->GetMedIterator());
152   this->SetDataType(otherfield->GetDataType());
153   this->SetMeshName(otherfield->GetMeshName());
154   this->SetTimeUnit(otherfield->GetTimeUnit());
155   this->SetParentFile(otherfield->GetParentFile());
156
157   this->SetNumberOfComponent(otherfield->GetNumberOfComponent());
158   for(int i=0; i< this->GetNumberOfComponent(); i++)
159     {
160     this->GetComponentName()->SetValue(i, otherfield->
161                                        GetComponentName()->GetValue(i));
162     }
163
164   this->AllocateNumberOfInterpolation(otherfield->GetNumberOfInterpolation());
165   for(int i=0; i<this->GetNumberOfInterpolation(); i++)
166     {
167     this->SetInterpolation(i, otherfield->GetInterpolation(i));
168     }
169
170   this->GetUnit()->SetNumberOfValues(
171       otherfield->GetUnit()->GetNumberOfValues());
172   for(int i=0; i<this->GetUnit()->GetNumberOfValues(); i++)
173     {
174     this->GetUnit()->SetValue(i, otherfield->GetUnit()->GetValue(i));
175     }
176
177   int nstep = otherfield->GetNumberOfFieldStep();
178   map<vtkMedFieldStep*, vtkMedFieldStep*> stepmap;
179   for(int stepid=0; stepid<nstep; stepid++)
180     {
181     vtkMedFieldStep* otherstep = otherfield->GetFieldStep(stepid);
182     vtkMedFieldStep* step = vtkMedFieldStep::New();
183     step->SetComputeStep(otherstep->GetComputeStep());
184     step->SetMedIterator(otherstep->GetMedIterator());
185     this->AddFieldStep(step);
186     step->Delete();
187
188     stepmap[otherstep] = step;
189
190     vtkMedFieldStep* previousstep = NULL;
191     if(stepmap.find(otherstep->GetPreviousStep()) != stepmap.end())
192       {
193       previousstep = stepmap[otherstep->GetPreviousStep()];
194       }
195     step->SetPreviousStep(previousstep);
196     step->SetParentField(this);
197     step->SetMeshComputeStep(otherstep->GetMeshComputeStep());
198
199     for(int eid=0; eid<otherstep->GetNumberOfFieldOverEntity(); eid++)
200       {
201       vtkMedFieldOverEntity* fieldOverEntity = otherstep->GetFieldOverEntity(eid);
202
203       if(type == vtkMedField::PointField)
204         {
205         if(fieldOverEntity->GetEntity().EntityType != MED_NODE)
206           {
207           continue;
208           }
209         step->AppendFieldOverEntity(fieldOverEntity);
210         otherstep->RemoveFieldOverEntity(fieldOverEntity);
211         fieldOverEntity->SetParentStep(step);
212         }
213       else if(type == vtkMedField::ElnoField)
214         {
215         if(fieldOverEntity->GetEntity().EntityType != MED_NODE_ELEMENT)
216           {
217           continue;
218           }
219
220         step->AppendFieldOverEntity(fieldOverEntity);
221         otherstep->RemoveFieldOverEntity(fieldOverEntity);
222         eid--;
223         fieldOverEntity->SetParentStep(step);
224         }
225       else
226         {
227         if(fieldOverEntity->GetEntity().EntityType == MED_NODE)
228           {
229           continue;
230           }
231         vtkMedFieldOverEntity* newfoe = vtkMedFieldOverEntity::New();
232         newfoe->SetEntity(fieldOverEntity->GetEntity());
233         newfoe->SetHasProfile(fieldOverEntity->GetHasProfile());
234         newfoe->SetParentStep(step);
235         step->AppendFieldOverEntity(newfoe);
236         newfoe->Delete();
237         for(int pid=0; pid<fieldOverEntity->GetNumberOfFieldOnProfile(); pid++)
238           {
239           vtkMedFieldOnProfile* fop = fieldOverEntity->GetFieldOnProfile(pid);
240           const char* locname = fop->GetLocalizationName();
241           if((type == vtkMedField::QuadratureField
242              && strcmp(locname, MED_NO_LOCALIZATION) != 0) ||
243              (type == vtkMedField::CellField
244              && strcmp(locname, MED_NO_LOCALIZATION) == 0 ))
245             {
246             newfoe->AppendFieldOnProfile(fop);
247             fieldOverEntity->RemoveFieldOnProfile(fop);
248             pid--;
249             fop->SetParentFieldOverEntity(newfoe);
250             }
251           }
252         if(fieldOverEntity->GetNumberOfFieldOnProfile() == 0)
253           {
254           otherstep->RemoveFieldOverEntity(fieldOverEntity);
255           eid--;
256           }
257         }
258       }
259     }
260
261   this->ComputeFieldType();
262   otherfield->ComputeFieldType();
263 }
264
265 void vtkMedField::SetNumberOfComponent(int ncomp)
266 {
267   if (this->NumberOfComponent == ncomp)
268     return;
269
270   this->NumberOfComponent = ncomp;
271   this->GetUnit()->SetNumberOfValues(this->NumberOfComponent);
272   this->GetComponentName()->SetNumberOfValues(this->NumberOfComponent);
273
274   this->Modified();
275 }
276
277 void  vtkMedField::AddFieldStep(vtkMedFieldStep* step)
278 {
279   this->FieldStep->AddObject(step->GetComputeStep(), step);
280 }
281
282 void  vtkMedField::ClearFieldStep()
283 {
284   this->FieldStep->clear();
285 }
286
287 vtkMedFieldStep* vtkMedField::GetFieldStep(const vtkMedComputeStep& cs)
288 {
289   return this->FieldStep->GetObject(cs);
290 }
291
292 vtkMedFieldStep* vtkMedField::FindFieldStep(const vtkMedComputeStep& cs,
293                                             int strategy)
294 {
295   return this->FieldStep->FindObject(cs, strategy);
296 }
297
298 med_int vtkMedField::GetNumberOfFieldStep()
299 {
300   return this->FieldStep->GetNumberOfObject();
301 }
302
303 vtkMedFieldStep* vtkMedField::GetFieldStep(med_int id)
304 {
305   return this->FieldStep->GetObject(id);
306 }
307
308 void  vtkMedField::GatherFieldTimes(std::set<med_float>& times)
309 {
310   this->FieldStep->GatherTimes(times);
311 }
312
313 void  vtkMedField::GatherFieldIterations(med_float time,
314                                          std::set<med_int>& iterations)
315 {
316   this->FieldStep->GatherIterations(time, iterations);
317 }
318
319 void vtkMedField::PrintSelf(ostream& os, vtkIndent indent)
320 {
321   this->Superclass::PrintSelf(os, indent);
322   PRINT_IVAR(os, indent, MedIterator);
323   PRINT_IVAR(os, indent, NumberOfComponent);
324   PRINT_IVAR(os, indent, FieldType);
325   PRINT_IVAR(os, indent, DataType);
326   PRINT_IVAR(os, indent, Local);
327 }