Salome HOME
merge from branch DEV tag mergeto_trunk_04apr08
[modules/yacs.git] / src / prs / YACSPrs_toString.cxx
1 // Copyright (C) 2005  OPEN CASCADE, CEA/DEN, EDF R&D, PRINCIPIA 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 <YACSPrs_toString.h>
21 #include <libxml/parser.h>
22 #include <libxml/tree.h>
23 #include <sstream>
24 #include <TypeConversions.hxx>
25 #include <Any.hxx>
26 #include <TypeCode.hxx>
27
28 using namespace YACS::ENGINE;
29
30 char * toString(CORBA::Any* theAny, QString& theRetStr)
31 {
32   if ( !theAny ) theRetStr += QString("< ? >");
33   else
34   {
35     CORBA::Any anAny = *theAny;
36     if ( !anAny.value() ) theRetStr += QString("< ? >");
37     else
38     {
39       std::ostringstream astr;
40       const char * retstr;
41       int startstr = 0;
42       switch ( anAny.type()->kind() )
43       {
44         case CORBA::tk_string: {
45           anAny >>= retstr;
46           theRetStr += QString(retstr);
47           break;
48         }
49         case CORBA::tk_long: {
50           CORBA::Long l;
51           anAny >>= l;
52           astr << l << std::ends;
53           theRetStr += QString(astr.str());
54           break;
55         }
56         case CORBA::tk_double: {
57           double d;
58           anAny >>= d;
59           astr << d << std::ends;
60           //astr << setw(25) << setprecision(18) << d << std::ends;
61           QString aRetStr = QString(astr.str());
62           int i = 0;
63           while ( i < (int ) theRetStr.length() && theRetStr.at(i++) == ' ' ) {
64             startstr = i;
65           }
66           theRetStr += aRetStr.mid(startstr,aRetStr.length());
67           break;
68         }
69         case CORBA::tk_sequence: {
70           theRetStr += QString("[");
71
72           CORBA::Long aSeqLength = 0;
73           *(anAny.type()->parameter(1)) >>= aSeqLength;
74
75           if ( aSeqLength == 0 )
76           {
77             theRetStr += QString("   ]");
78             break;
79           }
80           
81           // TO DO : implement recursion for the sequence type
82           /*CORBA::TypeCode* aType;
83           *(anAny.type()->parameter(0)) >>= aType;
84           switch ( aType->kind() )
85           {
86             case CORBA::tk_string: {
87               printf("StringElem\n");
88               CORBA::StringSeq* aStringSeq;
89               anAny >>= aStringSeq;
90               for (int i=0; i < aSeqLength; i++)
91               {
92                 CORBA::Any anArg;
93                 anArg <<= aStringSeq[i];
94                 toString( &anArg, theRetStr );
95                 if ( i < aSeqLength-1 ) theRetStr += QString(",");
96               }
97               break;
98             }
99             case CORBA::tk_double: {
100               printf("DoubleElem\n");
101               CORBA::DoubleSeq* aDoubleSeq;
102               anAny >>= aDoubleSeq;
103               for (int i=0; i < aSeqLength; i++)
104               {
105                 CORBA::Any anArg;
106                 anArg <<= aDoubleSeq[i];
107                 toString( &anArg, theRetStr );
108                 if ( i < aSeqLength-1 ) theRetStr += QString(",");
109               }
110               break;
111             }
112             case CORBA::tk_sequence: {
113               printf("SequenceElem\n");
114               CORBA::Any* aSequenceSeq;
115               anAny >>= aSequenceSeq;
116               for (int i=0; i < aSeqLength; i++)
117               {
118                 CORBA::Any anArg;
119                 anArg <<= aSequenceSeq[i];
120                 toString( &anArg, theRetStr );
121                 if ( i < aSeqLength-1 ) theRetStr += QString(",");
122               }
123               break;
124             }
125             default: {
126               printf("DefaultElem\n");
127               theRetStr += QString("< ? >");
128               break;
129             }
130           }*/
131           theRetStr += QString("]");
132           break;
133         }
134         case CORBA::tk_objref: {
135           /*CORBA::Object_ptr obj;
136           try {
137             anAny >>= (CORBA::Any::to_object ) obj;
138             theRetStr += QString( _Orb->object_to_string( obj ) );
139           }
140           catch ( ... ) {
141             theRetStr += QString("object_to_string catched ");
142           }*/
143           theRetStr += QString("Objref");
144           break;
145         }
146         default: {
147           theRetStr += QString("< ? >");
148           break;
149         }
150       }
151     }
152   }
153 }
154
155 void toString(PyObject* theObject, QString& theRetStr)
156 {
157   if ( !theObject ) theRetStr += QString("< ? >");
158
159   std::ostringstream aStr;
160   if ( PyString_CheckExact(theObject) )
161     theRetStr += QString( PyString_AsString(theObject) );
162   else if ( PyLong_CheckExact(theObject) )
163   {
164     long aVal = PyLong_AsLong(theObject);
165     aStr << aVal << std::ends;
166     theRetStr += QString( aStr.str() );
167   }
168   else if ( PyInt_CheckExact(theObject) )
169   {
170     long aVal = PyInt_AsLong(theObject);
171     aStr << aVal << std::ends;
172     theRetStr += QString( aStr.str() );
173   }
174   else if ( PyBool_Check(theObject) )
175     theRetStr += QString( (theObject == Py_True) ? "true" : "false" );
176   else if ( PyFloat_CheckExact(theObject) )
177   {
178     double aVal = PyFloat_AsDouble(theObject);
179     aStr << aVal << std::ends;
180     theRetStr += QString( aStr.str() );
181   }
182   else if ( PyList_CheckExact(theObject) )
183   {
184     theRetStr += QString("[");
185     for (int i=0; i < PyList_Size(theObject); i++)
186     {
187       toString( PyList_GetItem(theObject, i), theRetStr );
188       if ( i < PyList_Size(theObject)-1 ) theRetStr += QString(",");
189     }
190     theRetStr += QString("]");
191   }
192   //else if ( ... ) // objref case
193   else
194     theRetStr += QString("< ? >");
195 }
196
197 void toString(YACS::ENGINE::Any* theAny, QString& theValue)
198 {
199   if ( !theAny ) theValue += QString("< ? >");
200   else if ( theAny->getType() )
201   {
202     DynType aKind = theAny->getType()->kind();
203     switch (aKind)
204       {
205       case Double:
206         theValue += QString::number(theAny->getDoubleValue());
207         break;
208       case Int:
209         theValue += QString::number(theAny->getIntValue());
210         break;
211       case String:
212         theValue += QString(theAny->getStringValue());
213         break;
214       case Bool:
215         theValue += QString(theAny->getBoolValue()?"true":"false");
216         break;
217       case Objref:
218         theValue += QString("Objref"); /// ?
219         break;
220       case Sequence: {
221         SequenceAny* aSeqAny = dynamic_cast<SequenceAny*>( theAny );
222         if ( aSeqAny )
223         {
224           theValue += QString("[");
225           for (int i=0; i < aSeqAny->size(); i++)
226           {
227             toString( (*aSeqAny)[i], theValue );
228             if ( i < aSeqAny->size()-1 ) theValue += QString(",");
229           }
230           theValue += QString("]");
231         }
232         break;
233       }
234       case NONE:
235       default:
236         theValue += QString("");
237         break;
238       }
239   }
240 }
241
242 void toString(const std::string& value, const TypeCode * t,QString& theRetStr)
243 {
244   if(value == "")
245     {
246       theRetStr="";
247       return;
248     }
249   xmlDocPtr doc;
250   xmlNodePtr cur;
251   YACS::ENGINE::Any *ob=NULL;
252   doc = xmlParseMemory(value.c_str(), value.size());
253   if (doc == NULL )
254     {
255       theRetStr="< ? >";
256       return;
257     }
258   cur = xmlDocGetRootElement(doc);
259   if (cur == NULL)
260     {
261       xmlFreeDoc(doc);
262       theRetStr="< ? >";
263       return;
264     }
265   while (cur != NULL)
266     {
267       if ((!xmlStrcmp(cur->name, (const xmlChar *)"value")))
268         {
269           try
270             {
271               ob=convertXmlNeutral(t,doc,cur);
272             }
273           catch(...)
274             {
275             }
276           break;
277         }
278       cur = cur->next;
279     }
280   xmlFreeDoc(doc);
281   if(ob==NULL)
282     {
283       theRetStr="< ? >";
284     }
285   else
286     {
287       toString(ob,theRetStr);
288       ob->decrRef();
289     }
290 }
291