Salome HOME
[MEDCalc] Preparation for presentation edition: connect double click
[modules/med.git] / src / MEDCalc / cmp / MED.cxx
1 // Copyright (C) 2015-2016  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, or (at your option) any later version.
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 "MED.hxx"
21 #include "MEDFactoryClient.hxx"
22 #include <MEDCalcConstants.hxx>
23
24 #include <SALOMEconfig.h>
25 #include CORBA_CLIENT_HEADER(SALOMEDS_Attributes)
26
27 #include <SALOMEDS_SObject.hxx>
28 #include <Utils_ExceptHandlers.hxx>
29
30 #include <string>
31
32 /*!
33   \brief Constructor
34
35   Creates an instance of the MED component engine
36
37   \param orb reference to the ORB
38   \param poa reference to the POA
39   \param contId CORBA object ID, pointing to the owner SALOME container
40   \param instanceName SALOME component instance name
41   \param interfaceName SALOME component interface name
42 */
43 MED::MED(CORBA::ORB_ptr orb,
44          PortableServer::POA_ptr poa,
45          PortableServer::ObjectId* contId,
46          const char* instanceName,
47          const char* interfaceName)
48   : Engines_Component_i(orb, poa, contId, instanceName, interfaceName),
49     _fieldSeriesEntries()
50 {
51   _thisObj = this;
52   _id = _poa->activate_object(_thisObj); // register and activate this servant object
53 }
54
55 MED::~MED()
56 {
57   // nothing to do
58 }
59
60 MED_ORB::status
61 MED::addDatasourceToStudy(SALOMEDS::Study_ptr study,
62                           const MEDCALC::DatasourceHandler& datasourceHandler)
63 {
64   // set exception handler to catch unexpected CORBA exceptions
65   Unexpect aCatch(SALOME_SalomeException);
66
67   // set result status to error initially
68   MED_ORB::status result = MED_ORB::OP_ERROR;
69
70   // check if reference to study is valid
71   if (!CORBA::is_nil(study)) {
72     // get full object path
73     std::string fullName = CORBA::string_dup(datasourceHandler.name);
74     // check if the object with the same name is already registered in the study
75     SALOMEDS::SObject_var sobj = study->FindObjectByPath(fullName.c_str());
76     if (CORBA::is_nil(sobj)) {
77       // object is not registered yet -> register
78       SALOMEDS::GenericAttribute_var anAttr;
79       SALOMEDS::AttributeParameter_var aParam;
80       SALOMEDS::StudyBuilder_var studyBuilder = study->NewBuilder();
81       SALOMEDS::UseCaseBuilder_var useCaseBuilder = study->GetUseCaseBuilder();
82
83       // find MED component; create it if not found
84       SALOMEDS::SComponent_var father = study->FindComponent("MED");
85       if (CORBA::is_nil(father)) {
86         // create component
87         father = studyBuilder->NewComponent("MED");
88         // set name attribute
89         father->SetAttrString("AttributeName", "MEDCalc");
90         // set icon attribute
91         father->SetAttrString("AttributePixMap", "ICO_MED");
92         // register component in the study
93         studyBuilder->DefineComponentInstance(father, MED_Gen::_this());
94         // add component to the use case tree
95         // (to support tree representation customization and drag-n-drop)
96         useCaseBuilder->SetRootCurrent();
97         useCaseBuilder->Append(father); // component object is added as the top level item
98       }
99
100       // create new sub-object, as a child of the component object
101       SALOMEDS::SObject_var soDatasource = studyBuilder->NewObject(father);
102       soDatasource->SetAttrString("AttributeName", fullName.c_str());
103       soDatasource->SetAttrString("AttributePixMap", "ICO_DATASOURCE");
104       anAttr = studyBuilder->FindOrCreateAttribute(soDatasource, "AttributeParameter");
105       aParam = SALOMEDS::AttributeParameter::_narrow(anAttr);
106       aParam->SetInt(OBJECT_ID, datasourceHandler.id);
107       useCaseBuilder->AppendTo(soDatasource->GetFather(), soDatasource);
108
109       // We can add the meshes as children of the datasource
110       MEDCALC::MeshHandlerList* meshHandlerList =
111         MEDFactoryClient::getDataManager()->getMeshList(datasourceHandler.id);
112
113       for(CORBA::ULong iMesh=0; iMesh<meshHandlerList->length(); iMesh++) {
114         MEDCALC::MeshHandler meshHandler = (*meshHandlerList)[iMesh];
115         SALOMEDS::SObject_var soMesh = studyBuilder->NewObject(soDatasource);
116         soMesh->SetAttrString("AttributeName", meshHandler.name);
117         soMesh->SetAttrString("AttributePixMap", "ICO_DATASOURCE_MESH");
118         anAttr = studyBuilder->FindOrCreateAttribute(soMesh, "AttributeParameter");
119         aParam = SALOMEDS::AttributeParameter::_narrow(anAttr);
120         aParam->SetInt(OBJECT_ID, meshHandler.id);
121         anAttr = studyBuilder->FindOrCreateAttribute(soMesh, "AttributeParameter");
122         aParam = SALOMEDS::AttributeParameter::_narrow(anAttr);
123         aParam->SetBool(OBJECT_IS_IN_WORKSPACE, false);
124         useCaseBuilder->AppendTo(soMesh->GetFather(), soMesh);
125
126         // We add the field timeseries defined on this mesh, as children of the mesh SObject
127         MEDCALC::FieldseriesHandlerList * fieldseriesHandlerList =
128           MEDFactoryClient::getDataManager()->getFieldseriesListOnMesh(meshHandler.id);
129
130         for(CORBA::ULong iFieldseries=0; iFieldseries<fieldseriesHandlerList->length(); iFieldseries++) {
131           MEDCALC::FieldseriesHandler fieldseriesHandler = (*fieldseriesHandlerList)[iFieldseries];
132           SALOMEDS::SObject_var soFieldseries = studyBuilder->NewObject(soMesh);
133           _fieldSeriesEntries[fieldseriesHandler.id] = soFieldseries->GetID();
134
135           std::string label(fieldseriesHandler.name);
136           label +=" ("+std::string(mapTypeOfFieldLabel[fieldseriesHandler.type])+")";
137           soFieldseries->SetAttrString("AttributeName", label.c_str());
138           soFieldseries->SetAttrString("AttributePixMap", "ICO_DATASOURCE_FIELD");
139           anAttr = studyBuilder->FindOrCreateAttribute(soFieldseries, "AttributeParameter");
140           aParam = SALOMEDS::AttributeParameter::_narrow(anAttr);
141           aParam->SetInt(OBJECT_ID, fieldseriesHandler.id);
142           anAttr = studyBuilder->FindOrCreateAttribute(soFieldseries, "AttributeParameter");
143           aParam = SALOMEDS::AttributeParameter::_narrow(anAttr);
144           aParam->SetBool(OBJECT_IS_IN_WORKSPACE, false);
145
146           useCaseBuilder->AppendTo(soFieldseries->GetFather(), soFieldseries);
147           soFieldseries->UnRegister();
148         }
149         soMesh->UnRegister();
150       }
151
152       // cleanup
153       father->UnRegister();
154       soDatasource->UnRegister();
155     }
156   }
157
158   result = MED_ORB::OP_OK;
159   return result;
160 }
161
162 MED_ORB::status
163 MED::registerPresentation(SALOMEDS::Study_ptr study,
164                           CORBA::Long fieldId,
165                           const char* name,
166                           const char* label)
167 {
168   // set exception handler to catch unexpected CORBA exceptions
169   Unexpect aCatch(SALOME_SalomeException);
170
171   // set result status to error initially
172   MED_ORB::status result = MED_ORB::OP_ERROR;
173
174   if (_fieldSeriesEntries.find(fieldId) == _fieldSeriesEntries.end()) {
175     std::cerr << "Field not found\n";
176     return MED_ORB::OP_ERROR ;
177   }
178   std::string entry = _fieldSeriesEntries[fieldId];
179   SALOMEDS::SObject_var sobject = study->FindObjectID(entry.c_str());
180   SALOMEDS::SObject_ptr soFieldseries = sobject._retn();
181
182   if (soFieldseries->IsNull()) {
183     std::cerr << "Entry not found\n";
184     return  MED_ORB::OP_ERROR;
185   }
186
187   SALOMEDS::StudyBuilder_var studyBuilder = study->NewBuilder();
188   SALOMEDS::UseCaseBuilder_var useCaseBuilder = study->GetUseCaseBuilder();
189   SALOMEDS::SObject_var soPresentation = studyBuilder->NewObject(soFieldseries);
190   useCaseBuilder->AppendTo(soPresentation->GetFather(), soPresentation);
191
192   soPresentation->SetAttrString("AttributeName", name);
193   soPresentation->SetAttrString("AttributePixMap", label);
194
195   SALOMEDS::GenericAttribute_var anAttr;
196   SALOMEDS::AttributeParameter_var aParam;
197   anAttr = studyBuilder->FindOrCreateAttribute(soPresentation, "AttributeParameter");
198   aParam = SALOMEDS::AttributeParameter::_narrow(anAttr);
199   aParam->SetInt(FIELD_ID, fieldId);
200   aParam->SetBool(IS_PRESENTATION, true);
201
202   result = MED_ORB::OP_OK;
203   return result;
204 }
205
206 Engines::TMPFile*
207 MED::DumpPython(CORBA::Object_ptr theStudy,
208                 CORBA::Boolean isPublished,
209                 CORBA::Boolean isMultiFile,
210                 CORBA::Boolean& isValidScript)
211 {
212   std::cout << "In MED::DumpPython\n";
213
214   SALOMEDS::Study_var aStudy = SALOMEDS::Study::_narrow(theStudy);
215   if(CORBA::is_nil(aStudy)) {
216     std::cerr << "Error: Cannot find the study\n";
217     return new Engines::TMPFile(0);
218   }
219
220   SALOMEDS::SObject_var aSO = aStudy->FindComponent("MED");
221   if(CORBA::is_nil(aSO)) {
222     std::cerr << "Error: Cannot find component MED\n";
223     return new Engines::TMPFile(0);
224   }
225
226   std::string aScript;
227
228   MEDCALC::CommandsList* history = MEDFactoryClient::getCommandsHistoryManager()->getCommandsHistory();
229   for (CORBA::ULong i = 0; i < history->length(); ++i) {
230     aScript += (*history)[i];
231     aScript += "\n";
232   }
233
234   int aLen = aScript.size();
235   unsigned char* aBuffer = new unsigned char[aLen+1];
236   strcpy((char*)aBuffer, aScript.c_str());
237
238   CORBA::Octet* anOctetBuf =  (CORBA::Octet*)aBuffer;
239   Engines::TMPFile_var aStreamFile = new Engines::TMPFile(aLen+1, aLen+1, anOctetBuf, 1);
240
241   isValidScript = true;
242   return aStreamFile._retn();
243 }
244
245 extern "C"
246 {
247   /*!
248     \brief Exportable factory function: create an instance of the MED component engine
249     \param orb reference to the ORB
250     \param poa reference to the POA
251     \param contId CORBA object ID, pointing to the owner SALOME container
252     \param instanceName SALOME component instance name
253     \param interfaceName SALOME component interface name
254     \return CORBA object identifier of the registered servant
255   */
256   PortableServer::ObjectId* MEDEngine_factory(CORBA::ORB_ptr orb,
257                                               PortableServer::POA_ptr poa,
258                                               PortableServer::ObjectId* contId,
259                                               const char* instanceName,
260                                               const char* interfaceName)
261   {
262     MED* component = new MED(orb, poa, contId, instanceName, interfaceName);
263     return component->getId();
264   }
265 }