]> SALOME platform Git repositories - modules/gui.git/blob - src/Qtx/QtxStdOperations.cxx
Salome HOME
References in object browser
[modules/gui.git] / src / Qtx / QtxStdOperations.cxx
1 #include "QtxStdOperations.h"
2
3 #include <math.h>
4 #include <stdlib.h>
5
6 //================================================================
7 // Function : 
8 // Purpose  : 
9 //================================================================
10 QtxStdOperations::QtxStdOperations()
11 {
12 }
13
14 //================================================================
15 // Function : 
16 // Purpose  : 
17 //================================================================
18 QtxStdOperations::~QtxStdOperations()
19 {
20 }
21
22 //================================================================
23 // Function : 
24 // Purpose  : 
25 //================================================================
26 void QtxStdOperations::bracketsList( QStringList& list, bool open ) const
27 {
28     if( open )
29         list.append( "(" );
30     else
31         list.append( ")" );
32 }
33
34 //================================================================
35 // Function : 
36 // Purpose  : 
37 //================================================================
38 void QtxStdOperations::opersList( QStringList& list ) const
39 {
40     list += myOpers;
41 }
42
43 //================================================================
44 // Function : 
45 // Purpose  : 
46 //================================================================
47 void QtxStdOperations::addOperations( const QStringList& list )
48 {
49     QStringList::const_iterator anIt = list.begin(),
50                                 aLast = list.end();
51     for( ; anIt!=aLast; anIt++ )
52         if( myOpers.contains( *anIt )==0 )
53             myOpers.append( *anIt );
54 }
55
56 //================================================================
57 // Function : 
58 // Purpose  : 
59 //================================================================
60 void QtxStdOperations::addTypes( const ListOfTypes& list )
61 {
62     ListOfTypes::const_iterator anIt = list.begin(),
63                                 aLast = list.end();
64     for( ; anIt!=aLast; anIt++ )
65         if( myTypes.contains( *anIt )==0 )
66             myTypes.append( *anIt );
67 }
68
69 //================================================================
70 // Function : 
71 // Purpose  : 
72 //================================================================
73 QtxParser::Error QtxStdOperations::isValid( const QString& op,
74                                             const QVariant::Type t1,
75                                             const QVariant::Type t2 ) const
76 {
77     if( ( t1==QVariant::Invalid || myTypes.contains( t1 ) ) &&
78         ( t2==QVariant::Invalid || myTypes.contains( t2 ) ) &&
79         ( t1!=QVariant::Invalid || t2!=QVariant::Invalid ) )
80         if( prior( op, t1!=QVariant::Invalid && t2!=QVariant::Invalid ) > 0 )
81             return QtxParser::OK;
82         else
83             return QtxParser::InvalidOperation;
84     else
85         return QtxParser::OperandsNotMatch;
86 }
87
88
89
90
91
92
93
94
95 //================================================================
96 // Function : 
97 // Purpose  : 
98 //================================================================
99 QtxArithmetics::QtxArithmetics()
100 : QtxStdOperations()
101 {
102     QStringList aList;
103     aList.append( "+" );
104     aList.append( "-" );
105     aList.append( "*" );
106     aList.append( "/" );
107     aList.append( "=" );
108     aList.append( "<" );
109     aList.append( ">" );
110     aList.append( "<=" );
111     aList.append( ">=" );
112     aList.append( "<>" );
113     addOperations( aList );
114
115     ListOfTypes aTypes;
116     aTypes.append( QVariant::Int );
117     aTypes.append( QVariant::UInt );
118     aTypes.append( QVariant::Double );
119     addTypes( aTypes );
120 }
121
122 //================================================================
123 // Function : 
124 // Purpose  : 
125 //================================================================
126 QtxArithmetics::~QtxArithmetics()
127 {
128 }
129
130 //================================================================
131 // Function : 
132 // Purpose  : 
133 //================================================================
134 bool QtxArithmetics::createValue( const QString& str, QtxValue& v ) const
135 {
136     bool ok = false;
137     v = str.toInt( &ok );
138
139     if( !ok )
140     {
141         v = str.toDouble( &ok );
142         if( !ok )
143             ok = QtxStdOperations::createValue( str, v );
144     }
145     return ok;
146 }
147
148 //================================================================
149 // Function : 
150 // Purpose  : 
151 //================================================================
152 int QtxArithmetics::prior( const QString& op, bool isBin ) const
153 {
154     if( isBin )
155         if( op=="<" || op==">" || op=="=" || 
156             op=="<=" || op==">=" || op=="<>" )
157             return 1;
158         else if( op=="+" || op=="-" )
159             return 2;
160         else if( op=="*" || op=="/" )
161             return 3;
162         else
163             return 0;
164     else if( op=="+" || op=="-" )
165         return 5;
166     else
167         return 0;
168 }
169
170 void set( QVariant& v1, bool v2 )
171 {
172     v1 = QVariant( v2, 0 );
173 }
174
175 //================================================================
176 // Function : 
177 // Purpose  : 
178 //================================================================
179 QtxParser::Error QtxArithmetics::calculate( const QString& op, 
180                                                 QtxValue& v1, QtxValue& v2 ) const
181 {
182     QtxParser::Error err = QtxParser::OK;
183
184     if( v1.isValid() && v2.isValid() )
185         // binary operations
186         if( ( v1.type()==QVariant::Int || v1.type()==QVariant::UInt ) &&
187             ( v2.type()==QVariant::Int || v2.type()==QVariant::UInt ) )
188         {
189             int _v1 = v1.toInt(),
190                 _v2 = v2.toInt();
191
192             if( op=="+" )
193                 v1 = _v1 + _v2;
194             else if( op=="-" )
195                 v1 = _v1 - _v2;
196             else if( op=="*" )
197                 v1 = _v1 * _v2;
198             else if( op=="/" )
199                 if( _v2!=0 )
200                     if( _v1%_v2==0 )
201                         v1 = _v1 / _v2;
202                     else
203                         v1 = double( _v1 ) / double( _v2 );
204                 else
205                     err = QtxParser::InvalidResult;
206             else if( op=="<" )
207                 set( v1, _v1<_v2 );
208             else if( op==">" )
209                 set( v1, _v1>_v2 );
210             else if( op=="=" )
211                 set( v1, _v1==_v2 );
212             else if( op=="<=" )
213                 set( v1, _v1<=_v2 );
214             else if( op==">=" )
215                 set( v1, _v1>=_v2 );
216             else if( op=="<>" )
217                 set( v1, _v1!=_v2 );
218         }
219         else if( ( v1.type()==QVariant::Int || v1.type()==QVariant::Double ) &&
220                  ( v2.type()==QVariant::Int || v2.type()==QVariant::Double ) )
221         {
222             double _v1 = v1.toDouble(),
223                    _v2 = v2.toDouble();
224
225             if( op=="+" )
226                 v1 = _v1 + _v2;
227             else if( op=="-" )
228                 v1 = _v1 - _v2;
229             else if( op=="*" )
230                 v1 = _v1 * _v2;
231             else if( op=="/" )
232                 if( _v2!=0 )
233                     v1 = _v1 / _v2;
234                 else
235                     err = QtxParser::InvalidResult;
236             else if( op=="<" )
237                 set( v1, _v1<_v2 );
238             else if( op==">" )
239                 set( v1, _v1>_v2 );
240             else if( op=="=" )
241                 set( v1, _v1==_v2 );
242             else if( op=="<=" )
243                 set( v1, _v1<=_v2 );
244             else if( op==">=" )
245                 set( v1, _v1>=_v2 );
246             else if( op=="<>" )
247                 set( v1, _v1!=_v2 );
248         }
249     else
250         // prefix operations
251         if( op=="-" )
252             if( v2.type()==QVariant::Int )
253                 v2 = -v2.toInt();
254             else if( v2.type()==QVariant::Double )
255                 v2 = -v2.toDouble();
256
257     return err;
258 }
259
260
261
262
263
264
265
266
267
268
269
270 //================================================================
271 // Function : 
272 // Purpose  : 
273 //================================================================
274 QtxLogic::QtxLogic()
275 : QtxStdOperations()
276 {
277     QStringList aList;
278     aList.append( "and" );
279     aList.append( "&&" );
280     aList.append( "or" );
281     aList.append( "||" );
282     aList.append( "xor" );
283     aList.append( "not" );
284     aList.append( "!" );
285     aList.append( "imp" );
286     aList.append( "=" );
287     addOperations( aList );
288
289     ListOfTypes aTypes;
290     aTypes.append( QVariant::Bool );
291     addTypes( aTypes );
292 }
293
294 //================================================================
295 // Function : 
296 // Purpose  : 
297 //================================================================
298 QtxLogic::~QtxLogic()
299 {
300 }
301
302 //================================================================
303 // Function : 
304 // Purpose  : 
305 //================================================================
306 bool QtxLogic::createValue( const QString& str, QtxValue& v ) const
307 {
308     bool ok = true;
309     if( str.lower()=="true" )
310         v = true;
311     else if( str.lower()=="false" )
312         v = false;
313     else
314         ok = QtxStdOperations::createValue( str, v );
315
316     return ok;
317 }
318
319 //================================================================
320 // Function : 
321 // Purpose  : 
322 //================================================================
323 int QtxLogic::prior( const QString& op, bool isBin ) const
324 {
325     if( isBin )
326         if( op=="and" || op=="or" || op=="xor" ||
327             op=="&&"  || op=="||" ||
328             op=="imp" )
329             return 1;
330         else if( op=="=" )
331             return 2;
332         else 
333             return 0;
334     else if( op=="not" || op=="!" )
335             return 5;
336          else
337             return 0;
338 }
339
340 //================================================================
341 // Function : 
342 // Purpose  : 
343 //================================================================
344 QtxParser::Error QtxLogic::calculate( const QString& op,
345                                           QtxValue& v1, QtxValue& v2 ) const
346 {
347     QtxParser::Error err = QtxParser::OK;
348     if( v1.isValid() && v2.isValid() )
349     {
350         if( op=="and" || op=="&&" )
351             set( v1, v1.toBool() && v2.toBool() );
352         else if( op=="or" || op=="||" )
353             set( v1, v1.toBool() || v2.toBool() );
354         else if( op=="xor" )
355             set( v1, ( !v1.toBool() && v2.toBool() ) || ( v1.toBool() && !v2.toBool() ) );
356         else if( op=="imp" )
357             set( v1, !v1.toBool() || v2.toBool() );
358         else if( op=="=" )
359             set( v1, v1.toBool()==v2.toBool() );
360     }
361     else
362         if( op=="not" || op=="!" )
363             set( v2, !v2.toBool() );
364
365     return err;
366 }
367
368
369
370
371
372
373 //================================================================
374 // Function : 
375 // Purpose  : 
376 //================================================================
377 QtxFunctions::QtxFunctions()
378 : QtxStdOperations()
379 {
380     QStringList aList;
381     aList.append( "sqrt" );
382     aList.append( "abs" );
383     aList.append( "sin" );
384     aList.append( "cos" );
385     aList.append( "rad2grad" );
386     aList.append( "grad2rad" );
387     addOperations( aList );
388
389     ListOfTypes aTypes;
390     aTypes.append( QVariant::Int );
391     aTypes.append( QVariant::Double );
392     addTypes( aTypes );
393 }
394
395 //================================================================
396 // Function : 
397 // Purpose  : 
398 //================================================================
399 QtxFunctions::~QtxFunctions()
400 {
401 }
402
403 //================================================================
404 // Function : 
405 // Purpose  : 
406 //================================================================
407 bool QtxFunctions::createValue( const QString& str, QtxValue& v ) const
408 {
409     bool ok = false;
410     v = str.toInt( &ok );
411
412     if( !ok )
413     {
414         v = str.toDouble( &ok );
415         if( !ok )
416             ok = QtxStdOperations::createValue( str, v );
417     }
418     return ok;
419 }
420
421 //================================================================
422 // Function : 
423 // Purpose  : 
424 //================================================================
425 int QtxFunctions::prior( const QString& op, bool isBin ) const
426 {
427     if( isBin )
428         return 0;
429     else if( op=="sqrt" || op=="abs" || op=="sin" || op=="cos" ||
430              op=="rad2grad" || op=="grad2rad" )
431         return 1;
432     else
433         return 0;
434 }
435
436 //================================================================
437 // Function : 
438 // Purpose  : 
439 //================================================================
440 QtxParser::Error QtxFunctions::calculate( const QString& op,
441                                           QtxValue& v1, QtxValue& v2 ) const
442 {
443     QtxParser::Error err = QtxParser::OK;
444     double val = v2.toDouble();
445     if( op=="sqrt" )
446         if( val>=0 )
447             v2 = sqrt( val );
448         else
449             err = QtxParser::InvalidResult;
450     else if( op=="abs" )
451         if( v2.type()==QVariant::Int )
452             v2 = abs( v2.toInt() );
453         else 
454             v2 = fabs( v2.toDouble() );
455     else if( op=="sin" )
456         v2 = sin( val );
457     else if( op=="cos" )
458         v2 = cos( val );
459     else if( op=="grad2rad" )
460         v2 = val * 3.14159256 / 180.0;
461     else if( op=="rad2grad" )
462         v2 = val * 180.0 / 3.14159256;
463
464     return err;
465 }
466
467
468
469
470
471
472
473
474 //================================================================
475 // Function : 
476 // Purpose  : 
477 //================================================================
478 QtxStrings::QtxStrings()
479 : QtxStdOperations()
480 {
481     QStringList aList;
482     aList.append( "+" );
483     aList.append( "=" );
484     aList.append( "<" );
485     aList.append( ">" );
486     aList.append( "<=" );
487     aList.append( ">=" );
488     aList.append( "<>" );
489     aList.append( "length" );
490     aList.append( "lower" );
491     aList.append( "upper" );
492     addOperations( aList );
493
494     ListOfTypes aTypes;
495     aTypes.append( QVariant::Int );
496     aTypes.append( QVariant::Double );
497     aTypes.append( QVariant::String );
498     aTypes.append( QVariant::CString );
499     addTypes( aTypes );
500 }
501
502
503 //================================================================
504 // Function : 
505 // Purpose  : 
506 //================================================================
507 QtxStrings::~QtxStrings()
508 {
509 }
510
511 //================================================================
512 // Function : 
513 // Purpose  : 
514 //================================================================
515 bool QtxStrings::createValue( const QString& str, QtxValue& v ) const
516 {
517     QChar st = str[0],
518           fin = str[ ( int )( str.length()-1 ) ];
519     if( st=="'" && fin=="'" )
520     {
521         v = str.mid( 1, str.length()-2 );
522         return true;
523     }
524     else
525         return QtxStdOperations::createValue( str, v );
526 }
527
528 //================================================================
529 // Function : 
530 // Purpose  : 
531 //================================================================
532 int QtxStrings::prior( const QString& op, bool isBin ) const
533 {
534     if( isBin )
535         if( op=="+" ) 
536             return 2;
537         else if( op=="="  || op=="<"  || op==">"  ||
538                  op=="<=" || op==">=" || op=="<>" )
539             return 1;
540         else
541             return 0;
542     else
543         if( op=="length" || op=="lower" || op=="upper" )
544             return 5;
545         else
546             return 0;
547 }
548
549 //================================================================
550 // Function : 
551 // Purpose  : 
552 //================================================================
553 QtxParser::Error QtxStrings::calculate( const QString& op,
554                                             QtxValue& v1, QtxValue& v2 ) const
555 {
556     QtxParser::Error err = QtxParser::OK;
557     if( v1.isValid() && v2.isValid() )
558     {
559         QString _v1 = v1.toString(),
560                 _v2 = v2.toString();
561         if( op=="+" )
562             v1 = _v1 + _v2;
563         else if( op=="=" )
564             set( v1, _v1==_v2 );
565         else if( op=="<" )
566             set( v1, _v1<_v2 );
567         else if( op==">" )
568             set( v1, _v1>_v2 );
569         else if( op=="<>" )
570             set( v1, _v1!=_v2 );
571         else if( op=="<=" )
572             set( v1, _v1<_v2 || _v1==_v2 );
573         else if( op==">=" )
574             set( v1, _v1>_v2 || _v1==_v2 );
575     }
576     else if( !v1.isValid() && v2.isValid() )
577     {
578         QString val = v2.toString();
579         if( op=="length" )
580             v2 = ( int )val.length();
581         else if( op=="lower" )
582             v2 = val.lower();
583         else if( op=="upper" )
584             v2 = val.upper();
585     }
586
587     return err;
588 }
589
590
591
592
593
594
595 //================================================================
596 // Function : 
597 // Purpose  : 
598 //================================================================
599 QtxSets::QtxSets()
600 {
601     QStringList aList;
602     aList.append( "{" );
603     aList.append( "}" );
604     aList.append( "=" );
605     aList.append( "<>" );
606     aList.append( "+" );
607     aList.append( "-" );
608     aList.append( "*" );
609     aList.append( "in" );
610     aList.append( "count" );
611     addOperations( aList );
612
613     ListOfTypes aTypes;
614     aTypes.append( QVariant::List );
615     addTypes( aTypes );
616 }
617
618 //================================================================
619 // Function : 
620 // Purpose  : 
621 //================================================================
622 QtxSets::~QtxSets()
623 {
624 }
625
626 //================================================================
627 // Function : 
628 // Purpose  : 
629 //================================================================
630 void QtxSets::bracketsList( QStringList& list, bool open ) const
631 {
632     if( open )
633         list.append( "{" );
634     else 
635         list.append( "}" );
636     QtxStdOperations::bracketsList( list, open );
637 }
638
639 //================================================================
640 // Function : 
641 // Purpose  : 
642 //================================================================
643 bool QtxSets::createValue( const QString& str, QtxValue& val ) const
644 {
645     return QtxStdOperations::createValue( str, val );
646 }
647
648 //================================================================
649 // Function : 
650 // Purpose  : 
651 //================================================================
652 int QtxSets::prior( const QString& op, bool isBin ) const
653 {
654     if( isBin )
655         if( op=="=" || op=="<>" )
656             return 1;
657         else if( op=="+" || op=="-" || op=="*" )
658             return 2;
659         else if( op=="in" )
660             return 3;
661         else
662             return 0;
663
664     else 
665         if( op=="{" || op=="}" )
666             return 5;
667         else if( op=="count" )
668             return 4;
669         else
670             return 0;
671 }
672
673 //================================================================
674 // Function : 
675 // Purpose  : 
676 //================================================================
677 QtxParser::Error QtxSets::isValid( const QString& op,
678                                    const QVariant::Type t1,
679                                    const QVariant::Type t2 ) const
680 {
681     if( op=="{" )
682         return QtxParser::OK;
683     else if( op=="in" )
684         if( t1!=QVariant::Invalid && t2==QVariant::List )
685             return QtxParser::OK;
686         else
687             return QtxParser::OperandsNotMatch;
688     else
689         return QtxStdOperations::isValid( op, t1, t2 );
690 }
691
692 //================================================================
693 // Function : 
694 // Purpose  : 
695 //================================================================
696 void QtxSets::add( ValueSet& set, const QtxValue& v )
697 {
698     if( v.isValid() && set.contains( v )==0 )
699         set.append( v );
700 }
701
702 //================================================================
703 // Function : 
704 // Purpose  : 
705 //================================================================
706 void QtxSets::add( ValueSet& s1, const ValueSet& s2 )
707 {
708     ValueSet::const_iterator anIt = s2.begin(),
709                              aLast = s2.end();
710     for( ; anIt!=aLast; anIt++ )
711         add( s1, *anIt );
712 }
713
714 //================================================================
715 // Function : 
716 // Purpose  : 
717 //================================================================
718 void QtxSets::remove( ValueSet& set, const QtxValue& v )
719 {
720     set.remove( v );
721 }
722
723 //================================================================
724 // Function : 
725 // Purpose  : 
726 //================================================================
727 void QtxSets::remove( ValueSet& s1, const ValueSet& s2 )
728 {
729     ValueSet::const_iterator anIt = s2.begin(),
730                              aLast = s2.end();
731     for( ; anIt!=aLast; anIt++ )
732         s1.remove( *anIt );
733 }
734
735 //================================================================
736 // Function : 
737 // Purpose  : 
738 //================================================================
739 QtxParser::Error QtxSets::calculate( const QString& op, QtxValue& v1, QtxValue& v2 ) const
740 {
741     QtxParser::Error err = QtxParser::OK;
742
743     if( op!="{" )
744         if( op=="}" )
745         {
746             ValueSet aNewList;
747             add( aNewList, v1.toList() );
748             v1 = aNewList;
749         }
750
751         else if( op=="=" || op=="<>" || op=="+" || op=="-" || op=="*" )
752         {
753             ValueSet aNewList;
754             add( aNewList, v1.toList() );
755
756             if( op=="=" || op=="<>" || op=="-" )
757             {
758                 remove( aNewList, v2.toList() );
759
760                 if( op=="=" )
761                     set( v1, aNewList.isEmpty() );
762                 else if( op=="<>" )
763                     set( v1, !aNewList.isEmpty() );
764                 else
765                     v1 = aNewList;
766             }
767             else if( op=="+" )
768             {
769                 add( aNewList, v2.toList() );
770                 v1 = aNewList;
771             }
772             else if( op=="*" )
773             {
774                 ValueSet toDelete;
775                 add( toDelete, aNewList );
776                 remove( toDelete, v2.toList() );
777                 remove( aNewList, toDelete );
778                 v1 = aNewList;
779             }
780         }
781         else if( op=="count" )
782             v2 = ( int )v2.toList().count();
783         else if( op=="in" )
784         {
785             if( v1.type()==QVariant::List )
786             {
787                 bool res = true;
788                 ValueSet::const_iterator anIt = v1.toList().begin(),
789                                          aLast = v1.toList().end();
790                 for( ; anIt!=aLast && res; anIt++ )
791                     res = v2.toList().contains( *anIt )>0;
792
793                 set( v1, res );
794             }
795             else
796                 v1 = v2.toList().contains( v1 );
797         }
798
799     return err;
800 }