Cherrypick from master 2004-11-05 12:56:36 UTC prascle <prascle> 'PR: mergefrom_BR_GEAY_05Nov04':
examples/fedges.unv
idl/SALOME_Comm.idl
make_config.in
salome_adm/unix/config.h.in
salome_adm/unix/config_files/check_lam.m4
salome_adm/unix/config_files/check_openpbs.m4
salome_adm/unix/config_files/check_sockets.m4
src/Batch/Batch_APIInternalFailureException.cxx
src/Batch/Batch_APIInternalFailureException.hxx
src/Batch/Batch_BatchManager.cxx
src/Batch/Batch_BatchManager.hxx
src/Batch/Batch_BatchManagerCatalog.cxx
src/Batch/Batch_BatchManagerCatalog.hxx
src/Batch/Batch_BatchManager_PBS.cxx
src/Batch/Batch_BatchManager_PBS.hxx
src/Batch/Batch_BoolType.cxx
src/Batch/Batch_BoolType.hxx
src/Batch/Batch_CharType.cxx
src/Batch/Batch_CharType.hxx
src/Batch/Batch_ConnexionFailureException.cxx
src/Batch/Batch_ConnexionFailureException.hxx
src/Batch/Batch_Couple.cxx
src/Batch/Batch_Couple.hxx
src/Batch/Batch_CoupleType.cxx
src/Batch/Batch_CoupleType.hxx
src/Batch/Batch_Date.cxx
src/Batch/Batch_Date.hxx
src/Batch/Batch_DateType.cxx
src/Batch/Batch_DateType.hxx
src/Batch/Batch_Environnement.cxx
src/Batch/Batch_Environnement.hxx
src/Batch/Batch_FactBatchManager.cxx
src/Batch/Batch_FactBatchManager.hxx
src/Batch/Batch_FactBatchManager_PBS.cxx
src/Batch/Batch_FactBatchManager_PBS.hxx
src/Batch/Batch_GenericException.cxx
src/Batch/Batch_GenericException.hxx
src/Batch/Batch_GenericType.cxx
src/Batch/Batch_GenericType.hxx
src/Batch/Batch_IntType.cxx
src/Batch/Batch_IntType.hxx
src/Batch/Batch_InvalidArgumentException.cxx
src/Batch/Batch_InvalidArgumentException.hxx
src/Batch/Batch_InvalidKeyException.cxx
src/Batch/Batch_InvalidKeyException.hxx
src/Batch/Batch_Job.cxx
src/Batch/Batch_Job.hxx
src/Batch/Batch_JobId.cxx
src/Batch/Batch_JobId.hxx
src/Batch/Batch_JobInfo.cxx
src/Batch/Batch_JobInfo.hxx
src/Batch/Batch_JobInfo_PBS.cxx
src/Batch/Batch_JobInfo_PBS.hxx
src/Batch/Batch_Job_PBS.cxx
src/Batch/Batch_Job_PBS.hxx
src/Batch/Batch_ListIsFullException.cxx
src/Batch/Batch_ListIsFullException.hxx
src/Batch/Batch_LongType.cxx
src/Batch/Batch_LongType.hxx
src/Batch/Batch_MapKey.cxx
src/Batch/Batch_MapKey.hxx
src/Batch/Batch_NotYetImplementedException.cxx
src/Batch/Batch_NotYetImplementedException.hxx
src/Batch/Batch_Parametre.cxx
src/Batch/Batch_Parametre.hxx
src/Batch/Batch_PyVersatile.cxx
src/Batch/Batch_PyVersatile.hxx
src/Batch/Batch_RunTimeException.cxx
src/Batch/Batch_RunTimeException.hxx
src/Batch/Batch_StringType.cxx
src/Batch/Batch_StringType.hxx
src/Batch/Batch_TypeMismatchException.cxx
src/Batch/Batch_TypeMismatchException.hxx
src/Batch/Batch_Versatile.cxx
src/Batch/Batch_Versatile.hxx
src/Batch/Makefile.in
src/Batch_SWIG/Batch_test.py
src/Batch_SWIG/Makefile.in
src/Batch_SWIG/libBatch_Swig.i
src/Batch_SWIG/libBatch_Swig_exception.i
src/Batch_SWIG/libBatch_Swig_typemap.i
src/CASCatch/CASCatch_SignalsHandler.cxx
src/CASCatch/CASCatch_SignalsHandler.h
src/CASCatch/Makefile.in
src/Communication/Makefile.in
src/Communication/MultiCommException.cxx
src/Communication/MultiCommException.hxx
src/Communication/Receiver.cxx
src/Communication/Receiver.hxx
src/Communication/ReceiverFactory.cxx
src/Communication/ReceiverFactory.hxx
src/Communication/Receivers.cxx
src/Communication/Receivers.hxx
src/Communication/SALOMEMultiComm.cxx
src/Communication/SALOMEMultiComm.hxx
src/Communication/SALOME_Comm_i.cxx
src/Communication/SALOME_Comm_i.hxx
src/Communication/SenderFactory.cxx
src/Communication/SenderFactory.hxx
src/Container/SALOME_Container_SignalsHandler.cxx
src/MSG2QM/LICENSE.QPL
src/MSG2QM/README
src/OCCViewer/OCCViewer_Prs.cxx
src/OCCViewer/OCCViewer_Prs.h
src/PatchQt/LICENSE.QPL
src/PatchQt/README
src/PatchQt/qfiledialogP.cxx
src/PatchQt/qfiledialogP.h
src/Plot2d/Plot2d_Prs.cxx
src/Plot2d/Plot2d_Prs.h
src/Prs/Makefile.in
src/Prs/SALOME_Prs.cxx
src/Prs/SALOME_Prs.h
src/Session/SALOME_Session_SignalsHandler.cxx
src/Utils/Utils_SignalsHandler.cxx
src/Utils/Utils_SignalsHandler.h
src/VTKFilter/SALOME_ShrinkFilter.cxx
src/VTKFilter/SALOME_ShrinkFilter.h
src/VTKViewer/VTKViewer_Actor.cxx
src/VTKViewer/VTKViewer_Actor.h
src/VTKViewer/VTKViewer_Algorithm.h
src/VTKViewer/VTKViewer_Functor.h
src/VTKViewer/VTKViewer_Prs.cxx
src/VTKViewer/VTKViewer_Prs.h
--- /dev/null
+ -1
+ 2411
+ 1 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 0.0000000000000000E+00
+ 2 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 0.0000000000000000E+00
+ 3 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 0.0000000000000000E+00
+ 4 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 0.0000000000000000E+00
+ 5 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 0.0000000000000000E+00
+ 6 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 0.0000000000000000E+00
+ 7 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 0.0000000000000000E+00
+ 8 0 0 0
+ 0.0000000000000000E+00 -1.4350000000000000E+01 0.0000000000000000E+00
+ 9 0 0 0
+ 0.0000000000000000E+00 -1.5500000000000000E+01 5.0000000000000000E-01
+ 10 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 1.7000000000000000E+00
+ 11 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 3.3500000000000001E+00
+ 12 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 4.9500000000000002E+00
+ 13 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 7.1550000000000002E+00
+ 14 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 9.3599999999999994E+00
+ 15 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 1.2359999999999999E+01
+ 16 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 1.5359999999999999E+01
+ 17 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 1.7609999999999999E+01
+ 18 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 1.8969999999999999E+01
+ 19 0 0 0
+ 0.0000000000000000E+00 -1.6129999999999999E+01 2.0800000000000001E+01
+ 20 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 2.1449999999999999E+01
+ 21 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 2.1449999999999999E+01
+ 22 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 2.1366000000000000E+01
+ 23 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 2.1239000000000001E+01
+ 24 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 2.1111999999999998E+01
+ 25 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 2.1027999999999999E+01
+ 26 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 2.0916000000000000E+01
+ 27 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 2.0000000000000000E+00
+ 28 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 1.8969999999999999E+01
+ 29 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 2.0000000000000000E+00
+ 30 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 2.0000000000000000E+00
+ 31 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 2.0000000000000000E+00
+ 32 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 2.0000000000000000E+00
+ 33 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 2.0000000000000000E+00
+ 34 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 2.0000000000000000E+00
+ 35 0 0 0
+ 0.0000000000000000E+00 -1.2877000000000001E+01 3.2160000000000002E+00
+ 36 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 4.9500000000000002E+00
+ 37 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 7.1550000000000002E+00
+ 38 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 9.3599999999999994E+00
+ 39 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 1.2359999999999999E+01
+ 40 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 1.5359999999999999E+01
+ 41 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 1.7609999999999999E+01
+ 42 0 0 0
+ 0.0000000000000000E+00 -1.4130000000000001E+01 1.8969999999999999E+01
+ 43 0 0 0
+ 0.0000000000000000E+00 -1.3600000000000000E+01 2.0000000000000000E+00
+ 44 0 0 0
+ 0.0000000000000000E+00 -1.5199999999999999E+01 3.8500000000000001E+00
+ 45 0 0 0
+ 0.0000000000000000E+00 -1.4500000000000000E+01 3.8500000000000001E+00
+ 46 0 0 0
+ 0.0000000000000000E+00 -1.4150000000000000E+01 3.1040000000000001E+00
+ 47 0 0 0
+ 0.0000000000000000E+00 -1.5199999999999999E+01 2.0000000000000000E+00
+ 48 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 3.6600000000000001E+00
+ 49 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 4.9500000000000002E+00
+ 50 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 3.0000000000000000E+00
+ 51 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 2.7999999999999998E+00
+ 52 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 1.7609999999999999E+01
+ 53 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 0.0000000000000000E+00
+ 54 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 0.0000000000000000E+00
+ 55 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 0.0000000000000000E+00
+ 56 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 0.0000000000000000E+00
+ 57 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 0.0000000000000000E+00
+ 58 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 0.0000000000000000E+00
+ 59 0 0 0
+ 0.0000000000000000E+00 1.4350000000000000E+01 0.0000000000000000E+00
+ 60 0 0 0
+ 0.0000000000000000E+00 1.5500000000000000E+01 5.0000000000000000E-01
+ 61 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 1.7000000000000000E+00
+ 62 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 3.3500000000000001E+00
+ 63 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 4.9500000000000002E+00
+ 64 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 7.1550000000000002E+00
+ 65 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 9.3599999999999994E+00
+ 66 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 1.2359999999999999E+01
+ 67 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 1.5359999999999999E+01
+ 68 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 1.7609999999999999E+01
+ 69 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 1.8969999999999999E+01
+ 70 0 0 0
+ 0.0000000000000000E+00 1.6129999999999999E+01 2.0800000000000001E+01
+ 71 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 2.1449999999999999E+01
+ 72 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 2.1449999999999999E+01
+ 73 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 2.1449999999999999E+01
+ 74 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 2.1366000000000000E+01
+ 75 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 2.1239000000000001E+01
+ 76 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 2.1111999999999998E+01
+ 77 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 2.1027999999999999E+01
+ 78 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 2.0916000000000000E+01
+ 79 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 2.0000000000000000E+00
+ 80 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 2.0000000000000000E+00
+ 81 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 2.0000000000000000E+00
+ 82 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 2.0000000000000000E+00
+ 83 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 2.0000000000000000E+00
+ 84 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 2.0000000000000000E+00
+ 85 0 0 0
+ 0.0000000000000000E+00 1.2877000000000001E+01 3.2160000000000002E+00
+ 86 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 4.9500000000000002E+00
+ 87 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 7.1550000000000002E+00
+ 88 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 9.3599999999999994E+00
+ 89 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 1.2359999999999999E+01
+ 90 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 1.5359999999999999E+01
+ 91 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 1.7609999999999999E+01
+ 92 0 0 0
+ 0.0000000000000000E+00 1.4130000000000001E+01 1.8969999999999999E+01
+ 93 0 0 0
+ 0.0000000000000000E+00 1.3600000000000000E+01 2.0000000000000000E+00
+ 94 0 0 0
+ 0.0000000000000000E+00 1.5199999999999999E+01 3.8500000000000001E+00
+ 95 0 0 0
+ 0.0000000000000000E+00 1.4500000000000000E+01 3.8500000000000001E+00
+ 96 0 0 0
+ 0.0000000000000000E+00 1.4150000000000000E+01 3.1040000000000001E+00
+ 97 0 0 0
+ 0.0000000000000000E+00 1.5199999999999999E+01 2.0000000000000000E+00
+ 98 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 3.6600000000000001E+00
+ 99 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 4.9500000000000002E+00
+ 100 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 3.0000000000000000E+00
+ 101 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 7.1550000000000002E+00
+ 102 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 9.3599999999999994E+00
+ 103 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 1.2359999999999999E+01
+ 104 0 0 0
+ 0.0000000000000000E+00 0.0000000000000000E+00 1.5359999999999999E+01
+ 105 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 7.1550000000000002E+00
+ 106 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 9.3599999999999994E+00
+ 107 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 1.2359999999999999E+01
+ 108 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 1.5359999999999999E+01
+ 109 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 1.7609999999999999E+01
+ 110 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 3.2149999999999999E+00
+ 111 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 3.2149999999999999E+00
+ 112 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 3.2149999999999999E+00
+ 113 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 3.2149999999999999E+00
+ 114 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 3.2149999999999999E+00
+ 115 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 3.2149999999999999E+00
+ 116 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 3.2149999999999999E+00
+ 117 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 3.2149999999999999E+00
+ 118 0 0 0
+ 0.0000000000000000E+00 2.3999999999999999E+00 1.8969999999999999E+01
+ 119 0 0 0
+ 0.0000000000000000E+00 -1.2877000000000001E+01 4.9500000000000002E+00
+ 120 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 4.9500000000000002E+00
+ 121 0 0 0
+ 0.0000000000000000E+00 1.2877000000000001E+01 4.9500000000000002E+00
+ 122 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 4.9500000000000002E+00
+ 123 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 4.9500000000000002E+00
+ 124 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 7.1550000000000002E+00
+ 125 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 1.7609999999999999E+01
+ 126 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 1.7609999999999999E+01
+ 127 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 7.1550000000000002E+00
+ 128 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 1.7609999999999999E+01
+ 129 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 4.9500000000000002E+00
+ 130 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 1.7609999999999999E+01
+ 131 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 7.1550000000000002E+00
+ 132 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 7.1550000000000002E+00
+ 133 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 4.9500000000000002E+00
+ 134 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 4.9500000000000002E+00
+ 135 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 4.9500000000000002E+00
+ 136 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 9.3599999999999994E+00
+ 137 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 1.2359999999999999E+01
+ 138 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 1.5359999999999999E+01
+ 139 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 4.9500000000000002E+00
+ 140 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 4.9500000000000002E+00
+ 141 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 1.5359999999999999E+01
+ 142 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 1.2359999999999999E+01
+ 143 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 9.3599999999999994E+00
+ 144 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 9.3599999999999994E+00
+ 145 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 1.2359999999999999E+01
+ 146 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 1.5359999999999999E+01
+ 147 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 1.5359999999999999E+01
+ 148 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 1.2359999999999999E+01
+ 149 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 9.3599999999999994E+00
+ 150 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 4.9500000000000002E+00
+ 151 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 4.9500000000000002E+00
+ 152 0 0 0
+ 0.0000000000000000E+00 4.0000000000000000E+00 1.8969999999999999E+01
+ 153 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 1.8969999999999999E+01
+ 154 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 1.8969999999999999E+01
+ 155 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 1.8969999999999999E+01
+ 156 0 0 0
+ 0.0000000000000000E+00 1.2000000000000000E+01 1.8969999999999999E+01
+ 157 0 0 0
+ 0.0000000000000000E+00 -2.3999999999999999E+00 1.8969999999999999E+01
+ 158 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 1.8969999999999999E+01
+ 159 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 1.8969999999999999E+01
+ 160 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 1.8969999999999999E+01
+ 161 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 1.8969999999999999E+01
+ 162 0 0 0
+ 0.0000000000000000E+00 -1.2000000000000000E+01 1.8969999999999999E+01
+ 163 0 0 0
+ 3.3999999999999999E+00 -4.0000000000000000E+00 0.0000000000000000E+00
+ 164 0 0 0
+ 3.3999999999999999E+00 -2.3999999999999999E+00 0.0000000000000000E+00
+ 165 0 0 0
+ 3.3999999999999999E+00 4.0000000000000000E+00 0.0000000000000000E+00
+ 166 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 0.0000000000000000E+00
+ 167 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 0.0000000000000000E+00
+ 168 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 3.6600000000000001E+00
+ 169 0 0 0
+ 3.3999999999999999E+00 -5.5999999999999996E+00 0.0000000000000000E+00
+ 170 0 0 0
+ 3.3999999999999999E+00 -8.0000000000000000E+00 0.0000000000000000E+00
+ 171 0 0 0
+ 3.3999999999999999E+00 -1.0400000000000000E+01 0.0000000000000000E+00
+ 172 0 0 0
+ 3.3999999999999999E+00 -4.0000000000000000E+00 2.0000000000000000E+00
+ 173 0 0 0
+ 3.3999999999999999E+00 -2.3999999999999999E+00 2.0000000000000000E+00
+ 174 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 2.0000000000000000E+00
+ 175 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 2.0000000000000000E+00
+ 176 0 0 0
+ 3.3999999999999999E+00 4.0000000000000000E+00 2.0000000000000000E+00
+ 177 0 0 0
+ 3.3999999999999999E+00 5.5999999999999996E+00 0.0000000000000000E+00
+ 178 0 0 0
+ 3.3999999999999999E+00 8.0000000000000000E+00 0.0000000000000000E+00
+ 179 0 0 0
+ 3.3999999999999999E+00 1.0400000000000000E+01 0.0000000000000000E+00
+ 180 0 0 0
+ 3.3999999999999999E+00 -2.3999999999999999E+00 3.0000000000000000E+00
+ 181 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 7.1550000000000002E+00
+ 182 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 7.1550000000000002E+00
+ 183 0 0 0
+ 3.3999999999999999E+00 -8.0000000000000000E+00 2.0000000000000000E+00
+ 184 0 0 0
+ 3.3999999999999999E+00 -1.0400000000000000E+01 2.0000000000000000E+00
+ 185 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 3.6600000000000001E+00
+ 186 0 0 0
+ 3.3999999999999999E+00 -1.2000000000000000E+01 0.0000000000000000E+00
+ 187 0 0 0
+ 3.3999999999999999E+00 -1.2000000000000000E+01 2.0000000000000000E+00
+ 188 0 0 0
+ 3.3999999999999999E+00 -1.4350000000000000E+01 0.0000000000000000E+00
+ 189 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 1.7609999999999999E+01
+ 190 0 0 0
+ 3.3999999999999999E+00 -1.2877000000000001E+01 3.2160000000000002E+00
+ 191 0 0 0
+ 3.3999999999999999E+00 -1.5500000000000000E+01 5.0000000000000000E-01
+ 192 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 1.7609999999999999E+01
+ 193 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 1.9800000000000001E+01
+ 194 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 1.7000000000000000E+00
+ 195 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 3.3500000000000001E+00
+ 196 0 0 0
+ 3.3999999999999999E+00 8.0000000000000000E+00 2.0000000000000000E+00
+ 197 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 7.1550000000000002E+00
+ 198 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 7.1550000000000002E+00
+ 199 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 7.1550000000000002E+00
+ 200 0 0 0
+ 3.3999999999999999E+00 1.2000000000000000E+01 0.0000000000000000E+00
+ 201 0 0 0
+ 3.3999999999999999E+00 1.0400000000000000E+01 2.0000000000000000E+00
+ 202 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 1.7609999999999999E+01
+ 203 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 1.7609999999999999E+01
+ 204 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 1.7609999999999999E+01
+ 205 0 0 0
+ 3.3999999999999999E+00 1.4350000000000000E+01 0.0000000000000000E+00
+ 206 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 4.9500000000000002E+00
+ 207 0 0 0
+ 3.3999999999999999E+00 1.2000000000000000E+01 2.0000000000000000E+00
+ 208 0 0 0
+ 3.3999999999999999E+00 1.5500000000000000E+01 5.0000000000000000E-01
+ 209 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 7.1550000000000002E+00
+ 210 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 1.2359999999999999E+01
+ 211 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 7.1550000000000002E+00
+ 212 0 0 0
+ 3.3999999999999999E+00 1.2877000000000001E+01 3.2160000000000002E+00
+ 213 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 1.7000000000000000E+00
+ 214 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 3.3500000000000001E+00
+ 215 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 7.1550000000000002E+00
+ 216 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 4.9500000000000002E+00
+ 217 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 9.3599999999999994E+00
+ 218 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 1.2359999999999999E+01
+ 219 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 4.9500000000000002E+00
+ 220 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 7.1550000000000002E+00
+ 221 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 7.1550000000000002E+00
+ 222 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 4.9500000000000002E+00
+ 223 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 1.2359999999999999E+01
+ 224 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 9.3599999999999994E+00
+ 225 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 1.5359999999999999E+01
+ 226 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 1.7609999999999999E+01
+ 227 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 1.8969999999999999E+01
+ 228 0 0 0
+ 3.3999999999999999E+00 -1.6129999999999999E+01 2.0800000000000001E+01
+ 229 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 9.3599999999999994E+00
+ 230 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 1.2359999999999999E+01
+ 231 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 1.2359999999999999E+01
+ 232 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 9.3599999999999994E+00
+ 233 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 1.5359999999999999E+01
+ 234 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 1.5359999999999999E+01
+ 235 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 1.7609999999999999E+01
+ 236 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 1.8969999999999999E+01
+ 237 0 0 0
+ 3.3999999999999999E+00 1.6129999999999999E+01 2.0800000000000001E+01
+ 238 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 2.0916000000000000E+01
+ 239 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 1.8969999999999999E+01
+ 240 0 0 0
+ 3.3999999999999999E+00 -1.2000000000000000E+01 2.1027999999999999E+01
+ 241 0 0 0
+ 3.3999999999999999E+00 -1.0400000000000000E+01 2.1111999999999998E+01
+ 242 0 0 0
+ 3.3999999999999999E+00 -8.0000000000000000E+00 2.1239000000000001E+01
+ 243 0 0 0
+ 3.3999999999999999E+00 -5.5999999999999996E+00 2.1366000000000000E+01
+ 244 0 0 0
+ 3.3999999999999999E+00 -4.0000000000000000E+00 2.1449999999999999E+01
+ 245 0 0 0
+ 3.3999999999999999E+00 -2.3999999999999999E+00 2.1449999999999999E+01
+ 246 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 2.1449999999999999E+01
+ 247 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 2.1449999999999999E+01
+ 248 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 1.7609999999999999E+01
+ 249 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 1.7609999999999999E+01
+ 250 0 0 0
+ 3.3999999999999999E+00 4.0000000000000000E+00 2.1449999999999999E+01
+ 251 0 0 0
+ 3.3999999999999999E+00 5.5999999999999996E+00 2.1366000000000000E+01
+ 252 0 0 0
+ 3.3999999999999999E+00 8.0000000000000000E+00 2.1239000000000001E+01
+ 253 0 0 0
+ 3.3999999999999999E+00 1.0400000000000000E+01 2.1111999999999998E+01
+ 254 0 0 0
+ 3.3999999999999999E+00 1.2000000000000000E+01 2.1027999999999999E+01
+ 255 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 2.0916000000000000E+01
+ 256 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 1.8969999999999999E+01
+ 257 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 7.1550000000000002E+00
+ 258 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 7.1550000000000002E+00
+ 259 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 1.5359999999999999E+01
+ 260 0 0 0
+ 2.2000000000000002E+00 2.3999999999999999E+00 4.9500000000000002E+00
+ 261 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 9.3599999999999994E+00
+ 262 0 0 0
+ 2.2000000000000002E+00 2.3999999999999999E+00 9.3599999999999994E+00
+ 263 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 1.5359999999999999E+01
+ 264 0 0 0
+ 2.2000000000000002E+00 2.3999999999999999E+00 1.5359999999999999E+01
+ 265 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 1.7609999999999999E+01
+ 266 0 0 0
+ 3.3999999999999999E+00 -1.4130000000000001E+01 1.7609999999999999E+01
+ 267 0 0 0
+ 3.3999999999999999E+00 1.4130000000000001E+01 1.7609999999999999E+01
+ 268 0 0 0
+ 2.2000000000000002E+00 -1.2877000000000001E+01 4.9500000000000002E+00
+ 269 0 0 0
+ 2.2000000000000002E+00 -2.3999999999999999E+00 4.9500000000000002E+00
+ 270 0 0 0
+ 2.2000000000000002E+00 1.2877000000000001E+01 4.9500000000000002E+00
+ 271 0 0 0
+ 2.2000000000000002E+00 4.0000000000000000E+00 4.9500000000000002E+00
+ 272 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 9.3599999999999994E+00
+ 273 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 1.2359999999999999E+01
+ 274 0 0 0
+ 0.0000000000000000E+00 -4.0000000000000000E+00 1.5359999999999999E+01
+ 275 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 1.5359999999999999E+01
+ 276 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 1.2359999999999999E+01
+ 277 0 0 0
+ 3.3999999999999999E+00 -5.5999999999999996E+00 2.0000000000000000E+00
+ 278 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 4.9500000000000002E+00
+ 279 0 0 0
+ 0.0000000000000000E+00 -1.0400000000000000E+01 9.3599999999999994E+00
+ 280 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 9.3599999999999994E+00
+ 281 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 1.2359999999999999E+01
+ 282 0 0 0
+ 0.0000000000000000E+00 5.5999999999999996E+00 1.5359999999999999E+01
+ 283 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 1.2359999999999999E+01
+ 284 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 1.2359999999999999E+01
+ 285 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 1.5359999999999999E+01
+ 286 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 1.5359999999999999E+01
+ 287 0 0 0
+ 0.0000000000000000E+00 1.0400000000000000E+01 9.3599999999999994E+00
+ 288 0 0 0
+ 0.0000000000000000E+00 8.0000000000000000E+00 9.3599999999999994E+00
+ 289 0 0 0
+ 3.3999999999999999E+00 5.5999999999999996E+00 2.0000000000000000E+00
+ 290 0 0 0
+ 2.2000000000000002E+00 -2.3999999999999999E+00 9.3599999999999994E+00
+ 291 0 0 0
+ 2.2000000000000002E+00 -2.3999999999999999E+00 1.5359999999999999E+01
+ 292 0 0 0
+ 2.2000000000000002E+00 -1.2000000000000000E+01 4.9500000000000002E+00
+ 293 0 0 0
+ 2.2000000000000002E+00 -1.2000000000000000E+01 1.5359999999999999E+01
+ 294 0 0 0
+ 3.3999999999999999E+00 -2.3999999999999999E+00 1.9800000000000001E+01
+ 295 0 0 0
+ 2.2000000000000002E+00 -1.2000000000000000E+01 9.3599999999999994E+00
+ 296 0 0 0
+ 2.2000000000000002E+00 4.0000000000000000E+00 9.3599999999999994E+00
+ 297 0 0 0
+ 3.3999999999999999E+00 -1.2000000000000000E+01 1.9527999999999999E+01
+ 298 0 0 0
+ 2.2000000000000002E+00 4.0000000000000000E+00 1.5359999999999999E+01
+ 299 0 0 0
+ 2.2000000000000002E+00 1.2000000000000000E+01 1.5359999999999999E+01
+ 300 0 0 0
+ 2.2000000000000002E+00 1.2000000000000000E+01 4.9500000000000002E+00
+ 301 0 0 0
+ 2.2000000000000002E+00 1.2000000000000000E+01 9.3599999999999994E+00
+ 302 0 0 0
+ 3.3999999999999999E+00 -1.3600000000000000E+01 2.0000000000000000E+00
+ 303 0 0 0
+ 3.3999999999999999E+00 1.2000000000000000E+01 1.9527999999999999E+01
+ 304 0 0 0
+ 3.3999999999999999E+00 -4.0000000000000000E+00 2.7999999999999998E+00
+ 305 0 0 0
+ 3.3999999999999999E+00 -2.3999999999999999E+00 3.6600000000000001E+00
+ 306 0 0 0
+ 2.2000000000000002E+00 -4.0000000000000000E+00 4.9500000000000002E+00
+ 307 0 0 0
+ 3.3999999999999999E+00 1.3600000000000000E+01 2.0000000000000000E+00
+ 308 0 0 0
+ 2.2000000000000002E+00 5.5999999999999996E+00 4.9500000000000002E+00
+ 309 0 0 0
+ 2.2000000000000002E+00 1.0400000000000000E+01 4.9500000000000002E+00
+ 310 0 0 0
+ 2.2000000000000002E+00 8.0000000000000000E+00 4.9500000000000002E+00
+ 311 0 0 0
+ 2.2000000000000002E+00 -1.0400000000000000E+01 4.9500000000000002E+00
+ 312 0 0 0
+ 3.3999999999999999E+00 4.0000000000000000E+00 3.0000000000000000E+00
+ 313 0 0 0
+ 2.2000000000000002E+00 -8.0000000000000000E+00 4.9500000000000002E+00
+ 314 0 0 0
+ 2.2000000000000002E+00 -5.5999999999999996E+00 4.9500000000000002E+00
+ 315 0 0 0
+ 3.3999999999999999E+00 -1.5199999999999999E+01 2.0000000000000000E+00
+ 316 0 0 0
+ 3.3999999999999999E+00 -1.4150000000000000E+01 3.1040000000000001E+00
+ 317 0 0 0
+ 3.3999999999999999E+00 -4.0000000000000000E+00 1.9949999999999999E+01
+ 318 0 0 0
+ 3.3999999999999999E+00 -1.0400000000000000E+01 1.9611999999999998E+01
+ 319 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 4.9500000000000002E+00
+ 320 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 1.7609999999999999E+01
+ 321 0 0 0
+ 3.3999999999999999E+00 4.0000000000000000E+00 1.9949999999999999E+01
+ 322 0 0 0
+ 3.3999999999999999E+00 1.5199999999999999E+01 2.0000000000000000E+00
+ 323 0 0 0
+ 3.3999999999999999E+00 1.4150000000000000E+01 3.1040000000000001E+00
+ 324 0 0 0
+ 3.3999999999999999E+00 1.0400000000000000E+01 1.9611999999999998E+01
+ 325 0 0 0
+ 3.3999999999999999E+00 -1.5199999999999999E+01 3.8500000000000001E+00
+ 326 0 0 0
+ 3.3999999999999999E+00 -1.4500000000000000E+01 3.8500000000000001E+00
+ 327 0 0 0
+ 3.3999999999999999E+00 -8.0000000000000000E+00 1.9739000000000001E+01
+ 328 0 0 0
+ 3.3999999999999999E+00 -5.5999999999999996E+00 1.9866000000000000E+01
+ 329 0 0 0
+ 3.3999999999999999E+00 8.0000000000000000E+00 1.9739000000000001E+01
+ 330 0 0 0
+ 3.3999999999999999E+00 5.5999999999999996E+00 1.9866000000000000E+01
+ 331 0 0 0
+ 3.3999999999999999E+00 1.5199999999999999E+01 3.8500000000000001E+00
+ 332 0 0 0
+ 3.3999999999999999E+00 1.4500000000000000E+01 3.8500000000000001E+00
+ 333 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 1.5359999999999999E+01
+ 334 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 1.5359999999999999E+01
+ 335 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 1.2359999999999999E+01
+ 336 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 1.2359999999999999E+01
+ 337 0 0 0
+ 0.0000000000000000E+00 -8.0000000000000000E+00 9.3599999999999994E+00
+ 338 0 0 0
+ 0.0000000000000000E+00 -5.5999999999999996E+00 9.3599999999999994E+00
+ 339 0 0 0
+ 3.3999999999999999E+00 0.0000000000000000E+00 1.8969999999999999E+01
+ 340 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 7.1550000000000002E+00
+ 341 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 1.5359999999999999E+01
+ 342 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 9.3599999999999994E+00
+ 343 0 0 0
+ 3.3999999999999999E+00 2.3999999999999999E+00 1.2359999999999999E+01
+ 344 0 0 0
+ 6.7999999999999998E+00 -2.3999999999999999E+00 0.0000000000000000E+00
+ 345 0 0 0
+ 6.7999999999999998E+00 -4.0000000000000000E+00 0.0000000000000000E+00
+ 346 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 0.0000000000000000E+00
+ 347 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 0.0000000000000000E+00
+ 348 0 0 0
+ 6.7999999999999998E+00 4.0000000000000000E+00 0.0000000000000000E+00
+ 349 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 2.0000000000000000E+00
+ 350 0 0 0
+ 6.7999999999999998E+00 -2.3999999999999999E+00 2.0000000000000000E+00
+ 351 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 3.6600000000000001E+00
+ 352 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 2.0000000000000000E+00
+ 353 0 0 0
+ 6.7999999999999998E+00 -5.5999999999999996E+00 0.0000000000000000E+00
+ 354 0 0 0
+ 6.7999999999999998E+00 -4.0000000000000000E+00 2.0000000000000000E+00
+ 355 0 0 0
+ 6.7999999999999998E+00 -8.0000000000000000E+00 0.0000000000000000E+00
+ 356 0 0 0
+ 6.7999999999999998E+00 -1.0400000000000000E+01 0.0000000000000000E+00
+ 357 0 0 0
+ 6.7999999999999998E+00 5.5999999999999996E+00 0.0000000000000000E+00
+ 358 0 0 0
+ 6.7999999999999998E+00 4.0000000000000000E+00 2.0000000000000000E+00
+ 359 0 0 0
+ 6.7999999999999998E+00 8.0000000000000000E+00 0.0000000000000000E+00
+ 360 0 0 0
+ 6.7999999999999998E+00 1.0400000000000000E+01 0.0000000000000000E+00
+ 361 0 0 0
+ 6.7999999999999998E+00 -1.2000000000000000E+01 0.0000000000000000E+00
+ 362 0 0 0
+ 6.7999999999999998E+00 -8.0000000000000000E+00 2.0000000000000000E+00
+ 363 0 0 0
+ 6.7999999999999998E+00 -1.0400000000000000E+01 2.0000000000000000E+00
+ 364 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 7.1550000000000002E+00
+ 365 0 0 0
+ 6.7999999999999998E+00 -1.2000000000000000E+01 2.0000000000000000E+00
+ 366 0 0 0
+ 6.7999999999999998E+00 -1.4350000000000000E+01 0.0000000000000000E+00
+ 367 0 0 0
+ 6.7999999999999998E+00 -1.2877000000000001E+01 3.2160000000000002E+00
+ 368 0 0 0
+ 6.7999999999999998E+00 -1.5500000000000000E+01 5.0000000000000000E-01
+ 369 0 0 0
+ 6.7999999999999998E+00 1.2000000000000000E+01 0.0000000000000000E+00
+ 370 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 1.7000000000000000E+00
+ 371 0 0 0
+ 6.7999999999999998E+00 8.0000000000000000E+00 2.0000000000000000E+00
+ 372 0 0 0
+ 2.2000000000000002E+00 -4.0000000000000000E+00 9.3599999999999994E+00
+ 373 0 0 0
+ 6.7999999999999998E+00 1.0400000000000000E+01 2.0000000000000000E+00
+ 374 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 9.3599999999999994E+00
+ 375 0 0 0
+ 2.2000000000000002E+00 -4.0000000000000000E+00 1.5359999999999999E+01
+ 376 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 4.9500000000000002E+00
+ 377 0 0 0
+ 6.7999999999999998E+00 1.4350000000000000E+01 0.0000000000000000E+00
+ 378 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 3.3500000000000001E+00
+ 379 0 0 0
+ 6.7999999999999998E+00 1.2000000000000000E+01 2.0000000000000000E+00
+ 380 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 4.9500000000000002E+00
+ 381 0 0 0
+ 2.2000000000000002E+00 -1.0400000000000000E+01 1.5359999999999999E+01
+ 382 0 0 0
+ 6.7999999999999998E+00 1.5500000000000000E+01 5.0000000000000000E-01
+ 383 0 0 0
+ 2.2000000000000002E+00 -1.0400000000000000E+01 9.3599999999999994E+00
+ 384 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 7.1550000000000002E+00
+ 385 0 0 0
+ 2.2000000000000002E+00 5.5999999999999996E+00 9.3599999999999994E+00
+ 386 0 0 0
+ 2.2000000000000002E+00 1.0400000000000000E+01 9.3599999999999994E+00
+ 387 0 0 0
+ 2.2000000000000002E+00 8.0000000000000000E+00 9.3599999999999994E+00
+ 388 0 0 0
+ 6.7999999999999998E+00 1.2877000000000001E+01 3.2160000000000002E+00
+ 389 0 0 0
+ 2.2000000000000002E+00 5.5999999999999996E+00 1.5359999999999999E+01
+ 390 0 0 0
+ 2.2000000000000002E+00 1.0400000000000000E+01 1.5359999999999999E+01
+ 391 0 0 0
+ 2.2000000000000002E+00 8.0000000000000000E+00 1.5359999999999999E+01
+ 392 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 1.7000000000000000E+00
+ 393 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 7.1550000000000002E+00
+ 394 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 1.2359999999999999E+01
+ 395 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 9.3599999999999994E+00
+ 396 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 3.3500000000000001E+00
+ 397 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 4.9500000000000002E+00
+ 398 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 1.2359999999999999E+01
+ 399 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 9.3599999999999994E+00
+ 400 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 4.9500000000000002E+00
+ 401 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 1.5359999999999999E+01
+ 402 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 7.1550000000000002E+00
+ 403 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 7.1550000000000002E+00
+ 404 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 1.2359999999999999E+01
+ 405 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 1.5359999999999999E+01
+ 406 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 9.3599999999999994E+00
+ 407 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 9.3599999999999994E+00
+ 408 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 1.7609999999999999E+01
+ 409 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 1.5359999999999999E+01
+ 410 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 1.8969999999999999E+01
+ 411 0 0 0
+ 6.7999999999999998E+00 -1.6129999999999999E+01 2.0800000000000001E+01
+ 412 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 1.2359999999999999E+01
+ 413 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 1.2359999999999999E+01
+ 414 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 1.5359999999999999E+01
+ 415 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 1.7609999999999999E+01
+ 416 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 1.8969999999999999E+01
+ 417 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 2.0916000000000000E+01
+ 418 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 1.8969999999999999E+01
+ 419 0 0 0
+ 6.7999999999999998E+00 1.6129999999999999E+01 2.0800000000000001E+01
+ 420 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 1.5359999999999999E+01
+ 421 0 0 0
+ 6.7999999999999998E+00 -1.2000000000000000E+01 2.1027999999999999E+01
+ 422 0 0 0
+ 6.7999999999999998E+00 -1.0400000000000000E+01 2.1111999999999998E+01
+ 423 0 0 0
+ 6.7999999999999998E+00 -8.0000000000000000E+00 2.1239000000000001E+01
+ 424 0 0 0
+ 6.7999999999999998E+00 -5.5999999999999996E+00 2.1366000000000000E+01
+ 425 0 0 0
+ 6.7999999999999998E+00 -4.0000000000000000E+00 2.1449999999999999E+01
+ 426 0 0 0
+ 6.7999999999999998E+00 -2.3999999999999999E+00 2.1449999999999999E+01
+ 427 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 2.1449999999999999E+01
+ 428 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 2.1449999999999999E+01
+ 429 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 2.0916000000000000E+01
+ 430 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 1.8969999999999999E+01
+ 431 0 0 0
+ 6.7999999999999998E+00 4.0000000000000000E+00 2.1449999999999999E+01
+ 432 0 0 0
+ 6.7999999999999998E+00 1.2000000000000000E+01 2.1027999999999999E+01
+ 433 0 0 0
+ 6.7999999999999998E+00 1.0400000000000000E+01 2.1111999999999998E+01
+ 434 0 0 0
+ 6.7999999999999998E+00 5.5999999999999996E+00 2.1366000000000000E+01
+ 435 0 0 0
+ 6.7999999999999998E+00 8.0000000000000000E+00 2.1239000000000001E+01
+ 436 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 4.9500000000000002E+00
+ 437 0 0 0
+ 6.7999999999999998E+00 -5.5999999999999996E+00 2.0000000000000000E+00
+ 438 0 0 0
+ 6.7999999999999998E+00 -2.3999999999999999E+00 3.0000000000000000E+00
+ 439 0 0 0
+ 6.7999999999999998E+00 5.5999999999999996E+00 2.0000000000000000E+00
+ 440 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 3.6600000000000001E+00
+ 441 0 0 0
+ 2.2000000000000002E+00 -8.0000000000000000E+00 1.5359999999999999E+01
+ 442 0 0 0
+ 2.2000000000000002E+00 -5.5999999999999996E+00 1.5359999999999999E+01
+ 443 0 0 0
+ 2.2000000000000002E+00 -8.0000000000000000E+00 9.3599999999999994E+00
+ 444 0 0 0
+ 2.2000000000000002E+00 -5.5999999999999996E+00 9.3599999999999994E+00
+ 445 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 1.7609999999999999E+01
+ 446 0 0 0
+ 6.7999999999999998E+00 -1.4130000000000001E+01 1.7609999999999999E+01
+ 447 0 0 0
+ 6.7999999999999998E+00 1.4130000000000001E+01 1.7609999999999999E+01
+ 448 0 0 0
+ 6.7999999999999998E+00 0.0000000000000000E+00 1.8969999999999999E+01
+ 449 0 0 0
+ 6.7999999999999998E+00 -4.0000000000000000E+00 2.7999999999999998E+00
+ 450 0 0 0
+ 6.7999999999999998E+00 -2.3999999999999999E+00 3.6600000000000001E+00
+ 451 0 0 0
+ 6.7999999999999998E+00 4.0000000000000000E+00 3.0000000000000000E+00
+ 452 0 0 0
+ 6.7999999999999998E+00 -1.3600000000000000E+01 2.0000000000000000E+00
+ 453 0 0 0
+ 1.0199999999999999E+01 -2.3999999999999999E+00 0.0000000000000000E+00
+ 454 0 0 0
+ 1.0199999999999999E+01 -4.0000000000000000E+00 0.0000000000000000E+00
+ 455 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 0.0000000000000000E+00
+ 456 0 0 0
+ 1.0199999999999999E+01 2.3999999999999999E+00 0.0000000000000000E+00
+ 457 0 0 0
+ 1.0199999999999999E+01 4.0000000000000000E+00 0.0000000000000000E+00
+ 458 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 4.9500000000000002E+00
+ 459 0 0 0
+ 1.0199999999999999E+01 -2.3999999999999999E+00 2.0000000000000000E+00
+ 460 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 2.0000000000000000E+00
+ 461 0 0 0
+ 1.0199999999999999E+01 2.3999999999999999E+00 2.0000000000000000E+00
+ 462 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 3.6600000000000001E+00
+ 463 0 0 0
+ 1.0199999999999999E+01 -5.5999999999999996E+00 0.0000000000000000E+00
+ 464 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 1.9800000000000001E+01
+ 465 0 0 0
+ 1.0199999999999999E+01 -4.0000000000000000E+00 2.0000000000000000E+00
+ 466 0 0 0
+ 1.0199999999999999E+01 -8.0000000000000000E+00 0.0000000000000000E+00
+ 467 0 0 0
+ 1.0199999999999999E+01 5.5999999999999996E+00 0.0000000000000000E+00
+ 468 0 0 0
+ 6.7999999999999998E+00 1.3600000000000000E+01 2.0000000000000000E+00
+ 469 0 0 0
+ 1.0199999999999999E+01 -1.0400000000000000E+01 0.0000000000000000E+00
+ 470 0 0 0
+ 1.0199999999999999E+01 4.0000000000000000E+00 2.0000000000000000E+00
+ 471 0 0 0
+ 1.0199999999999999E+01 8.0000000000000000E+00 0.0000000000000000E+00
+ 472 0 0 0
+ 1.0199999999999999E+01 1.0400000000000000E+01 0.0000000000000000E+00
+ 473 0 0 0
+ 1.0199999999999999E+01 -1.2000000000000000E+01 0.0000000000000000E+00
+ 474 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 7.1550000000000002E+00
+ 475 0 0 0
+ 1.0199999999999999E+01 -8.0000000000000000E+00 2.0000000000000000E+00
+ 476 0 0 0
+ 1.0199999999999999E+01 -1.0400000000000000E+01 2.0000000000000000E+00
+ 477 0 0 0
+ 6.7999999999999998E+00 -1.4150000000000000E+01 3.1040000000000001E+00
+ 478 0 0 0
+ 1.0199999999999999E+01 -1.2000000000000000E+01 2.0000000000000000E+00
+ 479 0 0 0
+ 1.0199999999999999E+01 -1.4350000000000000E+01 0.0000000000000000E+00
+ 480 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 7.1550000000000002E+00
+ 481 0 0 0
+ 6.7999999999999998E+00 -1.5199999999999999E+01 2.0000000000000000E+00
+ 482 0 0 0
+ 6.7999999999999998E+00 -1.5199999999999999E+01 3.8500000000000001E+00
+ 483 0 0 0
+ 6.7999999999999998E+00 -1.4500000000000000E+01 3.8500000000000001E+00
+ 484 0 0 0
+ 1.0199999999999999E+01 1.2000000000000000E+01 0.0000000000000000E+00
+ 485 0 0 0
+ 1.0199999999999999E+01 -1.2877000000000001E+01 3.2160000000000002E+00
+ 486 0 0 0
+ 1.0199999999999999E+01 8.0000000000000000E+00 2.0000000000000000E+00
+ 487 0 0 0
+ 1.0199999999999999E+01 -1.5500000000000000E+01 5.0000000000000000E-01
+ 488 0 0 0
+ 1.0199999999999999E+01 1.0400000000000000E+01 2.0000000000000000E+00
+ 489 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 9.3599999999999994E+00
+ 490 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 1.7000000000000000E+00
+ 491 0 0 0
+ 1.0199999999999999E+01 1.4350000000000000E+01 0.0000000000000000E+00
+ 492 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 9.3599999999999994E+00
+ 493 0 0 0
+ 1.0199999999999999E+01 1.2000000000000000E+01 2.0000000000000000E+00
+ 494 0 0 0
+ 6.7999999999999998E+00 1.5199999999999999E+01 2.0000000000000000E+00
+ 495 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 4.9500000000000002E+00
+ 496 0 0 0
+ 6.7999999999999998E+00 1.4150000000000000E+01 3.1040000000000001E+00
+ 497 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 3.3500000000000001E+00
+ 498 0 0 0
+ 1.0199999999999999E+01 1.5500000000000000E+01 5.0000000000000000E-01
+ 499 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 4.9500000000000002E+00
+ 500 0 0 0
+ 6.7999999999999998E+00 1.5199999999999999E+01 3.8500000000000001E+00
+ 501 0 0 0
+ 6.7999999999999998E+00 1.4500000000000000E+01 3.8500000000000001E+00
+ 502 0 0 0
+ 6.7999999999999998E+00 -1.2000000000000000E+01 1.9527999999999999E+01
+ 503 0 0 0
+ 1.0199999999999999E+01 1.2877000000000001E+01 3.2160000000000002E+00
+ 504 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 7.1550000000000002E+00
+ 505 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 7.1550000000000002E+00
+ 506 0 0 0
+ 6.7999999999999998E+00 -2.3999999999999999E+00 1.9800000000000001E+01
+ 507 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 1.7000000000000000E+00
+ 508 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 1.2359999999999999E+01
+ 509 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 1.2359999999999999E+01
+ 510 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 9.3599999999999994E+00
+ 511 0 0 0
+ 6.7999999999999998E+00 1.2000000000000000E+01 1.9527999999999999E+01
+ 512 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 9.3599999999999994E+00
+ 513 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 1.5359999999999999E+01
+ 514 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 4.9500000000000002E+00
+ 515 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 1.2359999999999999E+01
+ 516 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 3.3500000000000001E+00
+ 517 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 4.9500000000000002E+00
+ 518 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 1.5359999999999999E+01
+ 519 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 7.1550000000000002E+00
+ 520 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 1.2359999999999999E+01
+ 521 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 7.1550000000000002E+00
+ 522 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 1.5359999999999999E+01
+ 523 0 0 0
+ 6.7999999999999998E+00 2.3999999999999999E+00 1.7609999999999999E+01
+ 524 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 9.3599999999999994E+00
+ 525 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 9.3599999999999994E+00
+ 526 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 1.5359999999999999E+01
+ 527 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 1.7609999999999999E+01
+ 528 0 0 0
+ 1.0199999999999999E+01 -5.5999999999999996E+00 2.0000000000000000E+00
+ 529 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 1.2359999999999999E+01
+ 530 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 4.9500000000000002E+00
+ 531 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 1.8969999999999999E+01
+ 532 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 1.2359999999999999E+01
+ 533 0 0 0
+ 1.0199999999999999E+01 -1.6129999999999999E+01 2.0800000000000001E+01
+ 534 0 0 0
+ 1.0199999999999999E+01 5.5999999999999996E+00 2.0000000000000000E+00
+ 536 0 0 0
+ 6.7999999999999998E+00 -1.0400000000000000E+01 1.9611999999999998E+01
+ 538 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 1.5359999999999999E+01
+ 539 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 1.5359999999999999E+01
+ 540 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 1.8969999999999999E+01
+ 541 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 2.0916000000000000E+01
+ 542 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 1.7609999999999999E+01
+ 543 0 0 0
+ 6.7999999999999998E+00 -4.0000000000000000E+00 1.9949999999999999E+01
+ 544 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 1.8969999999999999E+01
+ 545 0 0 0
+ 6.7999999999999998E+00 -8.0000000000000000E+00 1.9739000000000001E+01
+ 546 0 0 0
+ 6.7999999999999998E+00 -5.5999999999999996E+00 1.9866000000000000E+01
+ 547 0 0 0
+ 1.0199999999999999E+01 -1.2000000000000000E+01 2.1027999999999999E+01
+ 548 0 0 0
+ 1.0199999999999999E+01 1.6129999999999999E+01 2.0800000000000001E+01
+ 549 0 0 0
+ 6.7999999999999998E+00 4.0000000000000000E+00 1.9949999999999999E+01
+ 550 0 0 0
+ 1.0199999999999999E+01 -1.0400000000000000E+01 2.1111999999999998E+01
+ 551 0 0 0
+ 6.7999999999999998E+00 1.0400000000000000E+01 1.9611999999999998E+01
+ 552 0 0 0
+ 6.7999999999999998E+00 8.0000000000000000E+00 1.9739000000000001E+01
+ 553 0 0 0
+ 6.7999999999999998E+00 5.5999999999999996E+00 1.9866000000000000E+01
+ 554 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 1.8969999999999999E+01
+ 555 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 2.0916000000000000E+01
+ 556 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 2.1449999999999999E+01
+ 557 0 0 0
+ 1.0199999999999999E+01 -8.0000000000000000E+00 2.1239000000000001E+01
+ 558 0 0 0
+ 1.0199999999999999E+01 -2.3999999999999999E+00 2.1449999999999999E+01
+ 559 0 0 0
+ 1.0199999999999999E+01 -4.0000000000000000E+00 2.1449999999999999E+01
+ 560 0 0 0
+ 1.0199999999999999E+01 -5.5999999999999996E+00 2.1366000000000000E+01
+ 561 0 0 0
+ 1.0199999999999999E+01 2.3999999999999999E+00 2.1449999999999999E+01
+ 562 0 0 0
+ 1.0199999999999999E+01 1.2000000000000000E+01 2.1027999999999999E+01
+ 563 0 0 0
+ 1.0199999999999999E+01 4.0000000000000000E+00 2.1449999999999999E+01
+ 564 0 0 0
+ 1.0199999999999999E+01 1.0400000000000000E+01 2.1111999999999998E+01
+ 565 0 0 0
+ 1.0199999999999999E+01 5.5999999999999996E+00 2.1366000000000000E+01
+ 566 0 0 0
+ 1.0199999999999999E+01 8.0000000000000000E+00 2.1239000000000001E+01
+ 569 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 1.7609999999999999E+01
+ 570 0 0 0
+ 1.0199999999999999E+01 -1.4130000000000001E+01 1.7609999999999999E+01
+ 583 0 0 0
+ 1.0199999999999999E+01 1.4130000000000001E+01 1.7609999999999999E+01
+ 591 0 0 0
+ 1.0199999999999999E+01 0.0000000000000000E+00 1.8969999999999999E+01
+ 592 0 0 0
+ 1.0199999999999999E+01 -3.2556229999999999E-02 9.5263449999999992E+00
+ -1
+ -1
+ 2412
+ 1 44 2 1 7 4
+ 1 167 164 2
+ 2 44 2 1 7 4
+ 167 346 344 164
+ 3 44 2 1 7 4
+ 346 455 453 344
+ 9 44 2 1 7 4
+ 2 164 163 3
+ 10 44 2 1 7 4
+ 164 344 345 163
+ 11 44 2 1 7 4
+ 344 453 454 345
+ 17 44 2 1 7 4
+ 3 163 169 4
+ 18 44 2 1 7 4
+ 163 345 353 169
+ 19 44 2 1 7 4
+ 345 454 463 353
+ 25 44 2 1 7 4
+ 4 169 170 5
+ 26 44 2 1 7 4
+ 169 353 355 170
+ 27 44 2 1 7 4
+ 353 463 466 355
+ 33 44 2 1 7 4
+ 5 170 171 6
+ 34 44 2 1 7 4
+ 170 355 356 171
+ 35 44 2 1 7 4
+ 355 466 469 356
+ 41 44 2 1 7 4
+ 6 171 186 7
+ 42 44 2 1 7 4
+ 171 356 361 186
+ 43 44 2 1 7 4
+ 356 469 473 361
+ 49 44 2 1 7 4
+ 7 186 188 8
+ 50 44 2 1 7 4
+ 186 361 366 188
+ 51 44 2 1 7 4
+ 361 473 479 366
+ 57 44 2 1 7 4
+ 8 188 191 9
+ 58 44 2 1 7 4
+ 188 366 368 191
+ 59 44 2 1 7 4
+ 366 479 487 368
+ 65 44 2 1 7 4
+ 9 191 194 10
+ 66 44 2 1 7 4
+ 191 368 370 194
+ 67 44 2 1 7 4
+ 368 487 490 370
+ 73 44 2 1 7 4
+ 10 194 195 11
+ 74 44 2 1 7 4
+ 194 370 378 195
+ 75 44 2 1 7 4
+ 370 490 497 378
+ 81 44 2 1 7 4
+ 11 195 206 12
+ 82 44 2 1 7 4
+ 195 378 380 206
+ 83 44 2 1 7 4
+ 378 497 499 380
+ 89 44 2 1 7 4
+ 12 206 209 13
+ 90 44 2 1 7 4
+ 206 380 384 209
+ 91 44 2 1 7 4
+ 380 499 505 384
+ 97 44 2 1 7 4
+ 13 209 217 14
+ 98 44 2 1 7 4
+ 209 384 395 217
+ 99 44 2 1 7 4
+ 384 505 510 395
+ 105 44 2 1 7 4
+ 14 217 218 15
+ 106 44 2 1 7 4
+ 217 395 398 218
+ 107 44 2 1 7 4
+ 395 510 515 398
+ 113 44 2 1 7 4
+ 15 218 225 16
+ 114 44 2 1 7 4
+ 218 398 405 225
+ 115 44 2 1 7 4
+ 398 515 522 405
+ 121 44 2 1 7 4
+ 16 225 226 17
+ 122 44 2 1 7 4
+ 225 405 408 226
+ 123 44 2 1 7 4
+ 405 522 527 408
+ 129 44 2 1 7 4
+ 17 226 227 18
+ 130 44 2 1 7 4
+ 226 408 410 227
+ 131 44 2 1 7 4
+ 408 527 531 410
+ 137 44 2 1 7 4
+ 18 227 228 19
+ 138 44 2 1 7 4
+ 227 410 411 228
+ 139 44 2 1 7 4
+ 410 531 533 411
+ 145 44 2 1 7 4
+ 20 245 244 21
+ 146 44 2 1 7 4
+ 245 426 425 244
+ 147 44 2 1 7 4
+ 426 558 559 425
+ 153 44 2 1 7 4
+ 21 244 243 22
+ 154 44 2 1 7 4
+ 244 425 424 243
+ 155 44 2 1 7 4
+ 425 559 560 424
+ 161 44 2 1 7 4
+ 22 243 242 23
+ 162 44 2 1 7 4
+ 243 424 423 242
+ 163 44 2 1 7 4
+ 424 560 557 423
+ 169 44 2 1 7 4
+ 23 242 241 24
+ 170 44 2 1 7 4
+ 242 423 422 241
+ 171 44 2 1 7 4
+ 423 557 550 422
+ 177 44 2 1 7 4
+ 24 241 240 25
+ 178 44 2 1 7 4
+ 241 422 421 240
+ 179 44 2 1 7 4
+ 422 550 547 421
+ 185 44 2 1 7 4
+ 25 240 238 26
+ 186 44 2 1 7 4
+ 240 421 417 238
+ 187 44 2 1 7 4
+ 421 547 541 417
+ 193 44 2 1 7 4
+ 26 238 228 19
+ 194 44 2 1 7 4
+ 238 417 411 228
+ 195 44 2 1 7 4
+ 417 541 533 411
+ 201 44 2 1 7 4
+ 27 174 173 29
+ 202 44 2 1 7 4
+ 174 349 350 173
+ 203 44 2 1 7 4
+ 349 460 459 350
+ 209 44 2 1 7 4
+ 29 173 172 30
+ 210 44 2 1 7 4
+ 173 350 354 172
+ 211 44 2 1 7 4
+ 350 459 465 354
+ 217 44 2 1 7 4
+ 30 172 277 31
+ 218 44 2 1 7 4
+ 172 354 437 277
+ 219 44 2 1 7 4
+ 354 465 528 437
+ 225 44 2 1 7 4
+ 31 277 183 32
+ 226 44 2 1 7 4
+ 277 437 362 183
+ 227 44 2 1 7 4
+ 437 528 475 362
+ 233 44 2 1 7 4
+ 32 183 184 33
+ 234 44 2 1 7 4
+ 183 362 363 184
+ 235 44 2 1 7 4
+ 362 475 476 363
+ 241 44 2 1 7 4
+ 33 184 187 34
+ 242 44 2 1 7 4
+ 184 363 365 187
+ 243 44 2 1 7 4
+ 363 476 478 365
+ 249 44 2 1 7 4
+ 34 187 190 35
+ 250 44 2 1 7 4
+ 187 365 367 190
+ 251 44 2 1 7 4
+ 365 478 485 367
+ 257 44 2 1 7 4
+ 36 216 215 37
+ 258 44 2 1 7 4
+ 216 376 393 215
+ 259 44 2 1 7 4
+ 376 495 504 393
+ 265 44 2 1 7 4
+ 37 215 224 38
+ 266 44 2 1 7 4
+ 215 393 399 224
+ 267 44 2 1 7 4
+ 393 504 512 399
+ 273 44 2 1 7 4
+ 38 224 223 39
+ 274 44 2 1 7 4
+ 224 399 404 223
+ 275 44 2 1 7 4
+ 399 512 520 404
+ 281 44 2 1 7 4
+ 39 223 233 40
+ 282 44 2 1 7 4
+ 223 404 409 233
+ 283 44 2 1 7 4
+ 404 520 526 409
+ 289 44 2 1 7 4
+ 40 233 266 41
+ 290 44 2 1 7 4
+ 233 409 446 266
+ 291 44 2 1 7 4
+ 409 526 570 446
+ 297 44 2 1 7 4
+ 41 266 239 42
+ 298 44 2 1 7 4
+ 266 446 418 239
+ 299 44 2 1 7 4
+ 446 570 540 418
+ 305 44 2 1 7 4
+ 42 239 238 26
+ 306 44 2 1 7 4
+ 239 418 417 238
+ 307 44 2 1 7 4
+ 418 540 541 417
+ 313 44 2 1 7 4
+ 2 164 173 29
+ 314 44 2 1 7 4
+ 164 344 350 173
+ 315 44 2 1 7 4
+ 344 453 459 350
+ 321 44 2 1 7 4
+ 4 169 277 31
+ 322 44 2 1 7 4
+ 169 353 437 277
+ 323 44 2 1 7 4
+ 353 463 528 437
+ 329 44 2 1 7 4
+ 7 186 187 34
+ 330 44 2 1 7 4
+ 186 361 365 187
+ 331 44 2 1 7 4
+ 361 473 478 365
+ 337 44 2 1 7 4
+ 36 216 206 12
+ 338 44 2 1 7 4
+ 216 376 380 206
+ 339 44 2 1 7 4
+ 376 495 499 380
+ 345 44 2 1 7 4
+ 38 224 217 14
+ 346 44 2 1 7 4
+ 224 399 395 217
+ 347 44 2 1 7 4
+ 399 512 510 395
+ 353 44 2 1 7 4
+ 40 233 225 16
+ 354 44 2 1 7 4
+ 233 409 405 225
+ 355 44 2 1 7 4
+ 409 526 522 405
+ 361 44 2 1 7 4
+ 35 190 216 36
+ 362 44 2 1 7 4
+ 190 367 376 216
+ 363 44 2 1 7 4
+ 367 485 495 376
+ 369 44 2 1 7 4
+ 1 167 166 53
+ 370 44 2 1 7 4
+ 167 346 347 166
+ 371 44 2 1 7 4
+ 346 455 456 347
+ 377 44 2 1 7 4
+ 53 166 165 54
+ 378 44 2 1 7 4
+ 166 347 348 165
+ 379 44 2 1 7 4
+ 347 456 457 348
+ 385 44 2 1 7 4
+ 54 165 177 55
+ 386 44 2 1 7 4
+ 165 348 357 177
+ 387 44 2 1 7 4
+ 348 457 467 357
+ 393 44 2 1 7 4
+ 55 177 178 56
+ 394 44 2 1 7 4
+ 177 357 359 178
+ 395 44 2 1 7 4
+ 357 467 471 359
+ 401 44 2 1 7 4
+ 56 178 179 57
+ 402 44 2 1 7 4
+ 178 359 360 179
+ 403 44 2 1 7 4
+ 359 471 472 360
+ 409 44 2 1 7 4
+ 57 179 200 58
+ 410 44 2 1 7 4
+ 179 360 369 200
+ 411 44 2 1 7 4
+ 360 472 484 369
+ 417 44 2 1 7 4
+ 58 200 205 59
+ 418 44 2 1 7 4
+ 200 369 377 205
+ 419 44 2 1 7 4
+ 369 484 491 377
+ 425 44 2 1 7 4
+ 59 205 208 60
+ 426 44 2 1 7 4
+ 205 377 382 208
+ 427 44 2 1 7 4
+ 377 491 498 382
+ 433 44 2 1 7 4
+ 60 208 213 61
+ 434 44 2 1 7 4
+ 208 382 392 213
+ 435 44 2 1 7 4
+ 382 498 507 392
+ 441 44 2 1 7 4
+ 61 213 214 62
+ 442 44 2 1 7 4
+ 213 392 396 214
+ 443 44 2 1 7 4
+ 392 507 516 396
+ 449 44 2 1 7 4
+ 62 214 219 63
+ 450 44 2 1 7 4
+ 214 396 400 219
+ 451 44 2 1 7 4
+ 396 516 517 400
+ 457 44 2 1 7 4
+ 63 219 220 64
+ 458 44 2 1 7 4
+ 219 400 402 220
+ 459 44 2 1 7 4
+ 400 517 521 402
+ 465 44 2 1 7 4
+ 64 220 229 65
+ 466 44 2 1 7 4
+ 220 402 406 229
+ 467 44 2 1 7 4
+ 402 521 524 406
+ 473 44 2 1 7 4
+ 65 229 230 66
+ 474 44 2 1 7 4
+ 229 406 412 230
+ 475 44 2 1 7 4
+ 406 524 529 412
+ 481 44 2 1 7 4
+ 66 230 234 67
+ 482 44 2 1 7 4
+ 230 412 414 234
+ 483 44 2 1 7 4
+ 412 529 538 414
+ 489 44 2 1 7 4
+ 67 234 235 68
+ 490 44 2 1 7 4
+ 234 414 415 235
+ 491 44 2 1 7 4
+ 414 538 542 415
+ 497 44 2 1 7 4
+ 68 235 236 69
+ 498 44 2 1 7 4
+ 235 415 416 236
+ 499 44 2 1 7 4
+ 415 542 544 416
+ 505 44 2 1 7 4
+ 69 236 237 70
+ 506 44 2 1 7 4
+ 236 416 419 237
+ 507 44 2 1 7 4
+ 416 544 548 419
+ 513 44 2 1 7 4
+ 71 246 247 72
+ 514 44 2 1 7 4
+ 246 427 428 247
+ 515 44 2 1 7 4
+ 427 556 561 428
+ 521 44 2 1 7 4
+ 72 247 250 73
+ 522 44 2 1 7 4
+ 247 428 431 250
+ 523 44 2 1 7 4
+ 428 561 563 431
+ 529 44 2 1 7 4
+ 73 250 251 74
+ 530 44 2 1 7 4
+ 250 431 434 251
+ 531 44 2 1 7 4
+ 431 563 565 434
+ 537 44 2 1 7 4
+ 74 251 252 75
+ 538 44 2 1 7 4
+ 251 434 435 252
+ 539 44 2 1 7 4
+ 434 565 566 435
+ 545 44 2 1 7 4
+ 75 252 253 76
+ 546 44 2 1 7 4
+ 252 435 433 253
+ 547 44 2 1 7 4
+ 435 566 564 433
+ 553 44 2 1 7 4
+ 76 253 254 77
+ 554 44 2 1 7 4
+ 253 433 432 254
+ 555 44 2 1 7 4
+ 433 564 562 432
+ 561 44 2 1 7 4
+ 77 254 255 78
+ 562 44 2 1 7 4
+ 254 432 429 255
+ 563 44 2 1 7 4
+ 432 562 555 429
+ 569 44 2 1 7 4
+ 78 255 237 70
+ 570 44 2 1 7 4
+ 255 429 419 237
+ 571 44 2 1 7 4
+ 429 555 548 419
+ 577 44 2 1 7 4
+ 27 174 175 79
+ 578 44 2 1 7 4
+ 174 349 352 175
+ 579 44 2 1 7 4
+ 349 460 461 352
+ 585 44 2 1 7 4
+ 79 175 176 80
+ 586 44 2 1 7 4
+ 175 352 358 176
+ 587 44 2 1 7 4
+ 352 461 470 358
+ 593 44 2 1 7 4
+ 80 176 289 81
+ 594 44 2 1 7 4
+ 176 358 439 289
+ 595 44 2 1 7 4
+ 358 470 534 439
+ 601 44 2 1 7 4
+ 81 289 196 82
+ 602 44 2 1 7 4
+ 289 439 371 196
+ 603 44 2 1 7 4
+ 439 534 486 371
+ 609 44 2 1 7 4
+ 82 196 201 83
+ 610 44 2 1 7 4
+ 196 371 373 201
+ 611 44 2 1 7 4
+ 371 486 488 373
+ 617 44 2 1 7 4
+ 83 201 207 84
+ 618 44 2 1 7 4
+ 201 373 379 207
+ 619 44 2 1 7 4
+ 373 488 493 379
+ 625 44 2 1 7 4
+ 84 207 212 85
+ 626 44 2 1 7 4
+ 207 379 388 212
+ 627 44 2 1 7 4
+ 379 493 503 388
+ 633 44 2 1 7 4
+ 86 222 221 87
+ 634 44 2 1 7 4
+ 222 397 403 221
+ 635 44 2 1 7 4
+ 397 514 519 403
+ 641 44 2 1 7 4
+ 87 221 232 88
+ 642 44 2 1 7 4
+ 221 403 407 232
+ 643 44 2 1 7 4
+ 403 519 525 407
+ 649 44 2 1 7 4
+ 88 232 231 89
+ 650 44 2 1 7 4
+ 232 407 413 231
+ 651 44 2 1 7 4
+ 407 525 532 413
+ 657 44 2 1 7 4
+ 89 231 259 90
+ 658 44 2 1 7 4
+ 231 413 420 259
+ 659 44 2 1 7 4
+ 413 532 539 420
+ 665 44 2 1 7 4
+ 90 259 267 91
+ 666 44 2 1 7 4
+ 259 420 447 267
+ 667 44 2 1 7 4
+ 420 539 583 447
+ 673 44 2 1 7 4
+ 91 267 256 92
+ 674 44 2 1 7 4
+ 267 447 430 256
+ 675 44 2 1 7 4
+ 447 583 554 430
+ 681 44 2 1 7 4
+ 92 256 255 78
+ 682 44 2 1 7 4
+ 256 430 429 255
+ 683 44 2 1 7 4
+ 430 554 555 429
+ 689 44 2 1 7 4
+ 53 166 175 79
+ 690 44 2 1 7 4
+ 166 347 352 175
+ 691 44 2 1 7 4
+ 347 456 461 352
+ 697 44 2 1 7 4
+ 55 177 289 81
+ 698 44 2 1 7 4
+ 177 357 439 289
+ 699 44 2 1 7 4
+ 357 467 534 439
+ 705 44 2 1 7 4
+ 58 200 207 84
+ 706 44 2 1 7 4
+ 200 369 379 207
+ 707 44 2 1 7 4
+ 369 484 493 379
+ 713 44 2 1 7 4
+ 86 222 219 63
+ 714 44 2 1 7 4
+ 222 397 400 219
+ 715 44 2 1 7 4
+ 397 514 517 400
+ 721 44 2 1 7 4
+ 88 232 229 65
+ 722 44 2 1 7 4
+ 232 407 406 229
+ 723 44 2 1 7 4
+ 407 525 524 406
+ 729 44 2 1 7 4
+ 90 259 234 67
+ 730 44 2 1 7 4
+ 259 420 414 234
+ 731 44 2 1 7 4
+ 420 539 538 414
+ 737 44 2 1 7 4
+ 85 212 222 86
+ 738 44 2 1 7 4
+ 212 388 397 222
+ 739 44 2 1 7 4
+ 388 503 514 397
+ 745 44 2 1 7 4
+ 1 167 174 27
+ 746 44 2 1 7 4
+ 167 346 349 174
+ 747 44 2 1 7 4
+ 346 455 460 349
+ 753 44 2 1 7 4
+ 27 174 168 48
+ 754 44 2 1 7 4
+ 174 349 351 168
+ 755 44 2 1 7 4
+ 349 460 462 351
+ 761 44 2 1 7 4
+ 48 168 278 49
+ 762 44 2 1 7 4
+ 168 351 436 278
+ 763 44 2 1 7 4
+ 351 462 530 436
+ 769 44 2 1 7 4
+ 49 278 182 101
+ 770 44 2 1 7 4
+ 278 436 364 182
+ 771 44 2 1 7 4
+ 436 530 480 364
+ 777 44 2 1 7 4
+ 101 182 261 102
+ 778 44 2 1 7 4
+ 182 364 374 261
+ 779 44 2 1 7 4
+ 364 480 492 374
+ 785 44 2 1 7 4
+ 102 261 210 103
+ 786 44 2 1 7 4
+ 261 374 394 210
+ 787 44 2 1 7 4
+ 374 492 508 394
+ 793 44 2 1 7 4
+ 103 210 263 104
+ 794 44 2 1 7 4
+ 210 394 401 263
+ 795 44 2 1 7 4
+ 394 508 518 401
+ 801 44 2 1 7 4
+ 104 263 265 52
+ 802 44 2 1 7 4
+ 263 401 445 265
+ 803 44 2 1 7 4
+ 401 518 569 445
+ 809 44 2 1 7 4
+ 52 265 339 28
+ 810 44 2 1 7 4
+ 265 445 448 339
+ 811 44 2 1 7 4
+ 445 569 591 448
+ 817 44 2 1 7 4
+ 71 246 339 28
+ 818 44 2 1 7 4
+ 246 427 448 339
+ 819 44 2 1 7 4
+ 427 556 591 448
+ 825 44 2 1 7 4
+ 71 246 245 20
+ 826 44 2 1 7 4
+ 246 427 426 245
+ 827 44 2 1 7 4
+ 427 556 558 426
+ 838 11 2 1 7 2
+ 0 0 0
+ 450 436
+ 839 11 2 1 7 2
+ 0 0 0
+ 305 278
+ 845 11 2 1 7 2
+ 0 0 0
+ 449 450
+ 846 11 2 1 7 2
+ 0 0 0
+ 304 305
+ 852 11 2 1 7 2
+ 0 0 0
+ 437 449
+ 853 11 2 1 7 2
+ 0 0 0
+ 277 304
+ 859 11 2 1 7 2
+ 0 0 0
+ 350 349
+ 860 11 2 1 7 2
+ 0 0 0
+ 173 174
+ 861 11 2 1 7 2
+ 0 0 0
+ 29 27
+ 867 11 2 1 7 2
+ 0 0 0
+ 346 344
+ 868 11 2 1 7 2
+ 0 0 0
+ 167 164
+ 869 11 2 1 7 2
+ 0 0 0
+ 1 2
+ 875 11 2 1 7 2
+ 0 0 0
+ 477 452
+ 876 11 2 1 7 2
+ 0 0 0
+ 316 302
+ 882 11 2 1 7 2
+ 0 0 0
+ 483 477
+ 883 11 2 1 7 2
+ 0 0 0
+ 326 316
+ 889 11 2 1 7 2
+ 0 0 0
+ 482 483
+ 890 11 2 1 7 2
+ 0 0 0
+ 325 326
+ 896 11 2 1 7 2
+ 0 0 0
+ 481 482
+ 897 11 2 1 7 2
+ 0 0 0
+ 315 325
+ 903 11 2 1 7 2
+ 0 0 0
+ 452 481
+ 904 11 2 1 7 2
+ 0 0 0
+ 302 315
+ 910 11 2 1 7 2
+ 0 0 0
+ 446 502
+ 911 11 2 1 7 2
+ 0 0 0
+ 266 297
+ 917 11 2 1 7 2
+ 0 0 0
+ 502 536
+ 918 11 2 1 7 2
+ 0 0 0
+ 297 318
+ 924 11 2 1 7 2
+ 0 0 0
+ 536 545
+ 925 11 2 1 7 2
+ 0 0 0
+ 318 327
+ 931 11 2 1 7 2
+ 0 0 0
+ 545 546
+ 932 11 2 1 7 2
+ 0 0 0
+ 327 328
+ 938 11 2 1 7 2
+ 0 0 0
+ 546 543
+ 939 11 2 1 7 2
+ 0 0 0
+ 328 317
+ 945 11 2 1 7 2
+ 0 0 0
+ 543 506
+ 946 11 2 1 7 2
+ 0 0 0
+ 317 294
+ 952 11 2 1 7 2
+ 0 0 0
+ 506 445
+ 953 11 2 1 7 2
+ 0 0 0
+ 294 265
+ 954 11 2 1 7 2
+ 0 0 0
+ 216 268
+ 955 11 2 1 7 2
+ 0 0 0
+ 268 292
+ 956 11 2 1 7 2
+ 0 0 0
+ 292 311
+ 957 11 2 1 7 2
+ 0 0 0
+ 311 313
+ 958 11 2 1 7 2
+ 0 0 0
+ 313 314
+ 959 11 2 1 7 2
+ 0 0 0
+ 314 306
+ 960 11 2 1 7 2
+ 0 0 0
+ 306 269
+ 961 11 2 1 7 2
+ 0 0 0
+ 224 295
+ 962 11 2 1 7 2
+ 0 0 0
+ 295 383
+ 963 11 2 1 7 2
+ 0 0 0
+ 383 443
+ 964 11 2 1 7 2
+ 0 0 0
+ 443 444
+ 965 11 2 1 7 2
+ 0 0 0
+ 444 372
+ 966 11 2 1 7 2
+ 0 0 0
+ 372 290
+ 967 11 2 1 7 2
+ 0 0 0
+ 233 293
+ 968 11 2 1 7 2
+ 0 0 0
+ 293 381
+ 969 11 2 1 7 2
+ 0 0 0
+ 381 441
+ 970 11 2 1 7 2
+ 0 0 0
+ 441 442
+ 971 11 2 1 7 2
+ 0 0 0
+ 442 375
+ 972 11 2 1 7 2
+ 0 0 0
+ 375 291
+ 978 11 2 1 7 2
+ 0 0 0
+ 451 458
+ 979 11 2 1 7 2
+ 0 0 0
+ 312 319
+ 985 11 2 1 7 2
+ 0 0 0
+ 439 451
+ 986 11 2 1 7 2
+ 0 0 0
+ 289 312
+ 992 11 2 1 7 2
+ 0 0 0
+ 352 349
+ 993 11 2 1 7 2
+ 0 0 0
+ 175 174
+ 994 11 2 1 7 2
+ 0 0 0
+ 79 27
+ 1000 11 2 1 7 2
+ 0 0 0
+ 346 347
+ 1001 11 2 1 7 2
+ 0 0 0
+ 167 166
+ 1002 11 2 1 7 2
+ 0 0 0
+ 1 53
+ 1008 11 2 1 7 2
+ 0 0 0
+ 496 468
+ 1009 11 2 1 7 2
+ 0 0 0
+ 323 307
+ 1015 11 2 1 7 2
+ 0 0 0
+ 501 496
+ 1016 11 2 1 7 2
+ 0 0 0
+ 332 323
+ 1022 11 2 1 7 2
+ 0 0 0
+ 500 501
+ 1023 11 2 1 7 2
+ 0 0 0
+ 331 332
+ 1029 11 2 1 7 2
+ 0 0 0
+ 494 500
+ 1030 11 2 1 7 2
+ 0 0 0
+ 322 331
+ 1036 11 2 1 7 2
+ 0 0 0
+ 468 494
+ 1037 11 2 1 7 2
+ 0 0 0
+ 307 322
+ 1043 11 2 1 7 2
+ 0 0 0
+ 447 511
+ 1044 11 2 1 7 2
+ 0 0 0
+ 267 303
+ 1050 11 2 1 7 2
+ 0 0 0
+ 511 551
+ 1051 11 2 1 7 2
+ 0 0 0
+ 303 324
+ 1057 11 2 1 7 2
+ 0 0 0
+ 551 552
+ 1058 11 2 1 7 2
+ 0 0 0
+ 324 329
+ 1064 11 2 1 7 2
+ 0 0 0
+ 552 553
+ 1065 11 2 1 7 2
+ 0 0 0
+ 329 330
+ 1071 11 2 1 7 2
+ 0 0 0
+ 553 549
+ 1072 11 2 1 7 2
+ 0 0 0
+ 330 321
+ 1073 11 2 1 7 2
+ 0 0 0
+ 222 270
+ 1074 11 2 1 7 2
+ 0 0 0
+ 270 300
+ 1075 11 2 1 7 2
+ 0 0 0
+ 300 309
+ 1076 11 2 1 7 2
+ 0 0 0
+ 309 310
+ 1077 11 2 1 7 2
+ 0 0 0
+ 310 308
+ 1078 11 2 1 7 2
+ 0 0 0
+ 308 271
+ 1079 11 2 1 7 2
+ 0 0 0
+ 271 260
+ 1080 11 2 1 7 2
+ 0 0 0
+ 232 301
+ 1081 11 2 1 7 2
+ 0 0 0
+ 301 386
+ 1082 11 2 1 7 2
+ 0 0 0
+ 386 387
+ 1083 11 2 1 7 2
+ 0 0 0
+ 387 385
+ 1084 11 2 1 7 2
+ 0 0 0
+ 385 296
+ 1085 11 2 1 7 2
+ 0 0 0
+ 296 262
+ 1086 11 2 1 7 2
+ 0 0 0
+ 259 299
+ 1087 11 2 1 7 2
+ 0 0 0
+ 299 390
+ 1088 11 2 1 7 2
+ 0 0 0
+ 390 391
+ 1089 11 2 1 7 2
+ 0 0 0
+ 391 389
+ 1090 11 2 1 7 2
+ 0 0 0
+ 389 298
+ 1091 11 2 1 7 2
+ 0 0 0
+ 298 264
+ 1097 11 2 1 7 2
+ 0 0 0
+ 346 349
+ 1098 11 2 1 7 2
+ 0 0 0
+ 167 174
+ 1099 11 2 1 7 2
+ 0 0 0
+ 1 27
+ 1100 11 2 1 7 2
+ 0 0 0
+ 291 263
+ 1101 11 2 1 7 2
+ 0 0 0
+ 290 261
+ 1102 11 2 1 7 2
+ 0 0 0
+ 269 278
+ 1103 11 2 1 7 2
+ 0 0 0
+ 263 264
+ 1104 11 2 1 7 2
+ 0 0 0
+ 261 262
+ 1105 11 2 1 7 2
+ 0 0 0
+ 278 260
+ 1106 11 2 1 7 2
+ 0 0 0
+ 319 340
+ 1107 11 2 1 7 2
+ 0 0 0
+ 340 342
+ 1108 11 2 1 7 2
+ 0 0 0
+ 342 343
+ 1109 11 2 1 7 2
+ 0 0 0
+ 343 341
+ 1110 11 2 1 7 2
+ 0 0 0
+ 341 320
+ 1111 11 2 1 7 2
+ 0 0 0
+ 320 321
+ 1112 11 2 1 7 2
+ 0 0 0
+ 458 474
+ 1118 11 2 1 7 2
+ 0 0 0
+ 474 489
+ 1124 11 2 1 7 2
+ 0 0 0
+ 489 509
+ 1130 11 2 1 7 2
+ 0 0 0
+ 509 513
+ 1136 11 2 1 7 2
+ 0 0 0
+ 513 523
+ 1142 11 2 1 7 2
+ 0 0 0
+ 523 549
+ 1153 11 2 1 7 2
+ 0 0 0
+ 448 591
+ 1154 11 2 1 7 2
+ 0 0 0
+ 339 448
+ 1155 11 2 1 7 2
+ 0 0 0
+ 28 339
+ 1156 11 2 1 7 2
+ 0 0 0
+ 28 118
+ 1157 11 2 1 7 2
+ 0 0 0
+ 118 152
+ 1158 11 2 1 7 2
+ 0 0 0
+ 152 153
+ 1159 11 2 1 7 2
+ 0 0 0
+ 153 154
+ 1160 11 2 1 7 2
+ 0 0 0
+ 154 155
+ 1161 11 2 1 7 2
+ 0 0 0
+ 28 157
+ 1162 11 2 1 7 2
+ 0 0 0
+ 157 158
+ 1163 11 2 1 7 2
+ 0 0 0
+ 158 159
+ 1164 11 2 1 7 2
+ 0 0 0
+ 159 160
+ 1165 11 2 1 7 2
+ 0 0 0
+ 155 156
+ 1166 11 2 1 7 2
+ 0 0 0
+ 156 92
+ 1167 11 2 1 7 2
+ 0 0 0
+ 160 161
+ 1168 11 2 1 7 2
+ 0 0 0
+ 161 162
+ 1169 11 2 1 7 2
+ 0 0 0
+ 162 42
+ 1175 44 2 1 7 4
+ 438 351 349 350
+ 1176 44 2 1 7 4
+ 180 168 174 173
+ 1177 44 2 1 7 4
+ 50 48 27 29
+ 1183 44 2 1 7 4
+ 450 436 351 438
+ 1184 44 2 1 7 4
+ 305 278 168 180
+ 1190 44 2 1 7 4
+ 449 438 350 354
+ 1191 44 2 1 7 4
+ 304 180 173 172
+ 1197 44 2 1 7 4
+ 354 350 344 345
+ 1198 44 2 1 7 4
+ 172 173 164 163
+ 1199 44 2 1 7 4
+ 30 29 2 3
+ 1205 44 2 1 7 4
+ 437 354 345 353
+ 1206 44 2 1 7 4
+ 277 172 163 169
+ 1207 44 2 1 7 4
+ 31 30 3 4
+ 1213 44 2 1 7 4
+ 362 437 353 355
+ 1214 44 2 1 7 4
+ 183 277 169 170
+ 1215 44 2 1 7 4
+ 32 31 4 5
+ 1221 44 2 1 7 4
+ 363 362 355 356
+ 1222 44 2 1 7 4
+ 184 183 170 171
+ 1223 44 2 1 7 4
+ 33 32 5 6
+ 1229 44 2 1 7 4
+ 365 363 356 361
+ 1230 44 2 1 7 4
+ 187 184 171 186
+ 1236 44 2 1 7 4
+ 452 365 361 366
+ 1237 44 2 1 7 4
+ 302 187 186 188
+ 1238 44 2 1 7 4
+ 43 34 7 8
+ 1244 44 2 1 7 4
+ 481 452 366 368
+ 1245 44 2 1 7 4
+ 315 302 188 191
+ 1246 44 2 1 7 4
+ 47 43 8 9
+ 1252 44 2 1 7 4
+ 477 367 365 452
+ 1253 44 2 1 7 4
+ 316 190 187 302
+ 1254 44 2 1 7 4
+ 46 35 34 43
+ 1260 44 2 1 7 4
+ 483 376 367 477
+ 1261 44 2 1 7 4
+ 326 216 190 316
+ 1262 44 2 1 7 4
+ 45 36 35 46
+ 1268 44 2 1 7 4
+ 378 482 481 370
+ 1269 44 2 1 7 4
+ 195 325 315 194
+ 1270 44 2 1 7 4
+ 11 44 47 10
+ 1276 44 2 1 7 4
+ 380 376 483 482
+ 1277 44 2 1 7 4
+ 206 216 326 325
+ 1278 44 2 1 7 4
+ 12 36 45 44
+ 1284 44 2 1 7 4
+ 384 393 376 380
+ 1285 44 2 1 7 4
+ 209 215 216 206
+ 1286 44 2 1 7 4
+ 13 37 36 12
+ 1292 44 2 1 7 4
+ 395 399 393 384
+ 1293 44 2 1 7 4
+ 217 224 215 209
+ 1294 44 2 1 7 4
+ 14 38 37 13
+ 1300 44 2 1 7 4
+ 398 404 399 395
+ 1301 44 2 1 7 4
+ 218 223 224 217
+ 1302 44 2 1 7 4
+ 15 39 38 14
+ 1308 44 2 1 7 4
+ 405 409 404 398
+ 1309 44 2 1 7 4
+ 225 233 223 218
+ 1310 44 2 1 7 4
+ 16 40 39 15
+ 1316 44 2 1 7 4
+ 408 446 409 405
+ 1317 44 2 1 7 4
+ 226 266 233 225
+ 1318 44 2 1 7 4
+ 17 41 40 16
+ 1324 44 2 1 7 4
+ 410 418 446 408
+ 1325 44 2 1 7 4
+ 227 239 266 226
+ 1326 44 2 1 7 4
+ 18 42 41 17
+ 1332 44 2 1 7 4
+ 411 417 418 410
+ 1333 44 2 1 7 4
+ 228 238 239 227
+ 1334 44 2 1 7 4
+ 19 26 42 18
+ 1340 44 2 1 7 4
+ 417 421 502 418
+ 1341 44 2 1 7 4
+ 238 240 297 239
+ 1342 44 2 1 7 4
+ 26 25 162 42
+ 1348 44 2 1 7 4
+ 421 422 536 502
+ 1349 44 2 1 7 4
+ 240 241 318 297
+ 1350 44 2 1 7 4
+ 25 24 161 162
+ 1356 44 2 1 7 4
+ 422 423 545 536
+ 1357 44 2 1 7 4
+ 241 242 327 318
+ 1358 44 2 1 7 4
+ 24 23 160 161
+ 1364 44 2 1 7 4
+ 423 424 546 545
+ 1365 44 2 1 7 4
+ 242 243 328 327
+ 1366 44 2 1 7 4
+ 23 22 159 160
+ 1372 44 2 1 7 4
+ 424 425 543 546
+ 1373 44 2 1 7 4
+ 243 244 317 328
+ 1374 44 2 1 7 4
+ 22 21 158 159
+ 1380 44 2 1 7 4
+ 425 426 506 543
+ 1381 44 2 1 7 4
+ 244 245 294 317
+ 1382 44 2 1 7 4
+ 21 20 157 158
+ 1383 44 2 1 7 4
+ 44 45 46 47
+ 1384 44 2 1 7 4
+ 110 113 33 34
+ 1385 44 2 1 7 4
+ 113 112 32 33
+ 1386 44 2 1 7 4
+ 112 111 31 32
+ 1387 44 2 1 7 4
+ 111 51 30 31
+ 1388 44 2 1 7 4
+ 51 50 29 30
+ 1389 44 2 1 7 4
+ 119 123 110 35
+ 1390 44 2 1 7 4
+ 123 135 113 110
+ 1391 44 2 1 7 4
+ 135 150 112 113
+ 1392 44 2 1 7 4
+ 150 151 111 112
+ 1393 44 2 1 7 4
+ 151 133 51 111
+ 1394 44 2 1 7 4
+ 133 120 50 51
+ 1395 44 2 1 7 4
+ 120 49 48 50
+ 1396 44 2 1 7 4
+ 37 131 119 36
+ 1397 44 2 1 7 4
+ 131 211 135 123
+ 1398 44 2 1 7 4
+ 211 258 150 135
+ 1399 44 2 1 7 4
+ 258 257 151 150
+ 1400 44 2 1 7 4
+ 257 181 133 151
+ 1401 44 2 1 7 4
+ 181 124 120 133
+ 1402 44 2 1 7 4
+ 38 143 131 37
+ 1403 44 2 1 7 4
+ 143 279 211 131
+ 1404 44 2 1 7 4
+ 279 337 258 211
+ 1405 44 2 1 7 4
+ 337 338 257 258
+ 1406 44 2 1 7 4
+ 338 272 181 257
+ 1407 44 2 1 7 4
+ 272 136 124 181
+ 1408 44 2 1 7 4
+ 39 142 143 38
+ 1409 44 2 1 7 4
+ 142 276 279 143
+ 1410 44 2 1 7 4
+ 276 335 337 279
+ 1411 44 2 1 7 4
+ 335 336 338 337
+ 1412 44 2 1 7 4
+ 336 273 272 338
+ 1413 44 2 1 7 4
+ 273 137 136 272
+ 1414 44 2 1 7 4
+ 40 141 142 39
+ 1415 44 2 1 7 4
+ 141 275 276 142
+ 1416 44 2 1 7 4
+ 275 333 335 276
+ 1417 44 2 1 7 4
+ 333 334 336 335
+ 1418 44 2 1 7 4
+ 334 274 273 336
+ 1419 44 2 1 7 4
+ 274 138 137 273
+ 1420 44 2 1 7 4
+ 41 125 141 40
+ 1421 44 2 1 7 4
+ 125 189 275 141
+ 1422 44 2 1 7 4
+ 189 248 333 275
+ 1423 44 2 1 7 4
+ 248 249 334 333
+ 1424 44 2 1 7 4
+ 249 192 274 334
+ 1425 44 2 1 7 4
+ 192 126 138 274
+ 1426 44 2 1 7 4
+ 42 162 125 41
+ 1427 44 2 1 7 4
+ 162 161 189 125
+ 1428 44 2 1 7 4
+ 161 160 248 189
+ 1429 44 2 1 7 4
+ 160 159 249 248
+ 1430 44 2 1 7 4
+ 159 158 192 249
+ 1431 44 2 1 7 4
+ 158 157 126 192
+ 1432 44 2 1 7 4
+ 268 119 123 292
+ 1433 44 2 1 7 4
+ 292 123 135 311
+ 1434 44 2 1 7 4
+ 311 135 150 313
+ 1435 44 2 1 7 4
+ 313 150 151 314
+ 1436 44 2 1 7 4
+ 314 151 133 306
+ 1437 44 2 1 7 4
+ 306 133 120 269
+ 1438 44 2 1 7 4
+ 216 36 119 268
+ 1439 44 2 1 7 4
+ 224 38 143 295
+ 1440 44 2 1 7 4
+ 295 143 279 383
+ 1441 44 2 1 7 4
+ 383 279 337 443
+ 1442 44 2 1 7 4
+ 443 337 338 444
+ 1443 44 2 1 7 4
+ 444 338 272 372
+ 1444 44 2 1 7 4
+ 372 272 136 290
+ 1445 44 2 1 7 4
+ 233 40 141 293
+ 1446 44 2 1 7 4
+ 293 141 275 381
+ 1447 44 2 1 7 4
+ 381 275 333 441
+ 1448 44 2 1 7 4
+ 441 333 334 442
+ 1449 44 2 1 7 4
+ 442 334 274 375
+ 1450 44 2 1 7 4
+ 375 274 138 291
+ 1456 44 2 1 7 4
+ 440 351 349 352
+ 1457 44 2 1 7 4
+ 185 168 174 175
+ 1458 44 2 1 7 4
+ 98 48 27 79
+ 1464 44 2 1 7 4
+ 458 436 351 440
+ 1465 44 2 1 7 4
+ 319 278 168 185
+ 1471 44 2 1 7 4
+ 451 440 352 358
+ 1472 44 2 1 7 4
+ 312 185 175 176
+ 1478 44 2 1 7 4
+ 358 352 347 348
+ 1479 44 2 1 7 4
+ 176 175 166 165
+ 1480 44 2 1 7 4
+ 80 79 53 54
+ 1486 44 2 1 7 4
+ 439 358 348 357
+ 1487 44 2 1 7 4
+ 289 176 165 177
+ 1488 44 2 1 7 4
+ 81 80 54 55
+ 1494 44 2 1 7 4
+ 371 439 357 359
+ 1495 44 2 1 7 4
+ 196 289 177 178
+ 1496 44 2 1 7 4
+ 82 81 55 56
+ 1502 44 2 1 7 4
+ 373 371 359 360
+ 1503 44 2 1 7 4
+ 201 196 178 179
+ 1504 44 2 1 7 4
+ 83 82 56 57
+ 1510 44 2 1 7 4
+ 379 373 360 369
+ 1511 44 2 1 7 4
+ 207 201 179 200
+ 1512 44 2 1 7 4
+ 84 83 57 58
+ 1518 44 2 1 7 4
+ 468 379 369 377
+ 1519 44 2 1 7 4
+ 307 207 200 205
+ 1520 44 2 1 7 4
+ 93 84 58 59
+ 1526 44 2 1 7 4
+ 494 468 377 382
+ 1527 44 2 1 7 4
+ 322 307 205 208
+ 1528 44 2 1 7 4
+ 97 93 59 60
+ 1534 44 2 1 7 4
+ 496 388 379 468
+ 1535 44 2 1 7 4
+ 323 212 207 307
+ 1536 44 2 1 7 4
+ 96 85 84 93
+ 1542 44 2 1 7 4
+ 501 397 388 496
+ 1543 44 2 1 7 4
+ 332 222 212 323
+ 1544 44 2 1 7 4
+ 95 86 85 96
+ 1550 44 2 1 7 4
+ 396 500 494 392
+ 1551 44 2 1 7 4
+ 214 331 322 213
+ 1552 44 2 1 7 4
+ 62 94 97 61
+ 1558 44 2 1 7 4
+ 400 397 501 500
+ 1559 44 2 1 7 4
+ 219 222 332 331
+ 1560 44 2 1 7 4
+ 63 86 95 94
+ 1566 44 2 1 7 4
+ 402 403 397 400
+ 1567 44 2 1 7 4
+ 220 221 222 219
+ 1568 44 2 1 7 4
+ 64 87 86 63
+ 1574 44 2 1 7 4
+ 406 407 403 402
+ 1575 44 2 1 7 4
+ 229 232 221 220
+ 1576 44 2 1 7 4
+ 65 88 87 64
+ 1582 44 2 1 7 4
+ 412 413 407 406
+ 1583 44 2 1 7 4
+ 230 231 232 229
+ 1584 44 2 1 7 4
+ 66 89 88 65
+ 1590 44 2 1 7 4
+ 414 420 413 412
+ 1591 44 2 1 7 4
+ 234 259 231 230
+ 1592 44 2 1 7 4
+ 67 90 89 66
+ 1598 44 2 1 7 4
+ 415 447 420 414
+ 1599 44 2 1 7 4
+ 235 267 259 234
+ 1600 44 2 1 7 4
+ 68 91 90 67
+ 1606 44 2 1 7 4
+ 416 430 447 415
+ 1607 44 2 1 7 4
+ 236 256 267 235
+ 1608 44 2 1 7 4
+ 69 92 91 68
+ 1614 44 2 1 7 4
+ 419 429 430 416
+ 1615 44 2 1 7 4
+ 237 255 256 236
+ 1616 44 2 1 7 4
+ 70 78 92 69
+ 1622 44 2 1 7 4
+ 429 432 511 430
+ 1623 44 2 1 7 4
+ 255 254 303 256
+ 1624 44 2 1 7 4
+ 78 77 156 92
+ 1630 44 2 1 7 4
+ 432 433 551 511
+ 1631 44 2 1 7 4
+ 254 253 324 303
+ 1632 44 2 1 7 4
+ 77 76 155 156
+ 1638 44 2 1 7 4
+ 433 435 552 551
+ 1639 44 2 1 7 4
+ 253 252 329 324
+ 1640 44 2 1 7 4
+ 76 75 154 155
+ 1646 44 2 1 7 4
+ 435 434 553 552
+ 1647 44 2 1 7 4
+ 252 251 330 329
+ 1648 44 2 1 7 4
+ 75 74 153 154
+ 1654 44 2 1 7 4
+ 434 431 549 553
+ 1655 44 2 1 7 4
+ 251 250 321 330
+ 1656 44 2 1 7 4
+ 74 73 152 153
+ 1662 44 2 1 7 4
+ 431 428 464 549
+ 1663 44 2 1 7 4
+ 250 247 193 321
+ 1664 44 2 1 7 4
+ 73 72 118 152
+ 1670 44 2 1 7 4
+ 428 427 448 464
+ 1671 44 2 1 7 4
+ 247 246 339 193
+ 1672 44 2 1 7 4
+ 72 71 28 118
+ 1673 44 2 1 7 4
+ 94 95 96 97
+ 1674 44 2 1 7 4
+ 114 117 83 84
+ 1675 44 2 1 7 4
+ 117 116 82 83
+ 1676 44 2 1 7 4
+ 116 115 81 82
+ 1677 44 2 1 7 4
+ 115 100 80 81
+ 1678 44 2 1 7 4
+ 100 98 79 80
+ 1679 44 2 1 7 4
+ 121 129 114 85
+ 1680 44 2 1 7 4
+ 129 139 117 114
+ 1681 44 2 1 7 4
+ 139 140 116 117
+ 1682 44 2 1 7 4
+ 140 134 115 116
+ 1683 44 2 1 7 4
+ 134 122 100 115
+ 1684 44 2 1 7 4
+ 122 99 98 100
+ 1685 44 2 1 7 4
+ 99 49 48 98
+ 1686 44 2 1 7 4
+ 87 132 121 86
+ 1687 44 2 1 7 4
+ 132 199 139 129
+ 1688 44 2 1 7 4
+ 199 198 140 139
+ 1689 44 2 1 7 4
+ 198 197 134 140
+ 1690 44 2 1 7 4
+ 197 127 122 134
+ 1691 44 2 1 7 4
+ 88 149 132 87
+ 1692 44 2 1 7 4
+ 149 287 199 132
+ 1693 44 2 1 7 4
+ 287 288 198 199
+ 1694 44 2 1 7 4
+ 288 280 197 198
+ 1695 44 2 1 7 4
+ 280 144 127 197
+ 1696 44 2 1 7 4
+ 89 148 149 88
+ 1697 44 2 1 7 4
+ 148 283 287 149
+ 1698 44 2 1 7 4
+ 283 284 288 287
+ 1699 44 2 1 7 4
+ 284 281 280 288
+ 1700 44 2 1 7 4
+ 281 145 144 280
+ 1701 44 2 1 7 4
+ 90 147 148 89
+ 1702 44 2 1 7 4
+ 147 285 283 148
+ 1703 44 2 1 7 4
+ 285 286 284 283
+ 1704 44 2 1 7 4
+ 286 282 281 284
+ 1705 44 2 1 7 4
+ 282 146 145 281
+ 1706 44 2 1 7 4
+ 91 128 147 90
+ 1707 44 2 1 7 4
+ 128 202 285 147
+ 1708 44 2 1 7 4
+ 202 203 286 285
+ 1709 44 2 1 7 4
+ 203 204 282 286
+ 1710 44 2 1 7 4
+ 204 130 146 282
+ 1711 44 2 1 7 4
+ 92 156 128 91
+ 1712 44 2 1 7 4
+ 156 155 202 128
+ 1713 44 2 1 7 4
+ 155 154 203 202
+ 1714 44 2 1 7 4
+ 154 153 204 203
+ 1715 44 2 1 7 4
+ 153 152 130 204
+ 1716 44 2 1 7 4
+ 270 121 129 300
+ 1717 44 2 1 7 4
+ 300 129 139 309
+ 1718 44 2 1 7 4
+ 309 139 140 310
+ 1719 44 2 1 7 4
+ 310 140 134 308
+ 1720 44 2 1 7 4
+ 308 134 122 271
+ 1721 44 2 1 7 4
+ 271 122 99 260
+ 1722 44 2 1 7 4
+ 222 86 121 270
+ 1723 44 2 1 7 4
+ 232 88 149 301
+ 1724 44 2 1 7 4
+ 301 149 287 386
+ 1725 44 2 1 7 4
+ 386 287 288 387
+ 1726 44 2 1 7 4
+ 387 288 280 385
+ 1727 44 2 1 7 4
+ 385 280 144 296
+ 1728 44 2 1 7 4
+ 259 90 147 299
+ 1729 44 2 1 7 4
+ 299 147 285 390
+ 1730 44 2 1 7 4
+ 390 285 286 391
+ 1731 44 2 1 7 4
+ 391 286 282 389
+ 1732 44 2 1 7 4
+ 389 282 146 298
+ 1733 44 2 1 7 4
+ 136 102 101 124
+ 1734 44 2 1 7 4
+ 137 103 102 136
+ 1735 44 2 1 7 4
+ 138 104 103 137
+ 1736 44 2 1 7 4
+ 124 101 49 120
+ 1737 44 2 1 7 4
+ 126 52 104 138
+ 1738 44 2 1 7 4
+ 157 28 52 126
+ 1739 44 2 1 7 4
+ 269 120 49 278
+ 1740 44 2 1 7 4
+ 290 136 102 261
+ 1741 44 2 1 7 4
+ 291 138 104 263
+ 1742 44 2 1 7 4
+ 278 49 99 260
+ 1743 44 2 1 7 4
+ 127 105 99 122
+ 1744 44 2 1 7 4
+ 105 101 49 99
+ 1745 44 2 1 7 4
+ 144 106 105 127
+ 1746 44 2 1 7 4
+ 106 102 101 105
+ 1747 44 2 1 7 4
+ 145 107 106 144
+ 1748 44 2 1 7 4
+ 107 103 102 106
+ 1749 44 2 1 7 4
+ 146 108 107 145
+ 1750 44 2 1 7 4
+ 108 104 103 107
+ 1751 44 2 1 7 4
+ 296 144 106 262
+ 1752 44 2 1 7 4
+ 262 106 102 261
+ 1753 44 2 1 7 4
+ 298 146 108 264
+ 1754 44 2 1 7 4
+ 264 108 104 263
+ 1755 44 2 1 7 4
+ 130 109 108 146
+ 1756 44 2 1 7 4
+ 109 52 104 108
+ 1757 44 2 1 7 4
+ 152 118 109 130
+ 1758 44 2 1 7 4
+ 118 28 52 109
+ 1759 44 2 1 7 4
+ 340 182 278 319
+ 1760 44 2 1 7 4
+ 342 261 182 340
+ 1761 44 2 1 7 4
+ 343 210 261 342
+ 1762 44 2 1 7 4
+ 341 263 210 343
+ 1763 44 2 1 7 4
+ 320 265 263 341
+ 1764 44 2 1 7 4
+ 193 339 265 320
+ 1765 44 2 1 7 4
+ 474 364 436 458
+ 1771 44 2 1 7 4
+ 489 374 364 474
+ 1777 44 2 1 7 4
+ 509 394 374 489
+ 1783 44 2 1 7 4
+ 513 401 394 509
+ 1789 44 2 1 7 4
+ 523 445 401 513
+ 1795 44 2 1 7 4
+ 464 448 445 523
+ 1801 44 2 1 7 4
+ 71 20 157 28
+ 1802 44 2 1 7 4
+ 246 245 294 339
+ 1803 44 2 1 7 4
+ 427 426 506 448
+ 1809 44 2 1 7 4
+ 34 33 6 7
+ 1815 41 2 1 7 3
+ 506 448 445
+ 1816 41 2 1 7 3
+ 294 339 265
+ 1822 41 2 1 7 3
+ 449 450 438
+ 1823 41 2 1 7 3
+ 304 305 180
+ 1829 41 2 1 7 3
+ 437 449 354
+ 1830 41 2 1 7 3
+ 277 304 172
+ 1836 41 2 1 7 3
+ 380 482 378
+ 1837 41 2 1 7 3
+ 206 325 195
+ 1838 41 2 1 7 3
+ 12 44 11
+ 1843 41 2 1 7 3
+ 370 481 368
+ 1844 41 2 1 7 3
+ 194 315 191
+ 1845 41 2 1 7 3
+ 10 47 9
+ 1846 41 2 1 7 3
+ 43 46 47
+ 1847 41 2 1 7 3
+ 35 110 34
+ 1849 41 2 1 7 3
+ 36 119 35
+ 1850 41 2 1 7 3
+ 131 123 119
+ 1851 41 2 1 7 3
+ 239 297 266
+ 1852 41 2 1 7 3
+ 418 502 446
+ 1863 41 2 1 7 3
+ 451 458 440
+ 1864 41 2 1 7 3
+ 312 319 185
+ 1870 41 2 1 7 3
+ 439 451 358
+ 1871 41 2 1 7 3
+ 289 312 176
+ 1877 41 2 1 7 3
+ 400 500 396
+ 1878 41 2 1 7 3
+ 219 331 214
+ 1879 41 2 1 7 3
+ 63 94 62
+ 1884 41 2 1 7 3
+ 392 494 382
+ 1885 41 2 1 7 3
+ 213 322 208
+ 1886 41 2 1 7 3
+ 61 97 60
+ 1887 41 2 1 7 3
+ 93 96 97
+ 1888 41 2 1 7 3
+ 85 114 84
+ 1890 41 2 1 7 3
+ 86 121 85
+ 1891 41 2 1 7 3
+ 132 129 121
+ 1892 41 2 1 7 3
+ 256 303 267
+ 1893 41 2 1 7 3
+ 430 511 447
+ 1899 41 2 1 7 3
+ 193 321 320
+ 1900 41 2 1 7 3
+ 464 549 523
+ -1
--- /dev/null
+#include "SALOME_Exception.idl"
+
+module SALOME {
+
+ enum TypeOfDataTransmitted { _DOUBLE_,_INT_ };
+
+ enum TypeOfCommunication { CORBA_ , MPI_ , SOCKET_ };
+
+ typedef sequence<double> vectorOfDouble;
+
+ typedef sequence<long> vectorOfLong;
+
+ interface MultiCommClass {
+ void setProtocol(in TypeOfCommunication typ);
+ };
+
+ interface ServantLifeCycle {
+ void release();
+ };
+
+ interface Sender {
+ TypeOfDataTransmitted getTypeOfDataTransmitted();
+ Sender buildOtherWithProtocol(in TypeOfCommunication type);
+ void release();
+ };
+
+ //No compulsory copy between double and CORBA::Double
+ interface CorbaDoubleNCSender : Sender {
+ unsigned long getSize();
+ vectorOfDouble sendPart(in unsigned long n1,in unsigned long n2);
+ vectorOfDouble send();
+ };
+
+ //Compulsory copy between double and CORBA::Double
+ interface CorbaDoubleCSender : Sender {
+ unsigned long getSize();
+ //unsigned long getSize2();
+ vectorOfDouble sendPart(in unsigned long n1,in unsigned long n2);
+ };
+
+ //No compulsory copy between int and CORBA::Long
+ interface CorbaLongNCSender : Sender {
+ unsigned long getSize();
+ vectorOfLong sendPart(in unsigned long n1,in unsigned long n2);
+ vectorOfLong send();
+ };
+
+ //Compulsory copy between int and CORBA::Long
+ interface CorbaLongCSender : Sender {
+ unsigned long getSize();
+ vectorOfLong sendPart(in unsigned long n1,in unsigned long n2);
+ };
+
+ interface MPISender : Sender {
+ typedef struct Parameter {
+ unsigned long myproc;
+ unsigned long tag1;
+ unsigned long tag2;
+ string service;
+ } param;
+ param getParam();
+ void send();
+ void close(in param p);
+ };
+
+ interface SocketSender : Sender {
+ typedef struct Parameter {
+ unsigned long lstart;
+ unsigned long lend;
+ unsigned long myport;
+ string internet_address;
+ } param;
+ param getParam();
+ void initCom() raises(SALOME_Exception);
+ void acceptCom() raises(SALOME_Exception);
+ void closeCom();
+ void endOfCom() raises(SALOME_Exception);
+ void send();
+ };
+
+};
--- /dev/null
+# make_config.in: template for make_config script
+# make_config is used by check_cas.m4 to generate
+# config.h file in case it cannot be found in OCC
+# and SALOME include paths
+#=================================================
+dnl Process this file with autoconf to produce a configure script.
+
+AC_INIT(salome_adm/unix)
+AC_CONFIG_SRCDIR(salome_adm/unix/config.h.in)
+AC_CONFIG_AUX_DIR(salome_adm/unix/config_files)
+AC_CANONICAL_HOST
+
+AC_CONFIG_HEADERS(./salome_adm/unix/config.h)
+
+AC_ISC_POSIX
+AC_C_BIGENDIAN
+
+dnl Checks for programs.
+AC_PROG_CXX
+AC_PROG_CC_C_O
+
+AC_PROG_AWK
+AC_PROG_INSTALL
+AC_PROG_LN_S
+AC_PROG_YACC
+AC_PROG_MAKE_SET
+
+dnl Replace `main' with a function in -le:
+AC_CHECK_LIB(e, main)
+
+dnl Replace `main' with a function in -links:
+AC_CHECK_LIB(inks, main)
+
+dnl Checks for X window system directories.
+AC_PATH_X
+if test "x$ac_x_includes" = "x"; then
+ X_INCLUDE=""
+else
+ X_INCLUDE="-I$ac_x_includes"
+fi
+if test "x$ac_x_libraries" = "x"; then
+ X_LIBS="-lXt -lX11"
+else
+ X_LIBS="-L$ac_x_libraries -lXt -lX11"
+fi
+
+dnl Checks for header files.
+
+AC_HEADER_STDC
+AC_LANG([C])
+AC_MSG_CHECKING([ for C header files ])
+AC_CHECK_HEADERS(dlfcn.h dl.h ieeefp.h time.h sys/time.h pwd.h)
+AC_CHECK_HEADERS(sys/statvfs.h sys/vfs.h sys/param.h osfcn.h netdb.h)
+AC_CHECK_HEADERS(sys/ioctl.h net/if.h sys/systeminfo.h sys/utsname.h)
+AC_CHECK_HEADERS(sysent.h unistd.h sys/unistd.h sys/socket.h)
+AC_CHECK_HEADERS(ndir.h sys/ndir.h sys/dir.h signal.h sys/signal.h)
+AC_CHECK_HEADERS(sigfpe.h floatingpoint.h sys/machsig.h sys/siginfo.h)
+AC_CHECK_HEADERS(malloc.h strings.h sys/stat.h sys/sem.h sys/ipc.h)
+AC_CHECK_HEADERS(sys/times.h dirent.h getopt.h sys/vnode.h)
+
+
+AC_LANG([C++])
+AC_MSG_CHECKING([ for C++ header files ])
+AC_CHECK_HEADERS(istream ostream istream fstream ios iomanip iostream )
+AC_CHECK_HEADERS(stream.h strstream.h istream.h ostream.h fstream.h stdlib.h ios.h iostream.h)
+AC_CHECK_HEADERS(iomanip.h limits.h values.h float.h)
+AC_CHECK_HEADERS(siginfo.h bits/sigset.h bstring.h sys/types.h sys/select.h)
+AC_CHECK_HEADERS(X11/extensions/transovl.h X11/extensions/readdisplay.h)
+AC_CHECK_HEADERS(X11/extensions/multibuf.h)
+AC_CHECK_HEADERS(sys/filio.h sys/mman.h libc.h)
+
+dnl Checks for library functions.
+AC_TYPE_SIGNAL
+
+AC_OUTPUT()
--- /dev/null
+/* config.h.in. Generated from configure.in by autoheader. */
+
+/* Define to one of `_getb67', `GETB67', `getb67' for Cray-2 and Cray-YMP
+ systems. This function is required for `alloca.c' support on those systems.
+ */
+#undef CRAY_STACKSEG_END
+
+/* Define to 1 if using `alloca.c'. */
+#undef C_ALLOCA
+
+/* define if the compiler allows redefinition of stream input and output */
+#undef DEF_IOS_OK
+
+/* Define to 1 if you have `alloca', as a function or macro. */
+#undef HAVE_ALLOCA
+
+/* Define to 1 if you have <alloca.h> and it should be used (not on Ultrix).
+ */
+#undef HAVE_ALLOCA_H
+
+/* Define to 1 if you have the <bits/sigset.h> header file. */
+#undef HAVE_BITS_SIGSET_H
+
+/* Define to 1 if you have the <bstring.h> header file. */
+#undef HAVE_BSTRING_H
+
+/* Define to 1 if you have the <dirent.h> header file. */
+#undef HAVE_DIRENT_H
+
+/* Define to 1 if you have the <dlfcn.h> header file. */
+#undef HAVE_DLFCN_H
+
+/* Define to 1 if you have the <dl.h> header file. */
+#undef HAVE_DL_H
+
+/* Define to 1 if you have the <DPS/dpsXclient.h> header file. */
+#undef HAVE_DPS_DPSXCLIENT_H
+
+/* Define if we have a function called "finite" in -lm. */
+#undef HAVE_FINITE
+
+/* Define to 1 if you have the <floatingpoint.h> header file. */
+#undef HAVE_FLOATINGPOINT_H
+
+/* Define to 1 if you have the <float.h> header file. */
+#undef HAVE_FLOAT_H
+
+/* Define to 1 if you have the <fstream> header file. */
+#undef HAVE_FSTREAM
+
+/* Define to 1 if you have the <fstream.h> header file. */
+#undef HAVE_FSTREAM_H
+
+/* Define to 1 if you have the `gethostname' function. */
+#undef HAVE_GETHOSTNAME
+
+/* Define to 1 if you have the <getopt.h> header file. */
+#undef HAVE_GETOPT_H
+
+/* Define to 1 if you have the <ieeefp.h> header file. */
+#undef HAVE_IEEEFP_H
+
+/* Define to 1 if you have the <inttypes.h> header file. */
+#undef HAVE_INTTYPES_H
+
+/* Define to 1 if you have the <iomanip> header file. */
+#undef HAVE_IOMANIP
+
+/* Define to 1 if you have the <iomanip.h> header file. */
+#undef HAVE_IOMANIP_H
+
+/* Define to 1 if you have the <ios> header file. */
+#undef HAVE_IOS
+
+/* Define to 1 if you have the <iostream> header file. */
+#undef HAVE_IOSTREAM
+
+/* Define to 1 if you have the <iostream.h> header file. */
+#undef HAVE_IOSTREAM_H
+
+/* Define to 1 if you have the <ios.h> header file. */
+#undef HAVE_IOS_H
+
+/* Define to 1 if you have the <istream> header file. */
+#undef HAVE_ISTREAM
+
+/* Define to 1 if you have the <istream.h> header file. */
+#undef HAVE_ISTREAM_H
+
+/* Define to 1 if you have the <libc.h> header file. */
+#undef HAVE_LIBC_H
+
+/* Define to 1 if you have the `e' library (-le). */
+#undef HAVE_LIBE
+
+/* Define to 1 if you have the `inks' library (-links). */
+#undef HAVE_LIBINKS
+
+/* Define to 1 if you have the <limits.h> header file. */
+#undef HAVE_LIMITS_H
+
+/* Define if we have a function called "mallinfo" in -lmalloc. */
+#undef HAVE_MALLINFO
+
+/* Define to 1 if you have the <malloc.h> header file. */
+#undef HAVE_MALLOC_H
+
+/* Define to 1 if you have the <memory.h> header file. */
+#undef HAVE_MEMORY_H
+
+/* Define to 1 if you have the <ndir.h> header file. */
+#undef HAVE_NDIR_H
+
+/* Define to 1 if you have the <netdb.h> header file. */
+#undef HAVE_NETDB_H
+
+/* Define to 1 if you have the <net/if.h> header file. */
+#undef HAVE_NET_IF_H
+
+/* Define to 1 if you have the <osfcn.h> header file. */
+#undef HAVE_OSFCN_H
+
+/* Define to 1 if you have the <ostream> header file. */
+#undef HAVE_OSTREAM
+
+/* Define to 1 if you have the <ostream.h> header file. */
+#undef HAVE_OSTREAM_H
+
+/* Define to 1 if you have the `putenv' function. */
+#undef HAVE_PUTENV
+
+/* Define to 1 if you have the <pwd.h> header file. */
+#undef HAVE_PWD_H
+
+/* Define to 1 if you have the `regcomp' function. */
+#undef HAVE_REGCOMP
+
+/* Define to 1 if you have the `re_comp' function. */
+#undef HAVE_RE_COMP
+
+/* Define to 1 if you have the <sigfpe.h> header file. */
+#undef HAVE_SIGFPE_H
+
+/* Define to 1 if you have the <siginfo.h> header file. */
+#undef HAVE_SIGINFO_H
+
+/* Define to 1 if you have the <signal.h> header file. */
+#undef HAVE_SIGNAL_H
+
+/* Define to 1 if you have the `statfs' function. */
+#undef HAVE_STATFS
+
+/* Define to 1 if you have the `statvfs' function. */
+#undef HAVE_STATVFS
+
+/* Define to 1 if you have the <stdint.h> header file. */
+#undef HAVE_STDINT_H
+
+/* Define to 1 if you have the <stdlib.h> header file. */
+#undef HAVE_STDLIB_H
+
+/* Define to 1 if you have the `strcspn' function. */
+#undef HAVE_STRCSPN
+
+/* Define to 1 if you have the `strdup' function. */
+#undef HAVE_STRDUP
+
+/* Define to 1 if you have the <stream.h> header file. */
+#undef HAVE_STREAM_H
+
+/* Define to 1 if you have the <strings.h> header file. */
+#undef HAVE_STRINGS_H
+
+/* Define to 1 if you have the <string.h> header file. */
+#undef HAVE_STRING_H
+
+/* Define to 1 if you have the <strstream.h> header file. */
+#undef HAVE_STRSTREAM_H
+
+/* Define to 1 if you have the `strtol' function. */
+#undef HAVE_STRTOL
+
+/* Define if we have a function called "ieee_handler" in -lsunmath. */
+#undef HAVE_SUNMATH
+
+/* Define to 1 if you have the <sysent.h> header file. */
+#undef HAVE_SYSENT_H
+
+/* Define to 1 if you have the <sys/dir.h> header file. */
+#undef HAVE_SYS_DIR_H
+
+/* Define to 1 if you have the <sys/filio.h> header file. */
+#undef HAVE_SYS_FILIO_H
+
+/* Define to 1 if you have the <sys/ioctl.h> header file. */
+#undef HAVE_SYS_IOCTL_H
+
+/* Define to 1 if you have the <sys/ipc.h> header file. */
+#undef HAVE_SYS_IPC_H
+
+/* Define to 1 if you have the <sys/machsig.h> header file. */
+#undef HAVE_SYS_MACHSIG_H
+
+/* Define to 1 if you have the <sys/mman.h> header file. */
+#undef HAVE_SYS_MMAN_H
+
+/* Define to 1 if you have the <sys/ndir.h> header file. */
+#undef HAVE_SYS_NDIR_H
+
+/* Define to 1 if you have the <sys/param.h> header file. */
+#undef HAVE_SYS_PARAM_H
+
+/* Define to 1 if you have the <sys/select.h> header file. */
+#undef HAVE_SYS_SELECT_H
+
+/* Define to 1 if you have the <sys/sem.h> header file. */
+#undef HAVE_SYS_SEM_H
+
+/* Define to 1 if you have the <sys/siginfo.h> header file. */
+#undef HAVE_SYS_SIGINFO_H
+
+/* Define to 1 if you have the <sys/signal.h> header file. */
+#undef HAVE_SYS_SIGNAL_H
+
+/* Define to 1 if you have the <sys/socket.h> header file. */
+#undef HAVE_SYS_SOCKET_H
+
+/* Define to 1 if you have the <sys/statvfs.h> header file. */
+#undef HAVE_SYS_STATVFS_H
+
+/* Define to 1 if you have the <sys/stat.h> header file. */
+#undef HAVE_SYS_STAT_H
+
+/* Define to 1 if you have the <sys/systeminfo.h> header file. */
+#undef HAVE_SYS_SYSTEMINFO_H
+
+/* Define to 1 if you have the <sys/times.h> header file. */
+#undef HAVE_SYS_TIMES_H
+
+/* Define to 1 if you have the <sys/time.h> header file. */
+#undef HAVE_SYS_TIME_H
+
+/* Define to 1 if you have the <sys/types.h> header file. */
+#undef HAVE_SYS_TYPES_H
+
+/* Define to 1 if you have the <sys/unistd.h> header file. */
+#undef HAVE_SYS_UNISTD_H
+
+/* Define to 1 if you have the <sys/utsname.h> header file. */
+#undef HAVE_SYS_UTSNAME_H
+
+/* Define to 1 if you have the <sys/vfs.h> header file. */
+#undef HAVE_SYS_VFS_H
+
+/* Define to 1 if you have the <sys/vnode.h> header file. */
+#undef HAVE_SYS_VNODE_H
+
+/* Define to 1 if you have the <time.h> header file. */
+#undef HAVE_TIME_H
+
+/* Define to 1 if you have the <unistd.h> header file. */
+#undef HAVE_UNISTD_H
+
+/* Define to 1 if you have the <values.h> header file. */
+#undef HAVE_VALUES_H
+
+/* Define to 1 if you have the <X11/extensions/multibuf.h> header file. */
+#undef HAVE_X11_EXTENSIONS_MULTIBUF_H
+
+/* Define to 1 if you have the <X11/extensions/readdisplay.h> header file. */
+#undef HAVE_X11_EXTENSIONS_READDISPLAY_H
+
+/* Define to 1 if you have the <X11/extensions/transovl.h> header file. */
+#undef HAVE_X11_EXTENSIONS_TRANSOVL_H
+
+/* Define to 1 if you have the <Xmu/Editres.h> header file. */
+#undef HAVE_XMU_EDITRES_H
+
+/* Define to 1 if your C compiler doesn't accept -c and -o together. */
+#undef NO_MINUS_C_MINUS_O
+
+/* define if the class ostream has member function form */
+#undef OSTREAM_FORM_OK
+
+/* Name of package */
+#undef PACKAGE
+
+/* Define to the address where bug reports for this package should be sent. */
+#undef PACKAGE_BUGREPORT
+
+/* Define to the full name of this package. */
+#undef PACKAGE_NAME
+
+/* Define to the full name and version of this package. */
+#undef PACKAGE_STRING
+
+/* Define to the one symbol short name of this package. */
+#undef PACKAGE_TARNAME
+
+/* Define to the version of this package. */
+#undef PACKAGE_VERSION
+
+/* Define if compiler has function prototypes */
+#undef PROTOTYPES
+
+/* Define as the return type of signal handlers (`int' or `void'). */
+#undef RETSIGTYPE
+
+/* define if the function semctl takes a value */
+#undef SEMCTL_NO_REFERENCE
+
+/* define if the function semop takes a value */
+#undef SEMOP_NO_REFERENCE
+
+/* define if semun has member __buf */
+#undef SEMUN_BUF_DEFINED
+
+/* define if the union semun is in sys/sem.h */
+#undef SEMUN_DEFINED
+
+/* If using the C implementation of alloca, define if you know the
+ direction of stack growth for your system; otherwise it will be
+ automatically deduced at run-time.
+ STACK_DIRECTION > 0 => grows toward higher addresses
+ STACK_DIRECTION < 0 => grows toward lower addresses
+ STACK_DIRECTION = 0 => direction of growth unknown */
+#undef STACK_DIRECTION
+
+/* Define to 1 if you have the ANSI C header files. */
+#undef STDC_HEADERS
+
+/* Define to 1 if your <sys/time.h> declares `struct tm'. */
+#undef TM_IN_SYS_TIME
+
+/* Version number of package */
+#undef VERSION
+
+/* Define to 1 if your processor stores words with the most significant byte
+ first (like Motorola and SPARC, unlike Intel and VAX). */
+#undef WORDS_BIGENDIAN
+
+/* Define to 1 if on AIX 3.
+ System headers sometimes define this.
+ We just want to avoid a redefinition error message. */
+#ifndef _ALL_SOURCE
+# undef _ALL_SOURCE
+#endif
+
+/* Define to `unsigned' if <sys/types.h> does not define. */
+#undef size_t
--- /dev/null
+dnl Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+dnl CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+dnl
+dnl This library is free software; you can redistribute it and/or
+dnl modify it under the terms of the GNU Lesser General Public
+dnl License as published by the Free Software Foundation; either
+dnl version 2.1 of the License.
+dnl
+dnl This library is distributed in the hope that it will be useful,
+dnl but WITHOUT ANY WARRANTY; without even the implied warranty of
+dnl MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+dnl Lesser General Public License for more details.
+dnl
+dnl You should have received a copy of the GNU Lesser General Public
+dnl License along with this library; if not, write to the Free Software
+dnl Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+dnl
+dnl See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+dnl
+dnl
+dnl
+
+AC_DEFUN([CHECK_LAM],[
+
+AC_REQUIRE([AC_PROG_CC])dnl
+
+AC_ARG_WITH(lam,
+ --with-lam=DIR root directory path of LAM installation,
+ WITHLAM="yes",WITHLAM="no")
+
+MPI_INCLUDES=""
+MPI_LIBS=""
+if test "$WITHLAM" = yes; then
+
+ echo
+ echo ---------------------------------------------
+ echo testing lam
+ echo ---------------------------------------------
+ echo
+ LAM_HOME=$withval
+
+ if test "$LAM_HOME"; then
+ MPI_INCLUDES="-I$LAM_HOME/include"
+ MPI_LIBS="-L$LAM_HOME/lib"
+ fi
+
+ CPPFLAGS_old="$CPPFLAGS"
+ CPPFLAGS="$MPI_INCLUDES $CPPFLAGS"
+ AC_CHECK_HEADER(mpi.h,WITHLAM="yes",WITHLAM="no")
+ CPPFLAGS="$CPPFLAGS_old"
+
+ if test "$WITHLAM" = "yes";then
+ AC_CHECK_LIB(util,openpty,,WITHLAM="no")
+ LIBS_old="$LIBS"
+ LDFLAGS_old="$LDFLAGS"
+ LDFLAGS="$MPI_LIBS $LDFLAGS"
+ AC_CHECK_LIB(lam,lam_mp_init,,WITHLAM="no")
+ AC_CHECK_LIB(mpi,MPI_Init,WITHLAM="yes",WITHLAM="no")
+ AC_CHECK_LIB(mpi,MPI_Publish_name,WITHMPI2="yes",WITHMPI2="no")
+ LDFLAGS="$LDFLAGS_old"
+ LIBS="$LIBS_old"
+ fi
+
+ if test "$WITHLAM" = "yes";then
+ mpi_ok=yes
+ MPI_LIBS="$MPI_LIBS -lmpi -llam"
+ else
+ mpi_ok=no
+ fi
+
+fi
+
+
+])dnl
--- /dev/null
+# Check for OpenPBS
+AC_DEFUN([CHECK_OPENPBS],
+[
+ AC_ARG_VAR([OPENPBS], [OpenPBS home directory])
+ AC_ARG_WITH([openpbs],
+ AC_HELP_STRING([--with-openpbs=<path>],
+ [tell configure script to use OpenPBS that is located at <path>]),
+ [test ! x"${withval}" = xyes && OPENPBS=${withval}],
+ [])
+
+ dnl AC_ARG_VAR([OPENPBSSERVERNAME], [OpenPBS server_name file])
+ dnl AC_ARG_WITH([openpbs-server-name],
+ dnl AC_HELP_STRING([--with-openpbs-server-name=<path>],
+ dnl [tell configure script to use OpenPBS server_name file that is located at <path>]),
+ dnl [test ! x"${withval}" = xyes && OPENPBSSERVERNAME=${withval}],
+ dnl [with_openpbs_server_name=""])
+
+
+ if test -z "${OPENPBS}"
+ then
+ AC_MSG_WARN([Environment variable OPENPBS not set. Skipping OpenPBS configuration.])
+
+ else
+
+ OPENPBS_INCLUDES="-I${OPENPBS}/include"
+ saved_CPPFLAGS=${CPPFLAGS}
+ CPPFLAGS="${CPPFLAGS} ${OPENPBS_INCLUDES}"
+ AC_CHECK_HEADER([pbs_ifl.h], [openpbs_header_found=yes], [openpbs_header_found=no], [])
+ test x${openpbs_header_found} = xno && AC_MSG_WARN([OpenPBS include file not found])
+ CPPFLAGS=${saved_CPPFLAGS}
+ AC_SUBST(OPENPBS_INCLUDES)
+
+ OPENPBS_LIBDIR="-L${OPENPBS}/lib"
+ OPENPBS_LIBS="-lpbs"
+ saved_LDFLAGS=${LDFLAGS}
+ saved_LIBS=${LIBS}
+ LDFLAGS="${LDFLAGS} ${OPENPBS_LIBDIR}"
+ AC_CHECK_LIB([pbs], [pbs_connect], [openpbs_lib_found=yes], [openpbs_lib_found=no], [])
+ test x${openpbs_lib_found} = xno && AC_MSG_WARN([OpenPBS library not found])
+ LIBS="${LIBS} ${OPENPBS_LIBS}"
+ LDFLAGS=${saved_LDFLAGS}
+ LIBS=${saved_LIBS}
+ AC_SUBST(OPENPBS_LIBDIR)
+ AC_SUBST(OPENPBS_LIBS)
+
+ dnl test -z "${OPENPBSSERVERNAME}" && OPENPBSSERVERNAME="/usr/spool/PBS/server_name"
+ dnl AC_CHECK_FILE([${OPENPBSSERVERNAME}], [openpbs_server_name_found=yes], [openpbs_server_name_found=no])
+
+ test x${openpbs_header_found} = xyes && test x${openpbs_lib_found} = xyes && openpbs_ok="yes"
+
+ fi
+
+ WITHOPENPBS=$openpbs_ok
+ AC_SUBST(WITHOPENPBS)
+
+])
+
--- /dev/null
+AC_DEFUN([CHECK_SOCKETS],[
+
+dnl Author
+
+dnl Warren Young <warren@etr-usa.com>
+dnl M4 Source Code
+
+echo
+echo ---------------------------------------------
+echo testing sockets
+echo ---------------------------------------------
+echo
+
+AC_CACHE_CHECK(for libraries containing socket functions,
+ac_cv_socket_libs, [
+ oCFLAGS=$CFLAGS
+
+ AC_TRY_LINK([
+ #include <sys/types.h>
+ #include <sys/socket.h>
+ #include <netinet/in.h>
+ #include <arpa/inet.h>
+ ],
+ [
+ struct in_addr add;
+ int sd = socket(AF_INET, SOCK_STREAM, 0);
+ inet_ntoa(add);
+ ],
+ ac_cv_socket_libs=-lc, ac_cv_socket_libs=no)
+
+ if test x"$ac_cv_socket_libs" = "xno"
+ then
+ CFLAGS="$oCFLAGS -lsocket"
+ AC_TRY_LINK([
+ #include <sys/types.h>
+ #include <sys/socket.h>
+ #include <netinet/in.h>
+ #include <arpa/inet.h>
+ ],
+ [
+ struct in_addr add;
+ int sd = socket(AF_INET, SOCK_STREAM, 0);
+ inet_ntoa(add);
+ ],
+ ac_cv_socket_libs=-lsocket, ac_cv_socket_libs=no)
+ fi
+
+ if test x"$ac_cv_socket_libs" = "xno"
+ then
+ CFLAGS="$oCFLAGS -lsocket -lnsl"
+ AC_TRY_LINK([
+ #include <sys/types.h>
+ #include <sys/socket.h>
+ #include <netinet/in.h>
+ #include <arpa/inet.h>
+ ],
+ [
+ struct in_addr add;
+ int sd = socket(AF_INET, SOCK_STREAM, 0);
+ inet_ntoa(add);
+ ],
+ ac_cv_socket_libs="-lsocket -lnsl", ac_cv_socket_libs=no)
+ fi
+
+ CFLAGS=$oCFLAGS
+])
+
+ if test x"$ac_cv_socket_libs" = "xno"
+ then
+ AC_MSG_ERROR([Cannot find socket libraries])
+ elif test x"$ac_cv_socket_libs" = "x-lc"
+ then
+ SOCKETLIBS=""
+ CPPFLAGS="-DHAVE_SOCKET $CPPFLAGS"
+ CORBA_IDLCXXFLAGS="-DHAVE_SOCKET $CORBA_IDLCXXFLAGS"
+ CORBA_IDLPYFLAGS="-DHAVE_SOCKET $CORBA_IDLPYFLAGS"
+ else
+ SOCKETLIBS="$ac_cv_socket_libs"
+ CPPFLAGS="-DHAVE_SOCKET $CPPFLAGS"
+ CORBA_IDLCXXFLAGS="-DHAVE_SOCKET $CORBA_IDLCXXFLAGS"
+ CORBA_IDLPYFLAGS="-DHAVE_SOCKET $CORBA_IDLPYFLAGS"
+ fi
+
+ AC_SUBST(SOCKETLIBS)
+ AC_SUBST(SOCKETFLAGS)
+]) dnl CHECK_SOCKET
--- /dev/null
+/*
+ * APIInternalFailureException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 20 15:15:42 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_APIInternalFailureException.hxx"
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * APIInternalFailureException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 20 15:15:41 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _APIINTERNALFAILUREEXCEPTION_H_
+#define _APIINTERNALFAILUREEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class APIInternalFailureException : public GenericException
+ {
+ public:
+ // Constructeur
+ APIInternalFailureException(string ch = "undefined") : GenericException("APIInternalFailureException", ch) {}
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * BatchManager.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <iostream>
+#include <sstream>
+#include <string>
+#include <netdb.h>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_Job.hxx"
+#include "Batch_JobId.hxx"
+#include "Batch_JobInfo.hxx"
+#include "Batch_InvalidArgumentException.hxx"
+#include "Batch_FactBatchManager.hxx"
+#include "Batch_BatchManager.hxx"
+
+namespace Batch {
+
+ // Constructeur
+// BatchManager::BatchManager(string host) throw(InvalidArgumentException) : _hostname(host), jobid_map()
+// {
+// // On verifie que le hostname est correct
+// if (!gethostbyname(_hostname.c_str())) { // hostname unknown from network
+// string msg = "hostname \"";
+// msg += _hostname;
+// msg += "\" unknown from the network";
+// throw InvalidArgumentException(msg.c_str());
+// }
+// }
+ BatchManager::BatchManager(const FactBatchManager * parent, const char * host) throw(InvalidArgumentException) : _hostname(host), jobid_map(), _parent(parent)
+ {
+ // On verifie que le hostname est correct
+ if (!gethostbyname(_hostname.c_str())) { // hostname unknown from network
+ string msg = "hostname \"";
+ msg += _hostname;
+ msg += "\" unknown from the network";
+ throw InvalidArgumentException(msg.c_str());
+ }
+ }
+
+ // Destructeur
+ BatchManager::~BatchManager()
+ {
+ // Nothing to do
+ }
+
+ string BatchManager::__repr__() const
+ {
+ ostringstream oss;
+ oss << "<BatchManager of type '" << (_parent ? _parent->getType() : "unknown (no factory)") << "' connected to server '" << _hostname << "'>";
+ return oss.str();
+ }
+
+ // Recupere le l'identifiant d'un job deja soumis au BatchManager
+// const JobId BatchManager::getJobIdByReference(const string & ref)
+// {
+// return JobId(this, ref);
+// }
+ const JobId BatchManager::getJobIdByReference(const char * ref)
+ {
+ return JobId(this, ref);
+ }
+
+// // Methode pour le controle des jobs : soumet un job au gestionnaire
+// const JobId BatchManager::submitJob(const Job & job)
+// {
+// static int idx = 0;
+// //MEDMEM::STRING sst;
+// ostringstream sst;
+// sst << "Jobid_" << idx++;
+// JobId id(this, sst.str());
+// return id;
+// }
+
+// // Methode pour le controle des jobs : retire un job du gestionnaire
+// void BatchManager::deleteJob(const JobId & jobid)
+// {
+// // Nothing to do
+// }
+
+// // Methode pour le controle des jobs : suspend un job en file d'attente
+// void BatchManager::holdJob(const JobId & jobid)
+// {
+// // Nothing to do
+// }
+
+// // Methode pour le controle des jobs : relache un job suspendu
+// void BatchManager::releaseJob(const JobId & jobid)
+// {
+// // Nothing to do
+// }
+
+// // Methode pour le controle des jobs : modifie un job en file d'attente
+// void BatchManager::alterJob(const JobId & jobid, const Parametre & param, const Environnement & env)
+// {
+// // Nothing to do
+// }
+
+// // Methode pour le controle des jobs : modifie un job en file d'attente
+// void BatchManager::alterJob(const JobId & jobid, const Parametre & param)
+// {
+// // Nothing to do
+// }
+
+// // Methode pour le controle des jobs : modifie un job en file d'attente
+// void BatchManager::alterJob(const JobId & jobid, const Environnement & env)
+// {
+// // Nothing to do
+// }
+
+// // Methode pour le controle des jobs : renvoie l'etat du job
+// JobInfo BatchManager::queryJob(const JobId & jobid)
+// {
+// return JobInfo();
+// }
+
+}
--- /dev/null
+/*
+ * BatchManager.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _BATCHMANAGER_H_
+#define _BATCHMANAGER_H_
+
+using namespace std;
+#include <string>
+#include <map>
+#include "Batch_Job.hxx"
+#include "Batch_JobId.hxx"
+#include "Batch_JobInfo.hxx"
+#include "Batch_InvalidArgumentException.hxx"
+
+namespace Batch {
+
+ class Job;
+ class JobId;
+ class JobInfo;
+ class FactBatchManager;
+
+ class BatchManager
+ {
+ public:
+ // Constructeur et destructeur
+ //BatchManager(string host="localhost") throw(InvalidArgumentException); // connexion a la machine host
+ BatchManager(const FactBatchManager * parent, const char * host="localhost") throw(InvalidArgumentException); // connexion a la machine host
+ virtual ~BatchManager();
+ virtual string __repr__() const;
+
+ // Recupere le l'identifiant d'un job deja soumis au BatchManager
+ //virtual const JobId getJobIdByReference(const string & ref);
+ virtual const JobId getJobIdByReference(const char * ref);
+
+ // Methodes pour le controle des jobs : virtuelles pures
+ virtual const JobId submitJob(const Job & job) = 0; // soumet un job au gestionnaire
+ virtual void deleteJob(const JobId & jobid) = 0; // retire un job du gestionnaire
+ virtual void holdJob(const JobId & jobid) = 0; // suspend un job en file d'attente
+ virtual void releaseJob(const JobId & jobid) = 0; // relache un job suspendu
+ virtual void alterJob(const JobId & jobid, const Parametre & param, const Environnement & env) = 0; // modifie un job en file d'attente
+ virtual void alterJob(const JobId & jobid, const Parametre & param) = 0; // modifie un job en file d'attente
+ virtual void alterJob(const JobId & jobid, const Environnement & env) = 0; // modifie un job en file d'attente
+ virtual JobInfo queryJob(const JobId & jobid) = 0; // renvoie l'etat du job
+
+ protected:
+ string _hostname; // serveur ou tourne le BatchManager
+ map< const string, const JobId * > jobid_map; // table des jobs deja soumis
+ const FactBatchManager * _parent;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * BatchManagerCatalog.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2004
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include <sstream>
+#include <map>
+#include "Batch_BatchManagerCatalog.hxx"
+#include "Batch_FactBatchManager.hxx"
+
+namespace Batch {
+
+ pthread_mutex_t BatchManagerCatalog::_mutex = PTHREAD_MUTEX_INITIALIZER;
+ map<string, FactBatchManager *> * BatchManagerCatalog::_p_catalog = 0;
+
+ // Constructeur
+ BatchManagerCatalog::BatchManagerCatalog()
+ {
+ // Nothing to do
+ }
+
+ // Destructeur
+ BatchManagerCatalog::~BatchManagerCatalog()
+ {
+ // Nothing to do
+ }
+
+ // Functor
+ FactBatchManager * BatchManagerCatalog::getFactBatchManager(const char * type)
+ {
+ return (* BatchManagerCatalog::_p_catalog)[type];
+ }
+
+ void BatchManagerCatalog::addFactBatchManager(const char * type, FactBatchManager * pFBM)
+ {
+ if (pFBM) { // *** section critique ***
+ pthread_mutex_lock(&_mutex);
+
+ if (! BatchManagerCatalog::_p_catalog) BatchManagerCatalog::_p_catalog = new map<string, FactBatchManager *>;
+ (*BatchManagerCatalog::_p_catalog)[type] = pFBM;
+
+ pthread_mutex_unlock(&_mutex);
+ }
+ }
+
+ FactBatchManager * BatchManagerCatalog::operator() (const char * type) const
+ {
+ return BatchManagerCatalog::getFactBatchManager(type);
+ }
+
+ map<string, FactBatchManager *> * BatchManagerCatalog::dict() const
+ {
+ return _p_catalog;
+ }
+
+ string BatchManagerCatalog::__repr__() const
+ {
+ ostringstream oss;
+ oss << "<BatchManagerCatalog contains {";
+ string sep;
+ for(map<string, FactBatchManager *>::const_iterator it = (*_p_catalog).begin(); it != (*_p_catalog).end(); it++, sep=", ") {
+ oss << sep << "'" << (*it).first << "' : '" << (*it).second->__repr__() << "'";
+ }
+ oss << "}>";
+ return oss.str();
+ }
+
+}
--- /dev/null
+/*
+ * BatchManagerCatalog.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2004
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _CATALOG_H_
+#define _CATALOG_H_
+
+using namespace std;
+#include <string>
+#include <map>
+#include <pthread.h>
+
+namespace Batch {
+
+ class FactBatchManager;
+
+ class BatchManagerCatalog
+ {
+ public:
+ // Constructeur
+ BatchManagerCatalog();
+ // Destructeur
+ virtual ~BatchManagerCatalog();
+
+ static FactBatchManager * getFactBatchManager(const char * type);
+ static void addFactBatchManager(const char * type, FactBatchManager * pFBM);
+ virtual FactBatchManager * operator() (const char * type) const;
+
+ virtual map<string, FactBatchManager *> * dict() const;
+ virtual string __repr__() const;
+
+ protected:
+ static map<string, FactBatchManager *> * _p_catalog;
+ static pthread_mutex_t _mutex;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * BatchManager_PBS.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 6 10:17:22 2003
+ * Projet : Salome 2
+ *
+ */
+
+extern "C" {
+#include <pbs_error.h>
+#include <pbs_ifl.h>
+}
+#include <iostream>
+#include <fstream>
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_BatchManager_PBS.hxx"
+
+namespace Batch {
+
+ // Recupere le nom du serveur par defaut
+// string BatchManager_PBS::getDefaultServer() {
+// string server_name = "localhost";
+
+// const char * server_name_path = "@openpbsspooldir@/server_name";
+// ifstream server_name_file(server_name_path);
+// if (server_name_file) {
+// server_name_file >> server_name;
+// server_name_file.close();
+// }
+
+// return server_name;
+// }
+
+ // Constructeur
+// BatchManager_PBS::BatchManager_PBS() throw(InvalidArgumentException,ConnexionFailureException) : BatchManager(BatchManager_PBS::getDefaultServer())
+// {
+// // On se connecte au serveur PBS
+// _connect = pbs_connect(const_cast< char * >(_hostname.c_str()));
+// if (_connect < 0) { // si erreur
+// char * errmsg = pbs_geterrmsg(_connect);
+// string msg = "PBS Server on host \"";
+// msg += _hostname;
+// msg += "\" : ";
+// msg += errmsg ? errmsg : "Reason unknown";
+// throw ConnexionFailureException(msg.c_str());
+// }
+// }
+
+ // Constructeur
+// BatchManager_PBS::BatchManager_PBS(string host) throw(InvalidArgumentException,ConnexionFailureException) : BatchManager(host)
+// {
+// // On se connecte au serveur PBS
+// _connect = pbs_connect(const_cast< char * >(_hostname.c_str()));
+// if (_connect < 0) { // si erreur
+// char * errmsg = pbs_geterrmsg(_connect);
+// string msg = "PBS Server on host \"";
+// msg += _hostname;
+// msg += "\" : ";
+// msg += errmsg ? errmsg : "Reason unknown";
+// throw ConnexionFailureException(msg.c_str());
+// }
+// }
+ BatchManager_PBS::BatchManager_PBS(const FactBatchManager * parent, const char * host) throw(InvalidArgumentException,ConnexionFailureException) : BatchManager(parent, host)
+ {
+ // On se connecte au serveur PBS
+ _connect = pbs_connect(const_cast< char * >(_hostname.c_str()));
+ if (_connect < 0) { // si erreur
+ char * errmsg = pbs_geterrmsg(_connect);
+ string msg = "PBS Server on host \"";
+ msg += _hostname;
+ msg += "\" : ";
+ msg += errmsg ? errmsg : "Reason unknown";
+ throw ConnexionFailureException(msg.c_str());
+ }
+ }
+
+ // Destructeur
+ BatchManager_PBS::~BatchManager_PBS()
+ {
+ // On se deconnecte du serveur PBS
+ int rc = pbs_disconnect(_connect);
+ if (rc < 0) { // si erreur
+ string msg = "PBS Server on host \"";
+ msg += _hostname;
+ msg += "\" : ";
+ msg += pbs_geterrmsg(_connect);
+ throw ConnexionFailureException(msg.c_str());
+ }
+ }
+
+ // Methode pour le controle des jobs : soumet un job au gestionnaire
+ const JobId BatchManager_PBS::submitJob(const Job & job)
+ {
+ Job_PBS jobpbs = job;
+ char * ref = pbs_submit(_connect,
+ jobpbs.getAttributesOP(),
+ jobpbs.getScript(),
+ jobpbs.getDestination(),
+ NULL);
+ if (!ref) { // si erreur
+ char * msg = pbs_geterrmsg(_connect);
+ if (!msg) msg = "unknown";
+ throw APIInternalFailureException(string("PBS submit error. Reason : ") + msg);
+ }
+
+ JobId id(this, string(ref));
+ free(ref);
+ return id;
+ }
+
+ // Methode pour le controle des jobs : retire un job du gestionnaire
+ void BatchManager_PBS::deleteJob(const JobId & jobid)
+ {
+ char * ref = const_cast< char * >(jobid.getReference().c_str());
+ int rc = pbs_deljob(_connect, ref, 0);
+ if (rc) { // si erreur
+ char * msg = pbs_geterrmsg(_connect);
+ if (!msg) msg = "unknown";
+ throw APIInternalFailureException(string("PBS deljob error. Reason : ") + msg);
+ }
+ }
+
+ // Methode pour le controle des jobs : suspend un job en file d'attente
+ void BatchManager_PBS::holdJob(const JobId & jobid)
+ {
+ char * ref = const_cast< char * >(jobid.getReference().c_str());
+ int rc = pbs_holdjob(_connect, ref, USER_HOLD, 0);
+ if (rc) { // si erreur
+ char * msg = pbs_geterrmsg(_connect);
+ if (!msg) msg = "unknown";
+ throw APIInternalFailureException(string("PBS holdjob error. Reason : ") + msg);
+ }
+ }
+
+ // Methode pour le controle des jobs : relache un job suspendu
+ void BatchManager_PBS::releaseJob(const JobId & jobid)
+ {
+ char * ref = const_cast< char * >(jobid.getReference().c_str());
+ int rc = pbs_rlsjob(_connect, ref, USER_HOLD, 0);
+ if (rc) { // si erreur
+ char * msg = pbs_geterrmsg(_connect);
+ if (!msg) msg = "unknown";
+ throw APIInternalFailureException(string("PBS rlsjob error. Reason : ") + msg);
+ }
+ }
+
+
+ // Methode pour le controle des jobs : modifie un job en file d'attente
+ void BatchManager_PBS::alterJob(const JobId & jobid, const Parametre & param, const Environnement & env)
+ {
+ Job job(param, env);
+ Job_PBS jobpbs(job);
+
+ char * ref = const_cast< char * >(jobid.getReference().c_str());
+ int rc = pbs_alterjob(_connect,
+ ref,
+ jobpbs.getAttributes(),
+ NULL);
+ if (rc) { // si erreur
+ char * msg = pbs_geterrmsg(_connect);
+ if (!msg) msg = "unknown";
+ throw APIInternalFailureException(string("PBS alterjob error. Reason : ") + msg);
+ }
+
+ }
+
+ // Methode pour le controle des jobs : modifie un job en file d'attente
+ void BatchManager_PBS::alterJob(const JobId & jobid, const Parametre & param)
+ {
+ alterJob(jobid, param, Environnement());
+ }
+
+ // Methode pour le controle des jobs : modifie un job en file d'attente
+ void BatchManager_PBS::alterJob(const JobId & jobid, const Environnement & env)
+ {
+ alterJob(jobid, Parametre(), env);
+ }
+
+
+
+ // Methode pour le controle des jobs : renvoie l'etat du job
+ JobInfo BatchManager_PBS::queryJob(const JobId & jobid)
+ {
+ char * id = const_cast< char * >(jobid.getReference().c_str());
+ JobInfo_PBS ji = JobInfo_PBS(pbs_statjob(_connect, id, 0, 0), true);
+ return ji;
+ }
+
+
+
+}
--- /dev/null
+/*
+ * BatchManager_PBS.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 6 10:17:22 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _BATCHMANAGER_PBS_H_
+#define _BATCHMANAGER_PBS_H_
+
+
+#include "Batch_Job.hxx"
+#include "Batch_Job.hxx"
+#include "Batch_JobId.hxx"
+#include "Batch_JobInfo.hxx"
+#include "Batch_JobInfo_PBS.hxx"
+#include "Batch_Job_PBS.hxx"
+#include "Batch_InvalidArgumentException.hxx"
+#include "Batch_ConnexionFailureException.hxx"
+#include "Batch_APIInternalFailureException.hxx"
+#include "Batch_NotYetImplementedException.hxx"
+#include "Batch_BatchManager.hxx"
+
+namespace Batch {
+
+ class Job;
+ class JobId;
+ class JobInfo;
+ class FactBatchManager;
+
+ class BatchManager_PBS : public BatchManager
+ {
+ public:
+ // Constructeur et destructeur
+ //BatchManager_PBS() throw(InvalidArgumentException,ConnexionFailureException); // connexion au serveur par defaut
+ //BatchManager_PBS(string host) throw(InvalidArgumentException,ConnexionFailureException); // connexion a la machine host
+ BatchManager_PBS(const FactBatchManager * parent, const char * host="localhost") throw(InvalidArgumentException,ConnexionFailureException); // connexion a la machine host
+ virtual ~BatchManager_PBS();
+
+ // Recupere le nom du serveur par defaut
+ // static string BatchManager_PBS::getDefaultServer();
+
+ // Methodes pour le controle des jobs
+ virtual const JobId submitJob(const Job & job); // soumet un job au gestionnaire
+ virtual void deleteJob(const JobId & jobid); // retire un job du gestionnaire
+ virtual void holdJob(const JobId & jobid); // suspend un job en file d'attente
+ virtual void releaseJob(const JobId & jobid); // relache un job suspendu
+ virtual void alterJob(const JobId & jobid, const Parametre & param, const Environnement & env); // modifie un job en file d'attente
+ virtual void alterJob(const JobId & jobid, const Parametre & param); // modifie un job en file d'attente
+ virtual void alterJob(const JobId & jobid, const Environnement & env); // modifie un job en file d'attente
+ virtual JobInfo queryJob(const JobId & jobid); // renvoie l'etat du job
+
+ virtual void setParametre(const JobId & jobid, const Parametre & param) { return alterJob(jobid, param); } // modifie un job en file d'attente
+ virtual void setEnvironnement(const JobId & jobid, const Environnement & env) { return alterJob(jobid, env); } // modifie un job en file d'attente
+
+
+ protected:
+ int _connect; // PBS connect id
+
+ private:
+
+#ifdef SWIG
+ public:
+ // Recupere le l'identifiant d'un job deja soumis au BatchManager
+ //virtual const JobId getJobIdByReference(const string & ref) { return BatchManager::getJobIdByReference(ref); }
+ virtual const JobId getJobIdByReference(const char * ref) { return BatchManager::getJobIdByReference(ref); }
+#endif
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * BoolType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include "Batch_BoolType.hxx"
+
+namespace Batch {
+
+ // Conversion en chaine
+ string BoolType::affiche() const
+ {
+ return _data ? string("true") : string("false");
+ }
+
+ // Operateur d'affectation
+ BoolType & BoolType::operator =(bool b)
+ {
+ _data = b;
+ return *this;
+ }
+
+ // Conversion en bool
+ BoolType::operator bool() const
+ {
+ return this->_data;
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * BoolType::clone() const
+ {
+ BoolType * pB = new BoolType(this->_data);
+ assert(pB != 0);
+ return pB;
+ }
+
+}
--- /dev/null
+/*
+ * BoolType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _BOOLTYPE_H_
+#define _BOOLTYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+
+namespace Batch {
+
+ class BoolType : public GenericType
+ {
+ public:
+ // Constructeur
+ BoolType(const bool b=false) : _data(b) {}
+
+ // Conversion en chaine
+ virtual string affiche() const;
+
+ // Operateur d'affectation
+ virtual BoolType & operator =(bool);
+
+ // Conversion en bool
+ virtual operator bool() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ bool _data;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * CharType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include "Batch_CharType.hxx"
+
+namespace Batch {
+
+ // Conversion en chaine
+ string CharType::affiche() const
+ {
+ return string(1, _data);
+ }
+
+ // Operateur d'affectation
+ CharType & CharType::operator =(char c)
+ {
+ _data = c;
+ return *this;
+ }
+
+ // Conversion en char
+ CharType::operator char() const
+ {
+ return this->_data;
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * CharType::clone() const
+ {
+ CharType * pC = new CharType(this->_data);
+ assert(pC != 0);
+ return pC;
+ }
+
+}
--- /dev/null
+/*
+ * CharType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _CHARTYPE_H_
+#define _CHARTYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+
+namespace Batch {
+
+ class CharType : public GenericType
+ {
+ public:
+ // Constructeur
+ CharType(const char c=0) : _data(c) {}
+
+ // Conversion en chaine
+ virtual string affiche() const;
+
+ // Operateur d'affectation
+ virtual CharType & operator =(char);
+
+ // Conversion en char
+ virtual operator char() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ char _data;
+
+ private:
+
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * ConnexionFailureException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 13 11:24:31 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_ConnexionFailureException.hxx"
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * ConnexionFailureException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 13 11:24:31 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _CONNEXIONFAILUREEXCEPTION_H_
+#define _CONNEXIONFAILUREEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class ConnexionFailureException : public GenericException
+ {
+ public:
+ // Constructeur
+ ConnexionFailureException(string ch = "undefined") : GenericException("ConnexionFailureException", ch) {}
+
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * Couple.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Dec 9 15:00:35 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_Couple.hxx"
+
+namespace Batch {
+
+ // Operateur d'affectation
+ Couple & Couple::operator =(const Couple & C)
+ {
+ _local = C._local;
+ _remote = C._remote;
+ return *this;
+ }
+
+ // Conversion en chaine
+ string Couple::str() const
+ {
+ string res;
+ res = "Couple(local : ";
+ res += _local;
+ res += ", remote : ";
+ res += _remote;
+ res += ")";
+ return res;
+ }
+
+ // Operateur pour l'affichage sur un stream
+ ostream & operator << (ostream & os, const Couple & cp)
+ {
+ return os << cp.str();
+ }
+
+}
--- /dev/null
+/*
+ * Couple.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Dec 9 15:00:35 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _COUPLE_H_
+#define _COUPLE_H_
+
+using namespace std;
+#include <string>
+
+namespace Batch {
+
+ class Couple
+ {
+ public:
+ // Constructeur standard
+ Couple(const string & local="", const string & remote="") : _local(local), _remote(remote) {}
+
+ // Constructeur par recopie
+ Couple(const Couple & C) : _local(C._local), _remote(C._remote) {}
+
+ // Operateur pour l'affichage sur un stream
+ friend ostream & operator << (ostream & os, const Couple & cp);
+
+ // Operateur d'affectation
+ virtual Couple & operator =(const Couple &);
+
+ // Conversion en chaine
+ virtual string str() const;
+
+ // Accesseurs
+ virtual string getLocal() const { return _local; }
+ virtual string getRemote() const { return _remote; }
+
+ protected:
+ string _local; // chemin d'acces au fichier local
+ string _remote; // chemin d'acees au fichier distant
+
+ private:
+
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * CoupleType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Dec 9 14:51:53 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_CoupleType.hxx"
+
+namespace Batch {
+
+ // Conversion en chaine
+ string CoupleType::affiche() const
+ {
+ return _data.str();
+ }
+
+ // Operateur d'affectation
+ CoupleType & CoupleType::operator =(const Couple & C)
+ {
+ _data = C;
+ return *this;
+ }
+
+ // Conversion en char
+ CoupleType::operator Couple() const
+ {
+ return _data;
+ }
+
+ // Conversion en chaine
+ CoupleType::operator string() const
+ {
+ return _data.str();
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * CoupleType::clone() const
+ {
+ CoupleType * pC = new CoupleType(this->_data);
+ assert(pC != 0);
+ return pC;
+ }
+
+}
+
--- /dev/null
+/*
+ * CoupleType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Dec 9 14:51:53 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _COUPLETYPE_H_
+#define _COUPLETYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+#include "Batch_Couple.hxx"
+
+namespace Batch {
+
+ class CoupleType : public GenericType
+ {
+ public:
+ // Constructeur
+ CoupleType(const Couple & C) : _data(C) {}
+
+ // Conversion en chaine
+ virtual string affiche() const;
+ virtual operator string() const;
+
+ // Operateur d'affectation
+ virtual CoupleType & operator =(const Couple & C);
+
+ // Conversion en char
+ virtual operator Couple() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ Couple _data;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * Date.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Nov 26 14:11:42 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include <cstdio>
+#include <ctime>
+#include "Batch_Date.hxx"
+
+namespace Batch {
+
+ Date::Date(const long l)
+ {
+ struct tm * p_tm = localtime(&l);
+ _day = p_tm->tm_mday;
+ _month = p_tm->tm_mon + 1;
+ _year = p_tm->tm_year + 1900;
+ _hour = p_tm->tm_hour;
+ _min = p_tm->tm_min;
+ _sec = p_tm->tm_sec;
+ }
+
+ Date::Date(const string s)
+ {
+ if ((s == "now") || (s == "Now") || (s == "NOW")) {
+ long l = time(0);
+ struct tm * p_tm = localtime(&l);
+ _day = p_tm->tm_mday;
+ _month = p_tm->tm_mon + 1;
+ _year = p_tm->tm_year + 1900;
+ _hour = p_tm->tm_hour;
+ _min = p_tm->tm_min;
+ _sec = p_tm->tm_sec;
+
+ } else {
+ char c;
+// istringstream ist(s);
+// ist >> _day >> c
+// >> _month >> c
+// >> _year >> c
+// >> _hour >> c
+// >> _min >> c
+// >> _sec;
+ sscanf(s.c_str(), "%ld/%ld/%ld-%ld:%ld:%ld", &_day, &_month, &_year, &_hour, &_min, &_sec);
+ }
+ }
+
+ Date & Date::operator =(long l)
+ {
+ struct tm * p_tm = localtime(&l);
+ _day = p_tm->tm_mday;
+ _month = p_tm->tm_mon + 1;
+ _year = p_tm->tm_year + 1900;
+ _hour = p_tm->tm_hour;
+ _min = p_tm->tm_min;
+ _sec = p_tm->tm_sec;
+
+ return *this;
+ }
+
+ Date & Date::operator +(long l)
+ {
+ *this = epoch() + l;
+ return *this;
+ }
+
+ Date & Date::operator -(long l)
+ {
+ *this = epoch() - l;
+ return *this;
+ }
+
+ Date & Date::operator +=(long l)
+ {
+ *this = epoch() + l;
+ return *this;
+ }
+
+ Date & Date::operator -=(long l)
+ {
+ *this = epoch() - l;
+ return *this;
+ }
+
+ Date & Date::operator =(const string & s)
+ {
+ if ((s == "now") || (s == "Now") || (s == "NOW")) {
+ long l = time(0);
+ struct tm * p_tm = localtime(&l);
+ _day = p_tm->tm_mday;
+ _month = p_tm->tm_mon + 1;
+ _year = p_tm->tm_year + 1900;
+ _hour = p_tm->tm_hour;
+ _min = p_tm->tm_min;
+ _sec = p_tm->tm_sec;
+
+ } else {
+ char c;
+// istringstream ist(s);
+// ist >> _day >> c
+// >> _month >> c
+// >> _year >> c
+// >> _hour >> c
+// >> _min >> c
+// >> _sec;
+ sscanf(s.c_str(), "%ld/%ld/%ld-%ld:%ld:%ld", &_day, &_month, &_year, &_hour, &_min, &_sec);
+ }
+
+ return *this;
+ }
+
+ string Date::str() const
+ {
+ char buf[64];
+ string datestr;
+
+ // _day to char *
+ sprintf(buf, "%02ld", _day);
+ datestr += buf;
+ datestr += "/";
+
+ // _month to char *
+ sprintf(buf, "%02ld", _month);
+ datestr += buf;
+ datestr += "/";
+
+ // _year to char *
+ sprintf(buf, "%04ld", _year);
+ datestr += buf;
+ datestr += "-";
+
+ // _hour to char *
+ sprintf(buf, "%02ld", _hour);
+ datestr += buf;
+ datestr += ":";
+
+ // _min to char *
+ sprintf(buf, "%02ld", _min);
+ datestr += buf;
+ datestr += ":";
+
+ // _sec to char *
+ sprintf(buf, "%02ld", _sec);
+ datestr += buf;
+
+ return datestr;
+ }
+
+ long Date::epoch() const
+ {
+ struct tm T;
+ T.tm_mday = _day;
+ T.tm_mon = _month - 1;
+ T.tm_year = _year - 1900;
+ T.tm_hour = _hour;
+ T.tm_min = _min;
+ T.tm_sec = _sec;
+ return mktime(&T);
+ }
+
+}
+
+
+// COMMENTS
--- /dev/null
+/*
+ * Date.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Nov 26 14:11:42 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _DATE_H_
+#define _DATE_H_
+
+using namespace std;
+#include <string>
+
+namespace Batch {
+
+ class Date
+ {
+ public:
+ Date(const long l=0);
+ Date(const string s);
+ virtual Date & operator =(long l);
+ virtual Date & operator +(long l);
+ virtual Date & operator -(long l);
+ virtual Date & operator +=(long l);
+ virtual Date & operator -=(long l);
+ virtual Date & operator =(const string & s);
+ virtual string str() const;
+ virtual long epoch() const;
+
+ protected:
+ int _day, _month, _year;
+ int _hour, _min, _sec;
+
+ private:
+
+ };
+
+}
+
+#endif
+
+// COMMENTS
--- /dev/null
+/*
+ * DateType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Nov 26 11:15:34 2003
+ * Projet : Salome 2
+ *
+ */
+extern "C" {
+#include <time.h>
+}
+#include "Batch_DateType.hxx"
+
+namespace Batch {
+
+ // Conversion en chaine
+ string DateType::affiche() const
+ {
+ return _data.str();
+ }
+
+ // Operateur d'affectation
+ DateType & DateType::operator =(const Date & d)
+ {
+ _data = d;
+ return *this;
+ }
+
+ // Conversion en Date
+ DateType::operator Date() const
+ {
+ return _data;
+ }
+
+ // Conversion en long
+ DateType::operator long() const
+ {
+ return _data.epoch();
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * DateType::clone() const
+ {
+ DateType * pD = new DateType(this->_data);
+ assert(pD != 0);
+ return pD;
+ }
+
+}
--- /dev/null
+/*
+ * DateType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Nov 26 11:15:34 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _DATETYPE_H_
+#define _DATETYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+#include "Batch_Date.hxx"
+
+namespace Batch {
+
+ class DateType : public GenericType
+ {
+ public:
+ // Constructeur
+ DateType(const Date & d) : _data(d) {};
+
+ // Conversion en chaine
+ virtual string affiche() const;
+
+ // Operateur d'affectation
+ virtual DateType & operator =(const Date &);
+
+ // Conversion en Date
+ virtual operator Date() const;
+
+ // Conversion en long
+ virtual operator long() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ Date _data;
+
+ private:
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * Environnement.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Oct 16 11:37:47 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_Environnement.hxx"
+
+namespace Batch {
+
+
+}
--- /dev/null
+/*
+ * Environnement.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Oct 16 11:37:47 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _ENVIRONNEMENT_H_
+#define _ENVIRONNEMENT_H_
+
+
+using namespace std;
+#include <string>
+#include <map>
+
+namespace Batch {
+
+ typedef map < string, string > Environnement;
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * FactBatchManager.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2004
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include <sstream>
+#include "Batch_BatchManagerCatalog.hxx"
+#include "Batch_FactBatchManager.hxx"
+#include "utilities.h"
+
+namespace Batch {
+
+ // Constructeur
+ FactBatchManager::FactBatchManager(const string & _t) : type(_t)
+ {
+ BatchManagerCatalog::addFactBatchManager(type.c_str(), this);
+ ostringstream msg;
+ msg << "FactBatchManager of type '" << type << "' inserted into catalog";
+ MESSAGE(msg.str().c_str());
+ }
+
+ // Destructeur
+ FactBatchManager::~FactBatchManager()
+ {
+ // Nothing to do
+ }
+
+ // Accesseur
+ string FactBatchManager::getType() const
+ {
+ return type;
+ }
+
+ string FactBatchManager::__repr__() const
+ {
+ ostringstream oss;
+ oss << "<FactBatchManager of type '" << type << "'>";
+ return oss.str();
+ }
+
+}
--- /dev/null
+/*
+ * FactBatchManager.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2004
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _FACTBATCHMANAGER_H_
+#define _FACTBATCHMANAGER_H_
+
+using namespace std;
+#include <string>
+#include <map>
+
+namespace Batch {
+
+ class BatchManager;
+
+ class FactBatchManager
+ {
+ public:
+ // Constructeur et destructeur
+ FactBatchManager(const string & type);
+ virtual ~FactBatchManager();
+
+ virtual BatchManager * operator() (const char * hostname) const = 0;
+ string getType() const;
+ string __repr__() const;
+
+ protected:
+ string type;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * FactBatchManager_PBS.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2004
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include "Batch_BatchManager_PBS.hxx"
+#include "Batch_FactBatchManager_PBS.hxx"
+#include "utilities.h"
+
+namespace Batch {
+
+ static FactBatchManager_PBS sFBM_PBS;
+
+ // Constructeur
+ FactBatchManager_PBS::FactBatchManager_PBS() : FactBatchManager("PBS")
+ {
+ // Nothing to do
+ }
+
+ // Destructeur
+ FactBatchManager_PBS::~FactBatchManager_PBS()
+ {
+ // Nothing to do
+ }
+
+ // Functor
+ BatchManager_PBS * FactBatchManager_PBS::operator() (const char * hostname) const
+ {
+ MESSAGE("Building new BatchManager_PBS on host '" << hostname << "'");
+ return new BatchManager_PBS(this, hostname);
+ }
+
+
+}
--- /dev/null
+/*
+ * FactBatchManager_PBS.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2004
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _FACTBATCHMANAGER_PBS_H_
+#define _FACTBATCHMANAGER_PBS_H_
+
+using namespace std;
+#include <string>
+#include <map>
+#include "Batch_FactBatchManager.hxx"
+
+namespace Batch {
+
+ class BatchManager_PBS;
+
+ class FactBatchManager_PBS : public FactBatchManager
+ {
+ public:
+ // Constructeur et destructeur
+ FactBatchManager_PBS();
+ virtual ~FactBatchManager_PBS();
+
+ virtual BatchManager_PBS * operator() (const char * hostname) const;
+
+ protected:
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * GenericException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Nov 26 10:15:57 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * GenericException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Nov 26 10:15:56 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _GENERICEXCEPTION_H_
+#define _GENERICEXCEPTION_H_
+
+
+using namespace std;
+#include <string>
+
+namespace Batch {
+
+ class GenericException
+ {
+ public:
+ const string type; // la nature de l'exception
+ const string message; // la raison de l'exception
+
+ // Constructeur
+ GenericException(const string tp = "GenericException", const string ch = "undefined") : type(tp), message(ch) {}
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * GenericType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+
+#include <iostream>
+#include <string>
+#include "Batch_GenericType.hxx"
+
+namespace Batch {
+
+ // nombre total d'objet GenericType et al.
+ int GenericType::_nb = 0;
+
+ // Operateur pour l'affichage sur un stream
+ ostream & operator << (ostream & os, const GenericType & obj)
+ {
+ return os << obj.affiche();
+ }
+
+ // Conversion en chaine
+ string GenericType::affiche() const
+ {
+ return string("(GenericType : si ce message apparait, vous devez avoir un probleme)");
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * GenericType::clone() const
+ {
+ GenericType * pG = new GenericType;
+ assert(pG != 0);
+ return pG;
+ }
+
+}
+
--- /dev/null
+/*
+ * GenericType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _GENERICTYPE_H_
+#define _GENERICTYPE_H_
+
+
+using namespace std;
+#include <iostream>
+#include <string>
+
+namespace Batch {
+
+ class GenericType
+ {
+ public:
+ // Constructeur et destructeur
+ GenericType() { _nb++; }
+ virtual ~GenericType() { _nb--; }
+
+ // Operateur pour l'affichage sur un stream
+ friend ostream & operator << (ostream & os, const GenericType & obj);
+
+ // Conversion en chaine
+ virtual string affiche() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ // Retourne le nombre d'objets GenericType et al.
+ static int getNb() { return _nb; }
+
+ protected:
+
+ private:
+ static int _nb; // nombre total d'objets GenericType et al.
+
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * IntType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_IntType.hxx"
+
+
+namespace Batch {
+
+ // Conversion en chaine
+ string IntType::affiche() const
+ {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << _data;
+ return sst.str();
+ }
+
+ // Operateur d'affectation
+ IntType & IntType::operator =(int i)
+ {
+ _data = i;
+ return *this;
+ }
+
+ // Conversion en int
+ IntType::operator int() const
+ {
+ return this->_data;
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * IntType::clone() const
+ {
+ IntType * pI = new IntType(this->_data);
+ assert(pI != 0);
+ return pI;
+ }
+
+}
--- /dev/null
+/*
+ * IntType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _INTTYPE_H_
+#define _INTTYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+
+namespace Batch {
+
+ class IntType : public GenericType
+ {
+ public:
+ // Constructeur
+ IntType(const int i=0) : _data(i) {}
+
+ // Conversion en chaine
+ virtual string affiche() const;
+
+ // Operateur d'affectation
+ virtual IntType & operator =(int);
+
+ // Conversion en int
+ virtual operator int() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ int _data;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * InvalidArgumentException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Oct 16 16:18:00 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_InvalidArgumentException.hxx"
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * InvalidArgumentException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Oct 16 16:18:00 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _INVALIDARGUMENTEXCEPTION_H_
+#define _INVALIDARGUMENTEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class InvalidArgumentException : public GenericException
+ {
+ public:
+ // Constructeur
+ InvalidArgumentException(string ch = "undefined") : GenericException("InvalidArgumentException", ch) {}
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * InvalidKeyException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Oct 15 10:39:51 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_InvalidKeyException.hxx"
+
+namespace Batch {
+
+}
+
--- /dev/null
+/*
+ * InvalidKeyException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Wed Oct 15 10:39:51 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _INVALIDKEYEXCEPTION_H_
+#define _INVALIDKEYEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class InvalidKeyException : public GenericException
+ {
+ public:
+ // Constructeur
+ InvalidKeyException(string ch = "undefined") : GenericException("InvalidKeyException", ch) {}
+
+ protected:
+
+ private:
+
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * Job.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include "Batch_Job.hxx"
+#include "Batch_Parametre.hxx"
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+
+namespace Batch {
+
+ // Constructeur
+ Job::Job() : _param(), _env()
+ {
+ // Nothing to do
+ }
+
+
+ // Constructeur
+ Job::Job(Parametre param) : _param(param), _env()
+ {
+ // Nothing to do
+ }
+
+
+ // Constructeur
+ Job::Job(Environnement env) : _param(), _env(env)
+ {
+ // Nothing to do
+ }
+
+
+ // Constructeur
+ Job::Job(Parametre param, Environnement env) : _param(param), _env(env)
+ {
+ // Nothing to do
+ }
+
+ // Operateur pour l'affichage sur un stream
+ ostream & operator <<(ostream & os, const Job & job)
+ {
+ return os << job.__str__();
+ }
+
+ // Accesseur
+ Parametre Job::getParametre() const
+ {
+ return _param;
+ }
+
+ // Accesseur
+ void Job::setParametre(const Parametre & param)
+ {
+ _param = param;
+ }
+
+ // Accesseur
+ Environnement Job::getEnvironnement() const
+ {
+ return _env;
+ }
+
+ // Accesseur
+ void Job::setEnvironnement(const Environnement & env)
+ {
+ _env = env;
+ }
+
+
+ // Methode pour l'interfacage avec Python (SWIG) : affichage en Python
+ string Job::__str__() const {
+ //MEDMEM::STRING str;
+ ostringstream str;
+ str << "<Job (" << this << ") :" << endl;
+ str << " Parametre :" << endl;
+ Parametre::const_iterator itp;
+ for(itp=_param.begin(); itp!=_param.end(); itp++) {
+ str << " * " << (*itp).first << " : " << (*itp).second << endl;
+ }
+ str << " Environnement :" << endl;
+ Environnement::const_iterator ite;
+ for(ite=_env.begin(); ite!=_env.end(); ite++) {
+ str << " * " << (*ite).first << " : " << (*ite).second << endl;
+ }
+ str << " >";
+ return str.str();
+ }
+
+
+}
--- /dev/null
+/*
+ * Job.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _JOB_H_
+#define _JOB_H_
+
+
+#include "Batch_Parametre.hxx"
+#include "Batch_Environnement.hxx"
+
+namespace Batch {
+
+ class Job
+ {
+ public:
+ // Constructeurs et destructeur
+ Job();
+ Job(Parametre param);
+ Job(Environnement env);
+ Job(Parametre param, Environnement env);
+ virtual ~Job() {}
+
+ // Operateur pour l'affichage sur un stream
+ friend ostream & operator <<(ostream & os, const Job & job);
+
+ // Accesseurs
+ Parametre getParametre() const;
+ void setParametre(const Parametre &);
+
+ // Accesseurs
+ Environnement getEnvironnement() const;
+ void setEnvironnement(const Environnement &);
+
+ // Methodes pour l'interfacage avec Python (SWIG)
+ // TODO : supprimer ces methodes et transferer leur definitions dans SWIG
+ string __str__() const; // SWIG : affichage en Python
+ string __repr__() const { return __str__(); }; // SWIG : affichage en Python
+
+ protected:
+ Parametre _param; // table des parametres batch du job
+ Environnement _env; // table des variables d'environnement
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * JobId.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include "Batch_JobId.hxx"
+#include "Batch_BatchManager.hxx"
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+
+namespace Batch {
+
+ // Constructeur standard
+ JobId::JobId() : _p_batchmanager(), _reference("undefined")
+ {
+ // Nothing to do
+ }
+
+ // Constructeur avec le pointeur sur le BatchManager associe et avec une reference
+ JobId::JobId(BatchManager * _p_bm, string ref) : _p_batchmanager(_p_bm), _reference(ref)
+ {
+ // Nothing to do
+ }
+
+ // Destructeur
+ JobId::~JobId()
+ {
+ // Nothing to do
+ }
+
+ // Operateur d'affectation entre objets
+ JobId & JobId::operator =(const JobId & jobid)
+ {
+ _p_batchmanager = jobid._p_batchmanager;
+ _reference = jobid._reference;
+
+ return *this;
+ }
+
+ // Constructeur par recopie
+ JobId::JobId(const JobId & jobid) : _p_batchmanager(jobid._p_batchmanager), _reference(jobid._reference)
+ {
+ // Nothing to do
+ }
+
+ // Accesseur pour la reference interne
+ string JobId::getReference() const
+ {
+ return _reference;
+ }
+
+ // Methode pour le controle du job : retire le job du gestionnaire
+ void JobId::deleteJob() const
+ {
+ assert(_p_batchmanager != 0);
+ _p_batchmanager->deleteJob(*this);
+ }
+
+ // Methode pour le controle du job : suspend le job en file d'attente
+ void JobId::holdJob() const
+ {
+ assert(_p_batchmanager != 0);
+ _p_batchmanager->holdJob(*this);
+ }
+
+ // Methode pour le controle du job : relache le job suspendu
+ void JobId::releaseJob() const
+ {
+ assert(_p_batchmanager != 0);
+ _p_batchmanager->releaseJob(*this);
+ }
+
+ // Methode pour le controle du job : modifie le job en file d'attente
+ void JobId::alterJob(const Parametre & param, const Environnement & env) const
+ {
+ assert(_p_batchmanager != 0);
+ _p_batchmanager->alterJob(*this, param, env);
+ }
+
+ // Methode pour le controle du job : modifie le job en file d'attente
+ void JobId::alterJob(const Parametre & param) const
+ {
+ assert(_p_batchmanager != 0);
+ _p_batchmanager->alterJob(*this, param);
+ }
+
+ // Methode pour le controle du job : modifie le job en file d'attente
+ void JobId::alterJob(const Environnement & env) const
+ {
+ assert(_p_batchmanager != 0);
+ _p_batchmanager->alterJob(*this, env);
+ }
+
+ // Methode pour le controle du job : renvoie l'etat du job
+ JobInfo JobId::queryJob() const
+ {
+ assert(_p_batchmanager != 0);
+ return _p_batchmanager->queryJob(*this);
+ }
+
+
+ // Methode pour l'interfacage avec Python (SWIG) : affichage en Python
+ string JobId::__str__() const {
+ //MEDMEM::STRING str;
+ ostringstream str;
+ str << "<JobId (" << this << ") : referenced '" << _reference << "'>";
+ return str.str();
+ }
+
+}
--- /dev/null
+/*
+ * JobId.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _JOBID_H_
+#define _JOBID_H_
+
+
+#include "Batch_JobInfo.hxx"
+#include "Batch_BatchManager.hxx"
+
+namespace Batch {
+
+ class BatchManager;
+
+ class JobId
+ {
+ friend class BatchManager;
+
+ public:
+ // Constructeur standard et destructeur
+ JobId();
+ virtual ~JobId();
+
+ // Constructeur avec le pointeur sur le BatchManager associe et avec une reference
+ JobId(BatchManager *, string ref);
+
+ // Operateur d'affectation entre objets
+ virtual JobId & operator =(const JobId &);
+
+ // Constructeur par recopie
+ JobId(const JobId &);
+
+ // Accesseur pour la reference interne
+ virtual string getReference() const;
+
+ // Methodes pour le controle du job
+ virtual void deleteJob() const; // retire un job du gestionnaire
+ virtual void holdJob() const; // suspend un job en file d'attente
+ virtual void releaseJob() const; // relache un job suspendu
+ virtual void alterJob(const Parametre & param, const Environnement & env) const; // modifie un job en file d'attente
+ virtual void alterJob(const Parametre & param) const; // modifie un job en file d'attente
+ virtual void alterJob(const Environnement & env) const; // modifie un job en file d'attente
+ virtual void setParametre(const Parametre & param) { return alterJob(param); } // modifie un job en file d'attente
+ virtual void setEnvironnement(const Environnement & env) { return alterJob(env); } // modifie un job en file d'attente
+ virtual Batch::JobInfo queryJob() const; // renvoie l'etat du job
+
+ // Methodes pour l'interfacage avec Python (SWIG)
+ // TODO : supprimer ces methodes et transferer leur definitions dans SWIG
+ string __str__() const; // SWIG : affichage en Python
+ string __repr__() const { return __str__(); }; // SWIG : affichage en Python
+
+ protected:
+ BatchManager * _p_batchmanager; // pointeur sur le BatchManager qui controle le job
+ string _reference; // reference du job au sein du BatchManager
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * JobInfo.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 6 10:05:30 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include <iostream>
+#include <string>
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_JobInfo.hxx"
+
+namespace Batch {
+
+ // Destructeur
+ JobInfo::~JobInfo()
+ {
+ // Nothing to do
+ }
+
+
+ // Operateur pour l'affichage sur un stream
+ ostream & operator <<(ostream & os, const JobInfo & ji)
+ {
+ return os << ji.__str__();
+ }
+
+
+ // Methodes pour l'interfacage avec Python (SWIG) : affichage en Python
+ string JobInfo::__str__() const
+ {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "<JobInfo (" << this << ") :" << endl;
+ sst << " ID = " <<_param[ID] << endl;
+
+ sst << " + Parametre :" << endl;
+ Parametre::const_iterator itp;
+ for(itp=_param.begin(); itp!=_param.end(); itp++) {
+ if ( (*itp).first != ID ) {
+ sst << " * " << (*itp).first << " = " << (*itp).second << endl;
+ }
+ }
+
+ sst << " + Environnement :" << endl;
+ Environnement::const_iterator ite;
+ for(ite=_env.begin(); ite!=_env.end(); ite++) {
+ sst << " * " << (*ite).first << " = " << (*ite).second << endl;
+ }
+
+ sst << " >";
+
+ return sst.str();
+ }
+
+ // Accesseur
+ Parametre JobInfo::getParametre() const
+ {
+ return _param;
+ }
+
+ // Accesseur
+ Environnement JobInfo::getEnvironnement() const
+ {
+ return _env;
+ }
+
+
+}
--- /dev/null
+/*
+ * JobInfo.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Thu Nov 6 10:05:30 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _JOBINFO_H_
+#define _JOBINFO_H_
+
+using namespace std;
+#include <iostream>
+#include <string>
+#include "Batch_Parametre.hxx"
+#include "Batch_Environnement.hxx"
+
+namespace Batch {
+
+ class JobInfo
+ {
+ public:
+ // Constructeur standard et destructeur
+ JobInfo() : _param(), _env() {};
+ virtual ~JobInfo();
+
+ // Constructeur par recopie
+ JobInfo(const JobInfo & jinfo) : _param(jinfo._param), _env(jinfo._env) {};
+
+ // Operateur pour l'affichage sur un stream
+ friend ostream & operator <<(ostream & os, const JobInfo & ji);
+
+ // Accesseurs
+ virtual Parametre getParametre() const;
+ virtual Environnement getEnvironnement() const;
+
+ // Methodes pour l'interfacage avec Python (SWIG)
+ // TODO : supprimer ces methodes et transferer leur definitions dans SWIG
+ string __str__() const; // SWIG : affichage en Python
+ string __repr__() const { return __str__(); }; // SWIG : affichage en Python
+
+ protected:
+ Parametre _param; // parametres du job
+ Environnement _env; // variables d'environnement du job
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * JobInfo_PBS.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Fri Nov 21 09:42:06 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include <cstdio>
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_Parametre.hxx"
+#include "Batch_Environnement.hxx"
+#include "Batch_RunTimeException.hxx"
+#include "Batch_JobInfo_PBS.hxx"
+
+namespace Batch {
+
+ // Constructeurs
+ JobInfo_PBS::JobInfo_PBS(struct batch_status * list, bool tobedeleted) : JobInfo()
+ {
+ // On ne considere que le premier element de la liste
+ // Si tout est OK, la liste ne devrait contenir qu'un element
+ // Sinon on leve une exception.
+ struct batch_status * p_job = list;
+ int i;
+ for(i=0; p_job; p_job = p_job->next) i++;
+ if (i == 0) throw RunTimeException("Liste vide (le job est absent de la file)");
+ if (i > 1) {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "JobInfo_PBS::JobInfo_PBS(struct batch_status * list, bool tobedeleted) : la liste contient "
+ << i << " elements" << " (1 seul requis)" << endl;
+ throw RunTimeException(sst.str());
+ }
+ p_job = list;
+
+ // On remplit les membres _param et _env
+
+ if (p_job->name && strlen(p_job->name)) _param[ID] = p_job->name;
+ if (p_job->text && strlen(p_job->text)) _param[TEXT] = p_job->text;
+
+ for(struct attrl * p_attr = p_job->attribs; p_attr; p_attr = p_attr->next) {
+
+ string name, res, value;
+ if (p_attr->name && strlen(p_attr->name)) name = p_attr->name;
+ if (p_attr->resource && strlen(p_attr->resource)) res = p_attr->resource;
+ if (p_attr->value && strlen(p_attr->value)) value = p_attr->value;
+
+ if (name == ATTR_N) {
+ _param[NAME] = value;
+
+ } else if (name == ATTR_owner) {
+ _param[USER] = value;
+
+ } else if (name == ATTR_state) {
+ _param[STATE] = value;
+
+ } else if (name == ATTR_queue) {
+ _param[QUEUE] = value;
+
+ } else if (name == ATTR_A) {
+ _param[ACCOUNT] = value;
+
+ } else if (name == ATTR_M) {
+ _param[MAIL] = value;
+
+ } else if (name == ATTR_c) {
+ if (!strcmp(value.c_str(), CHECKPOINT_UNSPECIFIED)) _param[CHECKPOINT] = 1L;
+ else _param[CHECKPOINT] = 0L;
+
+ } else if (name == ATTR_h) {
+ if (!strcmp(value.c_str(), NO_HOLD)) _param[HOLD] = 0L;
+ else _param[HOLD] = 1L;
+
+ } else if (name == ATTR_ctime) {
+ _param[CREATIONTIME] = atol(value.c_str());
+
+ } else if (name == ATTR_etime) {
+ _param[ELIGIBLETIME] = atol(value.c_str());
+
+ } else if (name == ATTR_mtime) {
+ _param[MODIFICATIONTIME] = atol(value.c_str());
+
+ } else if (name == ATTR_qtime) {
+ _param[QUEUEDTIME] = atol(value.c_str());
+
+ } else if (name == ATTR_exechost) {
+ _param[EXECUTIONHOST] = value;
+
+ } else if (name == ATTR_session) {
+ _param[PID] = atol(value.c_str());
+
+ } else if (name == ATTR_euser) {
+ _param[EUSER] = value;
+
+ } else if (name == ATTR_egroup) {
+ _param[EGROUP] = value;
+
+ } else if (name == ATTR_l) {
+ if (res == "cput") {
+ _param[MAXCPUTIME] = HMStoLong(value);
+
+ } else if (res == "walltime") {
+ _param[MAXWALLTIME] = HMStoLong(value);
+
+ }
+
+ } else if (name == ATTR_used) {
+ if (res == "cput") {
+ _param[USEDCPUTIME] = HMStoLong(value);
+
+ } else if (res == "walltime") {
+ _param[USEDWALLTIME] = HMStoLong(value);
+
+ }
+
+ } else if (name == ATTR_v) {
+ int deb = 0;
+ int pos = 0;
+ bool ok = true;
+
+ while (ok) {
+ pos = value.find(",", deb);
+ string sub = value.substr(deb, pos-deb);
+ deb = pos + 1;
+ if (pos < 0) ok = false;
+
+ int eq = sub.find("=");
+ _env[sub.substr(0, eq)] = sub.substr(eq+1);
+ }
+
+ }
+ }
+
+
+ if (tobedeleted) pbs_statfree(list);
+ }
+
+ // Destructeur
+ JobInfo_PBS::~JobInfo_PBS()
+ {
+ // Nothing to do
+ }
+
+ // Convertit une date HH:MM:SS en secondes
+ long JobInfo_PBS::HMStoLong(const string & s)
+ {
+ long hour, min, sec;
+
+ sscanf( s.c_str(), "%ld:%ld:%ld", &hour, &min, &sec);
+ return ( ( ( hour * 60L ) + min ) * 60L ) + sec;
+ }
+
+ // Methode pour l'interfacage avec Python (SWIG) : affichage en Python
+ string JobInfo_PBS::__str__() const
+ {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "<JobInfo_PBS (" << this << ") :" << endl;
+ sst << " ID = " <<_param[ID] << endl;
+
+ sst << " + Parametre :" << endl;
+ Parametre::const_iterator itp;
+ for(itp=_param.begin(); itp!=_param.end(); itp++) {
+ if ( (*itp).first != ID ) {
+ sst << " * " << (*itp).first << " = " << (*itp).second << endl;
+ }
+ }
+ return sst.str();
+ }
+
+
+}
--- /dev/null
+/*
+ * JobInfo_PBS.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Fri Nov 21 09:42:05 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _JOBINFO_PBS_H_
+#define _JOBINFO_PBS_H_
+
+extern "C" {
+
+#include <pbs_error.h>
+#include <pbs_ifl.h>
+}
+#include <string>
+#include "Batch_RunTimeException.hxx"
+#include "Batch_JobInfo.hxx"
+
+namespace Batch {
+
+ class JobInfo_PBS : public JobInfo
+ {
+ public:
+ // Constructeurs et destructeur
+ JobInfo_PBS() : JobInfo() {};
+ JobInfo_PBS(struct batch_status * stat_list, bool tobedeleted = false);
+ virtual ~JobInfo_PBS();
+
+ // Constructeur par recopie
+ JobInfo_PBS(const JobInfo_PBS & jinfo) : JobInfo(jinfo) {};
+
+ // Methodes pour l'interfacage avec Python (SWIG)
+ // TODO : supprimer ces methodes et transferer leur definitions dans SWIG
+ string __str__() const; // SWIG : affichage en Python
+ string __repr__() const { return __str__(); }; // SWIG : affichage en Python
+
+ protected:
+
+ private:
+ // Convertit une date HH:MM:SS en secondes
+ long HMStoLong(const string &);
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * Job_PBS.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Fri Nov 14 11:00:39 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include <stdio.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include "Batch_Job_PBS.hxx"
+
+namespace Batch {
+
+ // Ajoute un element (name,resource,value) a la liste chainee d'attributs + operateur
+ void Job_PBS::setResourceAttributeOP(struct attropl ** attr_list, const char * attr_name, const char * attr_resource, const char * attr_value)
+ {
+ // L'element (name,resource,value) existe-t-il deja ? si oui ptr != 0
+ struct attropl * ptr = findResourceAttributeOP(*attr_list, attr_name, attr_resource);
+
+ if (!ptr) { // L'element n'existe pas, il faut le creer
+ if (ptr = lastAttributeOP(*attr_list)) { // la liste n'est pas vide
+ ptr->next = new struct attropl;
+ ptr = ptr->next;
+ ptr->next = 0;
+
+ } else { // la liste est completement vide
+ ptr = *attr_list = new struct attropl;
+ ptr->next = 0;
+ }
+
+ // On remplit les champs (name,resource,value)
+ ptr->name = new char[strlen(attr_name) + 1];
+ strncpy(ptr->name, attr_name, strlen(attr_name));
+ ptr->name[strlen(attr_name)] = 0;
+
+ ptr->resource = new char[strlen(attr_resource) + 1];
+ strncpy(ptr->resource, attr_resource, strlen(attr_resource));
+ ptr->resource[strlen(attr_resource)] = 0;
+
+ ptr->value = new char[strlen(attr_value) + 1];
+ strncpy(ptr->value, attr_value, strlen(attr_value));
+ ptr->value[strlen(attr_value)] = 0;
+
+ } else { // L'attribut existe, on change sa valeur
+ delete[] ptr->value; // On efface la valeur precedente
+ ptr->value = new char[strlen(attr_value) + 1];
+ strncpy(ptr->value, attr_value, strlen(attr_value));
+ ptr->value[strlen(attr_value)] = 0;
+
+ }
+ }
+
+
+ // Recherche un element (name,resource,value) dans la liste chainee d'attributs + operateur
+ struct attropl * Job_PBS::findResourceAttributeOP(struct attropl * attr_list, const char * attr_name, const char * attr_resource)
+ {
+ // On parcoure la liste chainee pour trouver l'element dont les champs name et resource coincident
+ struct attropl * ptr = attr_list;
+ while (ptr) {
+ if (!strcmp(ptr->name, attr_name) && !strcmp(ptr->resource, attr_resource)) break;
+ ptr = ptr->next;
+ }
+ return ptr;
+ }
+
+
+ // Recherche le dernier element de la liste chainee d'attributs + operateur
+ struct attropl * Job_PBS::lastAttributeOP(struct attropl * attr_list)
+ {
+ struct attropl * ptr = attr_list;
+ while (ptr && ptr->next) {
+ ptr = ptr->next;
+ }
+ return ptr;
+ }
+
+
+ // Convertit un objet Parametre en liste chainee d'attributs + operateur
+ struct attropl * Job_PBS::ParametreToAttributeOPList(struct attropl ** _p_attr_list, Parametre & P)
+ {
+ Parametre::iterator it;
+ string st_second;
+ for(it=P.begin(); it!=P.end(); it++) {
+ if ( (*it).first == ACCOUNT ) {
+ st_second = (*it).second.str();
+ setResourceAttributeOP(_p_attr_list, ATTR_A, "", st_second.c_str());
+
+
+ } else if ( (*it).first == CHECKPOINT ) {
+ setResourceAttributeOP(_p_attr_list, ATTR_c, "", "u");
+
+
+ } else if ( (*it).first == CKPTINTERVAL ) {
+ // Not significant
+
+ } else if ( (*it).first == EXECUTABLE ) {
+ // Already done
+
+ } else if ( (*it).first == HOLD ) {
+ if (static_cast< long >((*it).second))
+ setResourceAttributeOP(_p_attr_list, ATTR_h, "", USER_HOLD);
+ else
+ setResourceAttributeOP(_p_attr_list, ATTR_h, "", NO_HOLD);
+
+ } else if ( (*it).first == INFILE ) {
+ Versatile V = (*it).second;
+ Versatile::iterator Vit;
+
+ string sep = "";
+ string stagein;
+
+ for(Vit=V.begin(); Vit!=V.end(); Vit++, sep=",") {
+ CoupleType cpt = *static_cast< CoupleType * >(*Vit);
+ Couple cp = cpt;
+ string local = cp.getLocal();
+ string remote = cp.getRemote();
+
+ // ATTENTION : les notions de fichier "local" ou "remote" sont inverses de celle de PBS qui a un point de vue serveur et non pas utilisateur
+ stagein += sep + remote + "@" + local;
+ }
+
+ if (stagein.size())
+ setResourceAttributeOP(_p_attr_list, ATTR_stagein, "", stagein.c_str());
+
+
+ } else if ( (*it).first == MAIL ) {
+ st_second = (*it).second.str();
+ setResourceAttributeOP(_p_attr_list, ATTR_M, "", st_second.c_str());
+
+ } else if ( (*it).first == MAXCPUTIME ) {
+ char attr_value[32];
+ long secondes = (*it).second;
+ long heures = secondes / 3600L;
+ long minutes = (secondes - 3600L * heures) / 60L;
+ secondes = secondes % 60L;
+ sprintf(attr_value, "%02ld:%02ld:%02ld", heures, minutes, secondes);
+
+ setResourceAttributeOP(_p_attr_list, ATTR_l, "cput", attr_value);
+
+
+ } else if ( (*it).first == MAXDISKSIZE ) {
+
+ } else if ( (*it).first == MAXRAMSIZE ) {
+
+ } else if ( (*it).first == MAXWALLTIME ) {
+ char attr_value[32];
+ long secondes = (*it).second;
+ long heures = secondes / 3600L;
+ long minutes = (secondes - 3600L * heures) / 60L;
+ secondes = secondes % 60L;
+ sprintf(attr_value, "%02ld:%02ld:%02ld", heures, minutes, secondes);
+
+ setResourceAttributeOP(_p_attr_list, ATTR_l, "walltime", attr_value);
+
+
+ } else if ( (*it).first == NAME ) {
+ st_second = (*it).second.str();
+ setResourceAttributeOP(_p_attr_list, ATTR_N, "", st_second.c_str());
+
+
+ } else if ( (*it).first == OUTFILE ) {
+ Versatile V = (*it).second;
+ Versatile::iterator Vit;
+
+ string sep = "";
+ string stageout;
+
+ for(Vit=V.begin(); Vit!=V.end(); Vit++, sep=",") {
+ CoupleType cpt = *static_cast< CoupleType * >(*Vit);
+ Couple cp = cpt;
+ string local = cp.getLocal();
+ string remote = cp.getRemote();
+
+ if (remote == "stdout")
+ setResourceAttributeOP(_p_attr_list, ATTR_o, "", local.c_str());
+
+ else if (remote == "stderr")
+ setResourceAttributeOP(_p_attr_list, ATTR_e, "", local.c_str());
+
+ else
+ // ATTENTION : les notions de fichier "local" ou "remote" sont inverses de celle de PBS qui a un point de vue serveur et non pas utilisateur
+ stageout += sep + remote + "@" + local;
+ }
+
+ if (stageout.size())
+ setResourceAttributeOP(_p_attr_list, ATTR_stageout, "", stageout.c_str());
+
+ } else if ( (*it).first == QUEUE ) {
+ // Already done
+
+ } else if ( (*it).first == STARTDATE ) {
+
+ } else if ( (*it).first == TMPDIR ) {
+
+ } else if ( (*it).first == USER ) {
+ st_second = (*it).second.str();
+ setResourceAttributeOP(_p_attr_list, ATTR_u, "", st_second.c_str());
+
+ }
+ }
+ return *_p_attr_list;
+ }
+
+
+ // Convertit un objet Environnement en liste chainee d'attributs + operateur
+ struct attropl * Job_PBS::EnvironnementToAttributeOPList(struct attropl ** _p_attr_list, Environnement & E)
+ {
+ Environnement::iterator it;
+ for(it=E.begin(); it!=E.end(); it++) {
+ setResourceAttributeOP(_p_attr_list, ATTR_v, (*it).first.c_str(), ( (*it).first + "=" + (*it).second ).c_str());
+ }
+ return *_p_attr_list;
+ }
+
+
+ // Ajoute les variables d'environnement presentes dans tout job PBS
+ void Job_PBS::addPBSEnvironnement(Environnement & E)
+ {
+ char * c;
+
+ c = getenv("HOME");
+ if (c) E["PBS_O_HOME"] = c;
+
+ c = getenv("LANG");
+ if (c) E["PBS_O_LANG"] = c;
+
+ c = getenv("LOGNAME");
+ if (c) E["PBS_O_LOGNAME"] = c;
+
+ c = getenv("PATH");
+ if (c) E["PBS_O_PATH"] = c;
+
+ c = getenv("LD_LIBRARY_PATH");
+ if (c) E["PBS_O_LD_LIBRARY_PATH"] = c;
+
+ c = getenv("MAIL");
+ if (c) E["PBS_O_MAIL"] = c;
+
+ c = getenv("SHELL");
+ if (c) E["PBS_O_SHELL"] = c;
+
+ c = getenv("TZ");
+ if (c) E["PBS_O_TZ"] = c;
+
+ /* Recuperation du working directory */
+ size_t size = 256;
+ char * buf = 0;
+ char * rc = 0;
+ do {
+ if (buf) delete[] buf;
+ buf = new char[size];
+ rc = getcwd(buf, size);
+ size += size;
+ } while (!rc);
+ E["PBS_O_WORKDIR"] = buf;
+ delete[] buf;
+ }
+
+
+ // Ajoute un element (name,resource,value) a la liste chainee d'attributs
+ void Job_PBS::setResourceAttribute(struct attrl ** attr_list, const char * attr_name, const char * attr_resource, const char * attr_value)
+ {
+ // L'element (name,resource,value) existe-t-il deja ? si oui ptr != 0
+ struct attrl * ptr = findResourceAttribute(*attr_list, attr_name, attr_resource);
+
+ if (!ptr) { // L'attribut n'existe pas, il faut le creer
+ if (ptr = lastAttribute(*attr_list)) { // la liste n'est pas vide
+ ptr->next = new struct attrl;
+ ptr = ptr->next;
+ ptr->next = 0;
+
+ } else { // la liste est completement vide
+ ptr = *attr_list = new struct attrl;
+ ptr->next = 0;
+ }
+
+ // On remplit les champs (name,resource,value)
+ ptr->name = new char[strlen(attr_name) + 1];
+ strncpy(ptr->name, attr_name, strlen(attr_name));
+ ptr->name[strlen(attr_name)] = 0;
+
+ ptr->resource = new char[strlen(attr_resource) + 1];
+ strncpy(ptr->resource, attr_resource, strlen(attr_resource));
+ ptr->resource[strlen(attr_resource)] = 0;
+
+ ptr->value = new char[strlen(attr_value) + 1];
+ strncpy(ptr->value, attr_value, strlen(attr_value));
+ ptr->value[strlen(attr_value)] = 0;
+
+ } else { // L'attribut existe, on change sa valeur
+ delete[] ptr->value; // On efface la valeur precedente
+ ptr->value = new char[strlen(attr_value) + 1];
+ strncpy(ptr->value, attr_value, strlen(attr_value));
+ ptr->value[strlen(attr_value)] = 0;
+
+ }
+ }
+
+ // Recherche un element (name,resource,value) dans la liste chainee d'attributs
+ struct attrl * Job_PBS::findResourceAttribute(struct attrl * attr_list, const char * attr_name, const char * attr_resource)
+ {
+ // On parcoure la liste chainee pour trouver l'element dont les champs name et resource coincident
+ struct attrl * ptr = attr_list;
+ while (ptr) {
+ if (!strcmp(ptr->name, attr_name) && !strcmp(ptr->resource, attr_resource)) break;
+ ptr = ptr->next;
+ }
+ return ptr;
+ }
+
+
+ // Recherche le dernier element de la liste chainee d'attributs
+ struct attrl * Job_PBS::lastAttribute(struct attrl * attr_list)
+ {
+ struct attrl * ptr = attr_list;
+ while (ptr && ptr->next) {
+ ptr = ptr->next;
+ }
+ return ptr;
+ }
+
+
+ // Constructeur
+ Job_PBS::Job_PBS(const Job & job) : _p_attropl(0), _p_attrl(0), _script(0), _destination(0)
+ {
+ Parametre P = job.getParametre();
+ Parametre::iterator it;
+
+ // On extrait de l'objet Parametre le champ EXECUTABLE qui deviendra le script PBS
+ if ( (it=P.find(EXECUTABLE)) != P.end()) {
+ Versatile V = (*it).second;
+ string st_exe = V.str();
+ const char * exe = st_exe.c_str();
+ int lg = strlen(exe);
+ _script = new char[lg + 1];
+ for (int ii=0; ii<lg+1; ii++) _script[ii] = 0;
+ strcpy(_script, exe);
+ _script[lg] = 0;
+
+ } else {
+ _script = new char[1];
+ _script[0] = 0;
+ }
+
+ // On extrait de l'objet Parametre le champ QUEUE qui deviendra la destination
+ if ( (it=P.find(QUEUE)) != P.end()) {
+ Versatile V = (*it).second;
+ string st_dest = V.str();
+ const char * dest = st_dest.c_str();
+ _destination = new char[strlen(dest) + 2 + 1];
+ _destination[0] = 0;
+ strcat(_destination, dest);
+ _destination[strlen(dest)] = 0;
+ } else {
+ _destination = new char[1];
+ _destination[0] = 0;
+ }
+
+ // On convertit les objets Parametre et Environnement en liste chainee d'attributs + operateur
+ Environnement E = job.getEnvironnement();
+ addPBSEnvironnement(E);
+
+ _p_attropl = ParametreToAttributeOPList(&_p_attropl, P);
+ _p_attropl = EnvironnementToAttributeOPList(&_p_attropl, E);
+
+ }
+
+
+ // Destructeur
+ Job_PBS::~Job_PBS()
+ {
+ // On detruit la liste chainee d'attributs + operateur
+ struct attropl * current_p_attropl = _p_attropl;
+ while (current_p_attropl) {
+ struct attropl * next = current_p_attropl->next;
+ delete[] current_p_attropl->name;
+ delete[] current_p_attropl->resource;
+ delete[] current_p_attropl->value;
+ delete current_p_attropl;
+ current_p_attropl = next;
+ }
+
+ // On detruit la liste chainee d'attributs
+ struct attrl * current_p_attrl = _p_attrl;
+ while (current_p_attrl) {
+ struct attrl * next = current_p_attrl->next;
+ delete[] current_p_attrl->name;
+ delete[] current_p_attrl->resource;
+ delete[] current_p_attrl->value;
+ delete current_p_attrl;
+ current_p_attrl = next;
+ }
+
+ // On detruit les champs alloues
+ delete[] _script;
+ delete[] _destination;
+ }
+
+
+ // Accesseur
+ struct attropl * Job_PBS::getAttributesOP()
+ {
+ return _p_attropl;
+ }
+
+ // Accesseur
+ // Cette methode sert pour les pbs_alter de PBS
+ // Pbs_alter est buggé par rapport a la specification ers_all.ps car les
+ // variables d'environnement ne sont pas supportees (ATTR_v)
+ struct attrl * Job_PBS::getAttributes()
+ {
+ if (_p_attrl == 0) {
+
+ // On remplit la structure attrl a partir de la strucuture attropl
+ // (elles ne different que par le parametre op, mais elles ne sont pas interchangeables
+ // dans les appels)
+
+ struct attropl * current_p_attropl = _p_attropl;
+ while (current_p_attropl) {
+ if (strcmp(current_p_attropl->name, ATTR_v)) // Bug fix for ATTR_v
+ setResourceAttribute(&_p_attrl,
+ current_p_attropl->name,
+ current_p_attropl->resource,
+ current_p_attropl->value);
+
+ current_p_attropl = current_p_attropl->next;
+ }
+
+ }
+
+ return _p_attrl;
+ }
+
+ // Accesseur
+ char * Job_PBS::getScript()
+ {
+ return _script;
+ }
+
+ // Accesseur
+ char * Job_PBS::getDestination()
+ {
+ return _destination;
+ }
+
+}
--- /dev/null
+/*
+ * Job_PBS.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Fri Nov 14 11:00:39 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _JOB_PBS_H_
+#define _JOB_PBS_H_
+
+extern "C" {
+
+#include <pbs_error.h>
+#include <pbs_ifl.h>
+}
+#include "Batch_Job.hxx"
+
+namespace Batch {
+
+ class Job_PBS
+ {
+ public:
+ // Constructeur et destructeur
+ Job_PBS(const Job & job);
+ virtual ~Job_PBS();
+
+ // Accesseurs
+ struct attropl * getAttributesOP();
+ struct attrl * getAttributes();
+ char * getScript();
+ char * getDestination();
+
+ protected:
+ struct attropl * _p_attropl; // liste chainee d'attributs + operateur
+ struct attrl * _p_attrl; // liste chainee d'attributs
+ char * _script; // chemin d'acces au script du job
+ char * _destination; // queue dans laquelle le job est soumis
+
+ private:
+ // Ajoute un element (name,resource,value) a la liste chainee d'attributs + operateur
+ void setResourceAttributeOP(struct attropl ** attr_list, const char * attr_name, const char * attr_resource, const char * attr_value);
+
+ // Recherche un element (name,resource,value) dans la liste chainee d'attributs + operateur
+ struct attropl * findResourceAttributeOP(struct attropl * attr_list, const char * attr_name, const char * attr_resource);
+
+ // Recherche le dernier element de la liste chainee d'attributs + operateur
+ struct attropl * lastAttributeOP(struct attropl * attr_list);
+
+ // Convertit un objet Parametre en liste chainee d'attributs + operateur
+ struct attropl * ParametreToAttributeOPList(struct attropl ** _p_attr_list, Parametre & param);
+
+ // Convertit un objet Environnement en liste chainee d'attributs + operateur
+ struct attropl * EnvironnementToAttributeOPList(struct attropl ** _p_attr_list, Environnement & env);
+
+ // Ajoute les variables d'environnement presentes dans tout job PBS
+ void addPBSEnvironnement(Environnement & E);
+
+
+ // Ajoute un element (name,resource,value) a la liste chainee d'attributs
+ void setResourceAttribute(struct attrl ** attr_list, const char * attr_name, const char * attr_resource, const char * attr_value);
+
+ // Recherche un element (name,resource,value) dans la liste chainee d'attributs
+ struct attrl * findResourceAttribute(struct attrl * attr_list, const char * attr_name, const char * attr_resource);
+
+ // Recherche le dernier element de la liste chainee d'attributs
+ struct attrl * lastAttribute(struct attrl * attr_list);
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * ListIsFullException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include "Batch_ListIsFullException.hxx"
+
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * ListIsFullException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _LISTISFULLEXCEPTION_H_
+#define _LISTISFULLEXCEPTION_H_
+
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class ListIsFullException : public GenericException
+ {
+ public:
+ // Constructeur
+ ListIsFullException(string ch = "undefined") : GenericException("ListIsFullException", ch) {}
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * LongType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_LongType.hxx"
+
+namespace Batch {
+
+ // Conversion en chaine
+ string LongType::affiche() const
+ {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << _data;
+ return sst.str();
+ }
+
+ // Operateur d'affectation
+ LongType & LongType::operator =(long l)
+ {
+ _data = l;
+ return *this;
+ }
+
+ // Conversion en long
+ LongType::operator long() const
+ {
+ return this->_data;
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * LongType::clone() const
+ {
+ LongType * pL = new LongType(this->_data);
+ assert(pL != 0);
+ return pL;
+ }
+
+}
--- /dev/null
+/*
+ * LongType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _LONGTYPE_H_
+#define _LONGTYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+
+namespace Batch {
+
+ class LongType : public GenericType
+ {
+ public:
+ // Constructeur
+ LongType(const long l=0L) : _data(l) {}
+
+ // Conversion en chaine
+ virtual string affiche() const;
+
+ // Operateur d'affectation
+ virtual LongType & operator =(long);
+
+ // Conversion en long
+ virtual operator long() const;
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ long _data;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * MapKey.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Oct 14 14:00:30 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include <string>
+#include "Batch_MapKey.hxx"
+
+namespace Batch {
+
+
+}
+
+
+// COMMENTS
--- /dev/null
+/*
+ * MapKey.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Oct 14 14:00:29 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _MAPKEY_H_
+#define _MAPKEY_H_
+
+
+using namespace std;
+#include <string>
+
+namespace Batch {
+
+ // une classe privee pour les differents types
+ // ces types ne peuvent pas etre redefinis
+ class MapKey : public string
+ {
+ private:
+ friend class Parametre; // seule la classe Parametre peut creer des MapKey
+ MapKey() : string() {}
+ MapKey(const MapKey & mk, size_type pos, size_type npos) : string(mk, pos, npos) {}
+ MapKey(const char * s, size_type n) : string(s, n) {}
+ MapKey(const char * s) : string(s) {}
+ MapKey(size_type n, char c) : string(n, c) {}
+#ifdef __STL_MEMBER_TEMPLATES
+ template<class InputIterator>
+ MapKey(InputIterator __begin, InputIterator __end) : string(__begin, __end) {}
+#else
+ MapKey(const_iterator __begin, const_iterator __end) : string(__begin, __end) {}
+#endif
+
+ public:
+ MapKey(const MapKey & mk) : string(mk) {}
+
+ };
+
+}
+
+#endif
+
+// COMMENTS
--- /dev/null
+/*
+ * NotYetImplementedException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Nov 25 11:35:07 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_NotYetImplementedException.hxx"
+
+namespace Batch {
+
+}
+
--- /dev/null
+/*
+ * NotYetImplementedException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Nov 25 11:35:07 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _NOTYETIMPLEMENTEDEXCEPTION_H_
+#define _NOTYETIMPLEMENTEDEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class NotYetImplementedException : public GenericException
+ {
+ public:
+ // Constructeur
+ NotYetImplementedException(string ch = "undefined") : GenericException("NotYetImplementedException", ch) {}
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * Parametre.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <map>
+#include "Batch_Versatile.hxx"
+#include "Batch_InvalidKeyException.hxx"
+#include "Batch_Parametre.hxx"
+
+// Definition des membres constants statiques
+// Definition des noms globaux pour les clefs en tant que references
+// TODO : supprimer les declarations statiques des clefs de la map
+def_static_MapKey(ACCOUNT);
+def_static_MapKey(CHECKPOINT);
+def_static_MapKey(CKPTINTERVAL);
+def_static_MapKey(CREATIONTIME);
+def_static_MapKey(EGROUP);
+def_static_MapKey(ELIGIBLETIME);
+def_static_MapKey(EUSER);
+def_static_MapKey(EXECUTABLE);
+def_static_MapKey(EXECUTIONHOST);
+def_static_MapKey(HOLD);
+def_static_MapKey(ID);
+def_static_MapKey(INFILE);
+def_static_MapKey(MAIL);
+def_static_MapKey(MAXCPUTIME);
+def_static_MapKey(MAXDISKSIZE);
+def_static_MapKey(MAXRAMSIZE);
+def_static_MapKey(MAXWALLTIME);
+def_static_MapKey(MODIFICATIONTIME);
+def_static_MapKey(NAME);
+def_static_MapKey(OUTFILE);
+def_static_MapKey(PID);
+def_static_MapKey(QUEUE);
+def_static_MapKey(QUEUEDTIME);
+def_static_MapKey(SERVER);
+def_static_MapKey(STARTDATE);
+def_static_MapKey(STATE);
+def_static_MapKey(TEXT);
+def_static_MapKey(TMPDIR);
+def_static_MapKey(USEDCPUTIME);
+def_static_MapKey(USEDDISKSIZE);
+def_static_MapKey(USEDRAMSIZE);
+def_static_MapKey(USEDWALLTIME);
+def_static_MapKey(USER);
+
+namespace Batch {
+
+ // Constructeur standard
+ // La map interne TypeMap possede les memes clefs que la map principale, mais les
+ // valeurs associees contiennent le type des clefs de la map principale ainsi que
+ // le nombre de valeurs autorisees dans l'objet Versatile (0=nombre quelconque,
+ // sinon valeur precisee)
+ Parametre::Parametre() : map< string, Versatile >()
+ {
+ TypeMap[ACCOUNT].type = STRING;
+ TypeMap[ACCOUNT].maxelem = 1;
+
+ TypeMap[CHECKPOINT].type = LONG;
+ TypeMap[CHECKPOINT].maxelem = 1;
+
+ TypeMap[CKPTINTERVAL].type = LONG;
+ TypeMap[CKPTINTERVAL].maxelem = 1;
+
+ TypeMap[CREATIONTIME].type = LONG;
+ TypeMap[CREATIONTIME].maxelem = 1;
+
+ TypeMap[EGROUP].type = STRING;
+ TypeMap[EGROUP].maxelem = 1;
+
+ TypeMap[ELIGIBLETIME].type = LONG;
+ TypeMap[ELIGIBLETIME].maxelem = 1;
+
+ TypeMap[EUSER].type = STRING;
+ TypeMap[EUSER].maxelem = 1;
+
+ TypeMap[EXECUTABLE].type = STRING;
+ TypeMap[EXECUTABLE].maxelem = 1;
+
+ TypeMap[EXECUTIONHOST].type = STRING;
+ TypeMap[EXECUTIONHOST].maxelem = 0;
+
+ TypeMap[HOLD].type = LONG;
+ TypeMap[HOLD].maxelem = 1;
+
+ TypeMap[ID].type = STRING;
+ TypeMap[ID].maxelem = 1;
+
+ TypeMap[INFILE].type = COUPLE;
+ TypeMap[INFILE].maxelem = 0;
+
+ TypeMap[MAIL].type = STRING;
+ TypeMap[MAIL].maxelem = 1;
+
+ TypeMap[MAXCPUTIME].type = LONG;
+ TypeMap[MAXCPUTIME].maxelem = 1;
+
+ TypeMap[MAXDISKSIZE].type = LONG;
+ TypeMap[MAXDISKSIZE].maxelem = 1;
+
+ TypeMap[MAXRAMSIZE].type = LONG;
+ TypeMap[MAXRAMSIZE].maxelem = 1;
+
+ TypeMap[MAXWALLTIME].type = LONG;
+ TypeMap[MAXWALLTIME].maxelem = 1;
+
+ TypeMap[MODIFICATIONTIME].type = LONG;
+ TypeMap[MODIFICATIONTIME].maxelem = 1;
+
+ TypeMap[NAME].type = STRING;
+ TypeMap[NAME].maxelem = 1;
+
+ TypeMap[OUTFILE].type = COUPLE;
+ TypeMap[OUTFILE].maxelem = 0;
+
+ TypeMap[PID].type = LONG;
+ TypeMap[PID].maxelem = 1;
+
+ TypeMap[QUEUE].type = STRING;
+ TypeMap[QUEUE].maxelem = 1;
+
+ TypeMap[QUEUEDTIME].type = LONG;
+ TypeMap[QUEUEDTIME].maxelem = 1;
+
+ TypeMap[SERVER].type = STRING;
+ TypeMap[SERVER].maxelem = 1;
+
+ TypeMap[STARTDATE].type = LONG;
+ TypeMap[STARTDATE].maxelem = 1;
+
+ TypeMap[STATE].type = STRING;
+ TypeMap[STATE].maxelem = 1;
+
+ TypeMap[TEXT].type = STRING;
+ TypeMap[TEXT].maxelem = 1;
+
+ TypeMap[TMPDIR].type = STRING;
+ TypeMap[TMPDIR].maxelem = 1;
+
+ TypeMap[USEDCPUTIME].type = LONG;
+ TypeMap[USEDCPUTIME].maxelem = 1;
+
+ TypeMap[USEDDISKSIZE].type = LONG;
+ TypeMap[USEDDISKSIZE].maxelem = 1;
+
+ TypeMap[USEDRAMSIZE].type = LONG;
+ TypeMap[USEDRAMSIZE].maxelem = 1;
+
+ TypeMap[USEDWALLTIME].type = LONG;
+ TypeMap[USEDWALLTIME].maxelem = 1;
+
+ TypeMap[USER].type = STRING;
+ TypeMap[USER].maxelem = 1;
+ }
+
+ // Operateur de recherche dans la map
+ // Cet operateur agit sur les objets NON CONSTANTS, il autorise la modification de
+ // la valeur associée à la clef car il retourne une reference non constante
+ Versatile & Parametre::operator [] (const string & mk)
+ {
+ // On controle que la clef est valide
+ if (TypeMap.find(mk) == TypeMap.end()) throw InvalidKeyException(mk.c_str());
+
+ // On recherche la valeur associee...
+ Versatile & V = map< string, Versatile >::operator [] (mk);
+
+ // ... et on l'initialise systematiquement
+ // ATTENTION : si un probleme de type survient (ie, on stocke une valeur d'un type
+ // different de celui inscrit dans TypeMap) une exception TypeMismatchException est
+ // levee
+ V.setName(mk);
+ V.setType(TypeMap[mk].type);
+ V.setMaxSize(TypeMap[mk].maxelem);
+
+ return V;
+ }
+
+ // Operateur de recherche dans la map
+ // Cet operateur agit sur les objets CONSTANTS
+ const Versatile & Parametre::operator [] (const string & mk) const
+ {
+ // On controle que la clef est valide
+ if (TypeMap.find(mk) == TypeMap.end()) throw InvalidKeyException(mk.c_str());
+
+ // On recherche la valeur associee
+ Parametre::const_iterator it = find(mk);
+ const Versatile & V = (*it).second;
+
+ return V;
+ }
+
+ // Operateur d'affectation
+ Parametre & Parametre::operator =(const Parametre & PM)
+ {
+ // On ne reaffecte pas l'objet a lui-meme, sinon aie, aie, aie
+ if (this == &PM) return *this;
+
+ // On efface toute la map
+ erase(begin(), end());
+
+ // On recopie la map interne
+ // Meme si cela ne sert a rien pour le moment car les maps internes sont identiques,
+ // il n'est pas exclu que dans un avenir proche elles puissent etre differentes
+ (*this).TypeMap = PM.TypeMap;
+
+ // On recree la structure interne de la map avec les valeurs de celle passee en argument
+ Parametre::const_iterator it;
+ for(it=PM.begin(); it!=PM.end(); it++)
+ insert(make_pair( (*it).first ,
+ Versatile( (*it).second)
+ ) );
+
+ return *this;
+ }
+
+ // Constructeur par recopie
+ Parametre::Parametre(const Parametre & PM)
+ {
+ // inutile car l'objet est vierge : il vient d'etre cree
+ // On efface toute la map
+ // erase(begin(), end());
+
+ // On recopie la map interne
+ (*this).TypeMap = PM.TypeMap;
+
+ // On cree la structure interne de la map avec les valeurs de celle passee en argument
+ Parametre::const_iterator it;
+ for(it=PM.begin();
+ it!=PM.end();
+ it++)
+ insert(
+ make_pair(
+ (*it).first ,
+ Versatile( (*it).second)
+ ) );
+ }
+
+ // map< string, TypeParam > Parametre::getTypeMap() const
+ // {
+ // return TypeMap;
+ // }
+
+}
--- /dev/null
+/*
+ * Parametre.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _PARAMETRE_H_
+#define _PARAMETRE_H_
+
+using namespace std;
+#include <map>
+#include <string>
+#include "Batch_InvalidKeyException.hxx"
+#include "Batch_Versatile.hxx"
+
+
+// Ces macros permettent de simplifier l'ajout de nouvelles
+// clefs dans la map Parametre
+// TODO : remplacer ce mecanisme statique par la lecture
+// TODO : d'une descrption dans un fichier exterieur (genre XML)
+
+#define def_extern_MapKey(mk) extern const string & mk;
+#define def_static_MapKey(mk) const string Batch::Parametre::mk(#mk); \
+ const string & mk = Batch::Parametre::mk;
+
+namespace Batch {
+
+ class Parametre : public map< string, Versatile >
+ {
+ public:
+ // Constructeur standard
+ Parametre();
+
+ // Constructeur par recopie
+ Parametre::Parametre(const Parametre & PM);
+
+ // Operateur de recherche dans la map
+ Versatile & operator [] (const string &);
+ const Versatile & operator [] (const string &) const;
+
+ // Operateur d'affectation
+ Parametre & operator =(const Parametre & PM);
+
+ // Declarations statique des clefs de la map
+ // TODO : supprimer les declarations statiques des clefs de la map
+ static const string ACCOUNT;
+ static const string CHECKPOINT;
+ static const string CKPTINTERVAL;
+ static const string CREATIONTIME;
+ static const string EGROUP;
+ static const string ELIGIBLETIME;
+ static const string EUSER;
+ static const string EXECUTABLE;
+ static const string EXECUTIONHOST;
+ static const string HOLD;
+ static const string ID;
+ static const string INFILE;
+ static const string MAIL;
+ static const string MAXCPUTIME;
+ static const string MAXDISKSIZE;
+ static const string MAXRAMSIZE;
+ static const string MAXWALLTIME;
+ static const string MODIFICATIONTIME;
+ static const string NAME;
+ static const string OUTFILE;
+ static const string PID;
+ static const string QUEUE;
+ static const string QUEUEDTIME;
+ static const string SERVER;
+ static const string STARTDATE;
+ static const string STATE;
+ static const string TEXT;
+ static const string TMPDIR;
+ static const string USEDCPUTIME;
+ static const string USEDDISKSIZE;
+ static const string USEDRAMSIZE;
+ static const string USEDWALLTIME;
+ static const string USER;
+
+ protected:
+ map< string, TypeParam > TypeMap; // map interne servant a controler le type de la valeur associee a chaque clef
+
+ private:
+
+ };
+
+}
+
+def_extern_MapKey(ACCOUNT);
+def_extern_MapKey(CHECKPOINT);
+def_extern_MapKey(CKPTINTERVAL);
+def_extern_MapKey(CREATIONTIME);
+def_extern_MapKey(EGROUP);
+def_extern_MapKey(ELIGIBLETIME);
+def_extern_MapKey(EUSER);
+def_extern_MapKey(EXECUTABLE);
+def_extern_MapKey(EXECUTIONHOST);
+def_extern_MapKey(HOLD);
+def_extern_MapKey(ID);
+def_extern_MapKey(INFILE);
+def_extern_MapKey(MAIL);
+def_extern_MapKey(MAXCPUTIME);
+def_extern_MapKey(MAXDISKSIZE);
+def_extern_MapKey(MAXRAMSIZE);
+def_extern_MapKey(MAXWALLTIME);
+def_extern_MapKey(MODIFICATIONTIME);
+def_extern_MapKey(NAME);
+def_extern_MapKey(OUTFILE);
+def_extern_MapKey(PID);
+def_extern_MapKey(QUEUE);
+def_extern_MapKey(QUEUEDTIME);
+def_extern_MapKey(SERVER);
+def_extern_MapKey(STARTDATE);
+def_extern_MapKey(STATE);
+def_extern_MapKey(TEXT);
+def_extern_MapKey(TMPDIR);
+def_extern_MapKey(USEDCPUTIME);
+def_extern_MapKey(USEDDISKSIZE);
+def_extern_MapKey(USEDRAMSIZE);
+def_extern_MapKey(USEDWALLTIME);
+def_extern_MapKey(USER);
+
+#endif
--- /dev/null
+/*
+ * PyVersatile.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Mon Oct 13 12:01:12 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include <string>
+#include <Python.h>
+#include "Batch_TypeMismatchException.hxx"
+#include "Batch_ListIsFullException.hxx"
+#include "Batch_InvalidArgumentException.hxx"
+#include "Batch_PyVersatile.hxx"
+
+namespace Batch {
+
+ // Constructeur a partir d'un objet Versatile
+ PyVersatile::PyVersatile(const Versatile & V) : Versatile(V)
+ {
+ // Nothing to do
+ }
+
+
+ // Constructeur a partir d'un PyObject
+ // Les objets autorises sont les strings et les ints,
+ // ainsi que les listes de strings
+ PyVersatile::PyVersatile(const PyObject * PyO) throw(TypeMismatchException, ListIsFullException, InvalidArgumentException) : Versatile()
+ {
+ PyObject * _PyO = const_cast<PyObject *>(PyO);
+
+ if (PyList_Check(_PyO)) { // c'est une liste
+ _maxsize = PyList_Size(_PyO);
+ for(int i=0; i<_maxsize; i++) {
+ PyObject * val = PyList_GetItem(_PyO, i);
+ if (PyString_Check(val)) {
+ *this += PyString_AsString(val);
+
+ } else if (PyTuple_Check(val) &&
+ (PyTuple_Size(val) == 2) &&
+ PyString_Check( PyTuple_GetItem(val,0) ) &&
+ PyString_Check( PyTuple_GetItem(val,1) ) ) {
+ *this += Couple( PyString_AsString( PyTuple_GetItem(val,0) ),
+ PyString_AsString( PyTuple_GetItem(val,1) )
+ );
+
+ } else {
+ PyErr_SetString(PyExc_RuntimeWarning, "PyVersatile::PyVersatile(const PyObject * PyO) : invalid PyObject");
+ }
+ }
+
+ } else if (PyString_Check(_PyO)) { // c'est une string
+ const char * s = PyString_AsString(_PyO);
+ Versatile V = string(s);
+ *this = V;
+
+ } else if (PyInt_Check(_PyO)) { // c'est un int
+ *this = PyInt_AsLong(_PyO);
+
+ } else { // erreur
+ PyErr_SetString(PyExc_RuntimeWarning, "PyVersatile::PyVersatile(const PyObject * PyO) : invalid PyObject");
+ }
+ }
+
+
+
+ // Conversion de type vers un PyObject
+ PyVersatile::operator PyObject *() const
+ {
+ PyObject * obj;
+
+ if (_maxsize != 1) { // une liste
+ obj = PyList_New(0);
+ for(Versatile::const_iterator it=begin(); it!=end(); it++) {
+ char ch[2] = {0, 0};
+ string st;
+ Couple cp;
+// PyObject * tuple;
+ switch (_discriminator) {
+ // case BOOL:
+ // PyList_Append(obj, PyInt_FromLong(* static_cast<BoolType *>(*it)));
+ // break;
+
+ // case CHAR:
+ // *ch = * static_cast<CharType *>(*it);
+ // PyList_Append(obj, PyString_FromString(ch));
+ // break;
+
+ // case INT:
+ // PyList_Append(obj, PyInt_FromLong(* static_cast<IntType *>(*it)));
+ // break;
+
+ case LONG:
+ PyList_Append(obj, PyInt_FromLong(* static_cast<LongType *>(*it)));
+ break;
+
+ case STRING:
+ st = * static_cast<StringType *>(*it);
+ PyList_Append(obj, PyString_FromString(st.c_str()));
+ break;
+
+ case COUPLE:
+ cp = * static_cast<CoupleType *>(*it);
+// tuple = PyTuple_New(2);
+// PyTuple_SetItem(tuple, 0, PyString_FromString( cp.getLocal().c_str() ) );
+// PyTuple_SetItem(tuple, 1, PyString_FromString( cp.getRemote().c_str() ) );
+// PyList_Append(obj, tuple);
+ PyList_Append(obj, Py_BuildValue("(ss)", cp.getLocal().c_str(), cp.getRemote().c_str() ));
+ break;
+
+ case UNDEFINED:
+ PyList_Append(obj, Py_None);
+ break;
+ }
+
+ }
+
+ } else { // un scalaire
+ char ch[2] = {0, 0};
+ string st;
+ Couple cp;
+// PyObject * tuple;
+ switch (_discriminator) {
+ // case BOOL:
+ // obj = PyInt_FromLong(* static_cast<BoolType *>(front()));
+ // break;
+
+ // case CHAR:
+ // *ch = * static_cast<CharType *>(front());
+ // obj = PyString_FromString(ch);
+ // break;
+
+ // case INT:
+ // obj = PyInt_FromLong(* static_cast<IntType *>(front()));
+ // break;
+
+ case LONG:
+ obj = PyInt_FromLong(* static_cast<LongType *>(front()));
+ break;
+
+ case STRING:
+ st = * static_cast<StringType *>(front());
+ obj = PyString_FromString(st.c_str());
+ break;
+
+ case COUPLE:
+ cp = * static_cast<CoupleType *>(front());
+// tuple = PyTuple_New(2);
+// PyTuple_SetItem(tuple, 0, PyString_FromString( cp.getLocal().c_str() ) );
+// PyTuple_SetItem(tuple, 1, PyString_FromString( cp.getRemote().c_str() ) );
+// obj = PyList_New(0);
+// PyList_Append(obj, tuple);
+ obj = Py_BuildValue("[(ss)]", cp.getLocal().c_str(), cp.getRemote().c_str() );
+ break;
+
+ case UNDEFINED:
+ obj = Py_None;
+ break;
+ }
+ }
+
+ return obj;
+ }
+
+
+ // Operateur d'affectation a partir d'un objet Versatile
+ PyVersatile & PyVersatile::operator =(const Versatile & V)
+ {
+ Versatile * me = this;
+ *me = V;
+ return *this;
+ }
+
+}
+
+
+// COMMENTS
--- /dev/null
+/*
+ * PyVersatile.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Mon Oct 13 12:01:12 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _PYVERSATILE_H_
+#define _PYVERSATILE_H_
+
+
+#include <Python.h>
+#include "Batch_Versatile.hxx"
+#include "Batch_TypeMismatchException.hxx"
+#include "Batch_ListIsFullException.hxx"
+#include "Batch_InvalidArgumentException.hxx"
+
+namespace Batch {
+
+ class PyVersatile : public Versatile
+ {
+ public:
+ // Constructeur a partir d'un objet Versatile
+ PyVersatile(const Versatile &);
+
+ // Constructeur a partir d'un PyObject
+ PyVersatile(const PyObject *) throw(TypeMismatchException, ListIsFullException, InvalidArgumentException);
+
+ // Conversion de type vers un PyObject
+ operator PyObject *() const;
+
+ // Operateur d'affectation a partir d'un objet Versatile
+ PyVersatile & operator =(const Versatile &);
+
+ protected:
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * RunTimeException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Nov 25 14:04:13 2003
+ * Projet : Salome 2
+ *
+ */
+
+#include "Batch_RunTimeException.hxx"
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * RunTimeException.hxx :
+ *
+ * Auteur : %author% - EDF R&D
+ * Mail : mailto:ivan.dutka-malen@der.edf.fr
+ * Date : Tue Nov 25 14:04:13 2003
+ * Projet : Salome 2
+ *
+ */
+
+#ifndef _RUNTIMEEXCEPTION_H_
+#define _RUNTIMEEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class RunTimeException : public GenericException
+ {
+ public:
+ // Constructeur
+ RunTimeException(string ch = "undefined") : GenericException("RunTimeException", ch) {}
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * StringType.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <string>
+#include "Batch_StringType.hxx"
+
+namespace Batch {
+
+ // Conversion en chaine
+ string StringType::affiche() const
+ {
+ return _data;
+ }
+
+ // Operateur d'affectation
+ StringType & StringType::operator =(string s)
+ {
+ _data = s;
+ return *this;
+ }
+
+ // Conversion en chaine
+ StringType::operator string() const
+ {
+ return this->_data;
+ }
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ GenericType * StringType::clone() const
+ {
+ StringType * pS = new StringType(this->_data);
+ assert(pS != 0);
+ return pS;
+ }
+
+}
--- /dev/null
+/*
+ * StringType.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _STRINGTYPE_H_
+#define _STRINGTYPE_H_
+
+using namespace std;
+#include <string>
+#include "Batch_GenericType.hxx"
+
+namespace Batch {
+
+ class StringType : public GenericType
+ {
+ public:
+ // Constructeur
+ StringType(const string & s="") : _data(s) {}
+
+ // Conversion en chaine
+ virtual string affiche() const;
+ virtual operator string() const;
+
+ // Operateur d'affectation
+ virtual StringType & operator =(string);
+
+ // Clone duplique l'objet et en fabrique un nouveau a l'aide de new
+ // qu'il faudra detruire ensuite manuellement
+ virtual GenericType * clone() const;
+
+ protected:
+ string _data;
+
+ private:
+
+ };
+
+}
+
+#endif
--- /dev/null
+/*
+ * TypeMismatchException.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include "Batch_TypeMismatchException.hxx"
+
+namespace Batch {
+
+}
--- /dev/null
+/*
+ * TypeMismatchException.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _TYPEMISMATCHEXCEPTION_H_
+#define _TYPEMISMATCHEXCEPTION_H_
+
+
+#include "Batch_GenericException.hxx"
+
+namespace Batch {
+
+ class TypeMismatchException : public GenericException
+ {
+ public:
+ // Constructeur
+ TypeMismatchException(string ch = "undefined") : GenericException("TypeMismatchException", ch) {}
+ };
+
+}
+
+#endif
+
--- /dev/null
+/*
+ * Versatile.cxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#include <iostream>
+#include <list>
+#include <string>
+#include <sstream>
+//#include "MEDMEM_STRING.hxx"
+#include "Batch_GenericType.hxx"
+#include "Batch_IntType.hxx"
+#include "Batch_BoolType.hxx"
+#include "Batch_CharType.hxx"
+#include "Batch_LongType.hxx"
+#include "Batch_StringType.hxx"
+#include "Batch_Versatile.hxx"
+#include "Batch_TypeMismatchException.hxx"
+#include "Batch_ListIsFullException.hxx"
+
+namespace Batch {
+
+ // Constructeur par recopie
+ Versatile::Versatile(const Versatile & V) : _discriminator(V._discriminator), _maxsize(V._maxsize), _name(V._name) // , _str_value(0)
+ {
+ Versatile::const_iterator it;
+
+ // On prend un a un les elements de l'objet passe en argument qu'on duplique
+ for(it=V.begin(); it!=V.end(); it++)
+ push_back( (*it)->clone() ); // Attention, la methode clone fait un new implicite
+ }
+
+ // Destructeur
+ Versatile::~Versatile()
+ {
+ eraseAll();
+ }
+
+ // Operateur d'affectation entre objets
+ Versatile & Versatile::operator = (const Versatile & Vrhs) throw(TypeMismatchException)
+ {
+ // ATTENTION : le forçage de type leve une exception TypeMismatchException entre cas de conflit
+ setType(Vrhs._discriminator);
+ setMaxSize(Vrhs._maxsize);
+ _name = Vrhs._name;
+
+ // On efface les donnees precedentes
+ eraseAll();
+
+ // On copie les donnees de Vrhs
+ Versatile::const_iterator it;
+
+ for(it=Vrhs.begin(); it!=Vrhs.end(); it++)
+ push_back( (*it)->clone() ); // Attention, la methode clone fait un new implicite
+
+ return *this;
+ }
+
+ // Operateur d'affectation a partir d'un long
+ Versatile & Versatile::operator = (const long l) throw(TypeMismatchException)
+ {
+ // ATTENTION : le forçage de type leve une exception TypeMismatchException entre cas de conflit
+ setType(LONG);
+
+ // On efface les donnees precedentes
+ eraseAll();
+
+ // On ajoute un element interne de type long a l'objet
+ LongType * pL = new LongType(l);
+ assert(pL != 0);
+ push_back(pL);
+ return *this;
+ }
+
+ // Operateur d'affectation a partir d'une string
+ Versatile & Versatile::operator = (const string & ch) throw(TypeMismatchException)
+ {
+ // ATTENTION : le forçage de type leve une exception TypeMismatchException entre cas de conflit
+ setType(STRING);
+
+ // On efface les donnees precedentes
+ eraseAll();
+
+ // On ajoute un element interne de type string a l'objet
+ StringType * pS = new StringType(ch);
+ assert(pS != 0);
+ push_back(pS);
+
+ return *this;
+ }
+
+ // Operateur de concatenation a partir d'une string
+ Versatile & Versatile::operator +=(const string & ch) throw(TypeMismatchException,ListIsFullException)
+ {
+ // ATTENTION : le forçage de type leve une exception TypeMismatchException entre cas de conflit
+ setType(STRING);
+
+ // Si la taille maximale est atteinte, on leve une exception ListIsFullException
+ if (_maxsize == 0) push_back(new StringType(ch));
+ else if ((_maxsize > 0) && (size() < _maxsize)) push_back(new StringType(ch));
+ else {
+ //MEDMEM::STRING msg;
+ ostringstream msg;
+ msg << "Taille maximum : " << _maxsize;
+ throw(ListIsFullException(msg.str()));
+ }
+ return *this;
+ }
+
+ // Operateur de concatenation a partir d'une string
+ Versatile & Versatile::operator , (const string & ch) throw(TypeMismatchException,ListIsFullException)
+ {
+ *this += ch;
+ return *this;
+ }
+
+ // Operateur d'affectation a partir d'un Couple
+ Versatile & Versatile::operator = (const Couple & cp) throw(TypeMismatchException)
+ {
+ // ATTENTION : le forçage de type leve une exception TypeMismatchException entre cas de conflit
+ setType(COUPLE);
+
+ // On efface les donnees precedentes
+ eraseAll();
+
+ // On ajoute un element interne de type Couple a l'objet
+ CoupleType * pC = new CoupleType(cp);
+ assert(pC != 0);
+ push_back(pC);
+
+ return *this;
+ }
+
+ // Operateur de concatenation a partir d'un Couple
+ Versatile & Versatile::operator +=(const Couple & cp) throw(TypeMismatchException,ListIsFullException)
+ {
+ // ATTENTION : le forçage de type leve une exception TypeMismatchException entre cas de conflit
+ setType(COUPLE);
+
+ // Si la taille maximale est atteinte, on leve une exception ListIsFullException
+ if (_maxsize == 0) push_back(new CoupleType(cp));
+ else if ((_maxsize > 0) && (size() < _maxsize)) push_back(new CoupleType(cp));
+ else {
+ //MEDMEM::STRING msg;
+ ostringstream msg;
+ msg << "Taille maximum : " << _maxsize;
+ throw(ListIsFullException(msg.str()));
+ }
+ return *this;
+ }
+
+ // Operateur de concatenation a partir d'un Couple
+ Versatile & Versatile::operator , (const Couple & cp) throw(TypeMismatchException,ListIsFullException)
+ {
+ *this += cp;
+ return *this;
+ }
+
+ ostream & operator << (ostream & os, const Versatile & V)
+ {
+ Versatile::const_iterator it;
+ char * sep = "";
+
+ for(it=V.begin(); it!=V.end(); it++, sep=" ") {
+ string s = (*it)->affiche();
+ os << sep << s;
+ }
+ return os;
+ }
+
+ // Positionnement du type de l'element interne
+ void Versatile::setType(DiscriminatorType t) throw(TypeMismatchException)
+ {
+ // Si le type est deja defini et ne correspond pas au type en argument
+ // une exception TypeMismatchException est levee
+ if ( (_discriminator == UNDEFINED) || (_discriminator == t) )
+ _discriminator = t;
+ else {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "Trying to change type of Versatile object \""
+ << _name << "\"";
+ throw(TypeMismatchException(sst.str()));
+ }
+ }
+
+ // Positionnement du nombre d'elements internes
+ void Versatile::setMaxSize(int i)
+ {
+ _maxsize = i;
+ if (i <= 0) return;
+ // Si la nouvelle taille est inferieure au nombre d'elements deja
+ // presents, les elements en surplus sont effaces (troncature)
+ if (size() > _maxsize)
+ {
+ int reste = size() - _maxsize;
+ Versatile::iterator it;
+ for(it=end(); (it!=begin()) && reste; it--, reste--)
+ {
+ delete back();
+ pop_back();
+ }
+ }
+ }
+
+
+ // Conversion de type vers un long
+ Versatile::operator long() const throw(TypeMismatchException)
+ {
+ // Si le type ne correspond pas ou si la liste contient plus d'un element,
+ // la conversion est impossible et une exception TypeMismatchException
+ // est levee
+ if ( (_maxsize != 1) || (_discriminator != LONG) || (size() == 0) ) {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "Cannot cast Versatile object \""
+ << _name << "\" to long";
+ throw(TypeMismatchException(sst.str()));
+ }
+ return *( static_cast<LongType *>(this->front()) );
+ }
+
+ // Conversion de type vers un Couple
+ Versatile::operator Couple() const throw(TypeMismatchException)
+ {
+ // Si le type ne correspond pas ou si la liste contient plus d'un element,
+ // la conversion est impossible et une exception TypeMismatchException
+ // est levee
+ if ( (_maxsize != 1) || (_discriminator != COUPLE) || (size() == 0) ) {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "Cannot cast Versatile object \""
+ << _name << "\" to Couple";
+ throw(TypeMismatchException(sst.str()));
+ }
+ return *( static_cast<CoupleType *>(this->front()) );
+ }
+
+ // Conversion de type vers une string
+ string Versatile::str() const throw(TypeMismatchException)
+ {
+ // Si le type ne correspond pas, la conversion est impossible et
+ // une exception TypeMismatchException est levee
+ if ( (_discriminator != STRING) || (size() == 0) ) {
+ //MEDMEM::STRING sst;
+ ostringstream sst;
+ sst << "Cannot cast Versatile object \""
+ << _name << "\" to string";
+ throw(TypeMismatchException(sst.str()));
+ }
+
+ // La chaine renvoyee est la concatenation des chaines internes
+ string s;
+ Versatile::const_iterator it;
+ const char * sep = "";
+ for(it=begin(); it!=end(); it++, s+=sep, sep=" ")
+ s += *( static_cast<StringType *>(*it));
+
+ return s;
+ }
+
+ // Conversion de type vers une string
+ Versatile::operator string () const throw(TypeMismatchException)
+ {
+ return str();
+ }
+
+ // Efface tous les elements internes de l'objet
+ void Versatile::eraseAll()
+ {
+ while(!empty())
+ {
+ delete back();
+ pop_back();
+ }
+ }
+
+
+ // Recuperation du type de l'element interne
+ DiscriminatorType Versatile::getType() const
+ {
+ return _discriminator;
+ }
+
+ // Recuperation du nom de l'objet
+ string Versatile::getName() const
+ {
+ return _name;
+ }
+
+ // Positionnement du nom de l'objet
+ void Versatile::setName(const string & name)
+ {
+ _name = name;
+ }
+}
--- /dev/null
+/*
+ * Versatile.hxx :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+#ifndef _VERSATILE_H_
+#define _VERSATILE_H_
+
+using namespace std;
+#include <iostream>
+#include <list>
+#include <string>
+#include "Batch_GenericType.hxx"
+#include "Batch_IntType.hxx"
+#include "Batch_BoolType.hxx"
+#include "Batch_CharType.hxx"
+#include "Batch_LongType.hxx"
+#include "Batch_StringType.hxx"
+#include "Batch_CoupleType.hxx"
+#include "Batch_TypeMismatchException.hxx"
+#include "Batch_ListIsFullException.hxx"
+
+namespace Batch {
+
+ // Les types autorises
+ // enum DiscriminatorType { UNDEFINED, BOOL, CHAR, INT, LONG, STRING};
+ enum DiscriminatorType { UNDEFINED, LONG, STRING, COUPLE };
+
+ typedef struct {
+ DiscriminatorType type; // le type de l'element interne
+ int maxelem; // le nombre d'elements autorises
+ } TypeParam;
+
+ class Versatile : public list< GenericType * >
+ {
+ public:
+ // Constructeur standard et destructeur
+ Versatile() : _discriminator(UNDEFINED), _maxsize(1), _name("undefined") {}
+ virtual ~Versatile();
+
+ // Constructeur par recopie
+ Versatile(const Versatile & V);
+
+ // Constructeur depuis le type de "base"
+ Versatile(long l) : _discriminator(LONG), _maxsize(1), _name("long") { push_back(new LongType(l)); }
+ Versatile(const string & s) : _discriminator(STRING), _maxsize(1), _name("string") { push_back(new StringType(s)); }
+ Versatile(const Couple & c) : _discriminator(COUPLE), _maxsize(1), _name("couple") { push_back(new CoupleType(c)); }
+
+ // Operateur d'affectation et de concatenation a partir d'un type de "base"
+ Versatile & operator = (const long l) throw(TypeMismatchException);
+ Versatile & operator = (const string & ch) throw(TypeMismatchException);
+ Versatile & operator +=(const string & ch) throw(TypeMismatchException,ListIsFullException);
+ Versatile & operator , (const string & ch) throw(TypeMismatchException,ListIsFullException);
+ Versatile & operator = (const Couple & cp) throw(TypeMismatchException);
+ Versatile & operator +=(const Couple & cp) throw(TypeMismatchException,ListIsFullException);
+ Versatile & operator , (const Couple & cp) throw(TypeMismatchException,ListIsFullException);
+
+ // Operateur d'affectation entre objets
+ Versatile & operator = (const Versatile & V) throw(TypeMismatchException);
+
+ // Conversion de type vers un type de "base"
+ operator long() const throw(TypeMismatchException);
+ operator string() const throw(TypeMismatchException);
+ operator Couple() const throw(TypeMismatchException);
+ string str() const throw(TypeMismatchException);
+
+ // Operateur pour l'affichage sur un stream
+ friend ostream & operator << (ostream & os, const Versatile & );
+
+ // Positionnement et recuperation du type de l'element interne
+ void setType(DiscriminatorType) throw(TypeMismatchException);
+ DiscriminatorType getType() const;
+
+ // Positionnement et recuperation du nombre d'elements internes
+ void setMaxSize(int i);
+ int getMaxSize() const { return _maxsize; }
+
+ // Positionnement et recuperation du nom de l'objet
+ string getName() const;
+ void setName(const string & name);
+
+ protected:
+ // Efface tous les elements internes de l'objet
+ virtual void eraseAll();
+
+ DiscriminatorType _discriminator; // type de l'element interne
+ int _maxsize; // nombre max d'elements internes
+ string _name; // nom de l'objet (sert pour les exceptions)
+
+ private:
+
+ };
+
+}
+
+#endif
+
--- /dev/null
+# SALOME Container : implementation of container and engine for Kernel
+#
+# Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+# CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License as published by the Free Software Foundation; either
+# version 2.1 of the License.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with this library; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+#
+# See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+#
+#
+#
+# File : Makefile.in
+# Author : EDF
+# Module : SALOME
+# $Header$
+
+top_srcdir=@top_srcdir@
+top_builddir=../..
+srcdir=@srcdir@
+VPATH=.:@srcdir@:@top_srcdir@/idl
+
+
+@COMMENCE@
+
+EXPORT_HEADERS = \
+ Batch_APIInternalFailureException.hxx \
+ Batch_BatchManager.hxx \
+ Batch_BatchManagerCatalog.hxx \
+ Batch_BoolType.hxx \
+ Batch_CharType.hxx \
+ Batch_ConnexionFailureException.hxx \
+ Batch_Couple.hxx \
+ Batch_CoupleType.hxx \
+ Batch_Date.hxx \
+ Batch_DateType.hxx \
+ Batch_Environnement.hxx \
+ Batch_FactBatchManager.hxx \
+ Batch_GenericException.hxx \
+ Batch_GenericType.hxx \
+ Batch_IntType.hxx \
+ Batch_InvalidArgumentException.hxx \
+ Batch_InvalidKeyException.hxx \
+ Batch_Job.hxx \
+ Batch_JobId.hxx \
+ Batch_JobInfo.hxx \
+ Batch_ListIsFullException.hxx \
+ Batch_LongType.hxx \
+ Batch_MapKey.hxx \
+ Batch_NotYetImplementedException.hxx \
+ Batch_Parametre.hxx \
+ Batch_PyVersatile.hxx \
+ Batch_RunTimeException.hxx \
+ Batch_StringType.hxx \
+ Batch_TypeMismatchException.hxx \
+ Batch_Versatile.hxx
+
+# Specialisation pour OpenPBS
+EXPORT_HEADERS += \
+ Batch_BatchManager_PBS.hxx \
+ Batch_FactBatchManager_PBS.hxx \
+ Batch_JobInfo_PBS.hxx \
+ Batch_Job_PBS.hxx
+
+
+# Libraries targets
+
+LIB = libSalomeBatch.la
+LIB_SRC = \
+ Batch_APIInternalFailureException.cxx \
+ Batch_BatchManager.cxx \
+ Batch_BatchManagerCatalog.cxx \
+ Batch_BoolType.cxx \
+ Batch_CharType.cxx \
+ Batch_ConnexionFailureException.cxx \
+ Batch_Couple.cxx \
+ Batch_CoupleType.cxx \
+ Batch_Date.cxx \
+ Batch_DateType.cxx \
+ Batch_Environnement.cxx \
+ Batch_FactBatchManager.cxx \
+ Batch_GenericException.cxx \
+ Batch_GenericType.cxx \
+ Batch_IntType.cxx \
+ Batch_InvalidArgumentException.cxx \
+ Batch_InvalidKeyException.cxx \
+ Batch_Job.cxx \
+ Batch_JobId.cxx \
+ Batch_JobInfo.cxx \
+ Batch_ListIsFullException.cxx \
+ Batch_LongType.cxx \
+ Batch_MapKey.cxx \
+ Batch_NotYetImplementedException.cxx \
+ Batch_Parametre.cxx \
+ Batch_PyVersatile.cxx \
+ Batch_RunTimeException.cxx \
+ Batch_StringType.cxx \
+ Batch_TypeMismatchException.cxx \
+ Batch_Versatile.cxx
+
+# Specialisation pour OpenPBS
+LIB_SRC += \
+ Batch_BatchManager_PBS.cxx \
+ Batch_FactBatchManager_PBS.cxx \
+ Batch_JobInfo_PBS.cxx \
+ Batch_Job_PBS.cxx
+
+LIB_SERVER_IDL =
+
+
+CPPFLAGS += $(PYTHON_INCLUDES) $(OPENPBS_INCLUDES)
+
+CXXFLAGS += $(PYTHON_INCLUDES) $(OPENPBS_INCLUDES)
+
+LDFLAGS += $(OPENPBS_LIBDIR)
+
+LIBS += $(OPENPBS_LIBS) -lSALOMELocalTrace
+
+@CONCLUDE@
--- /dev/null
+#Batch_test.py
+
+# pratique
+import readline
+import rlcompleter
+readline.parse_and_bind('tab: complete')
+
+# Importation de la bibliotheque de classes Batch
+from libBatch_Swig import *
+
+def work():
+ # Definition d'un job...
+ job=Job()
+ # ... de ses parametres ...
+ p={}
+ p['EXECUTABLE']='/home/dutka/tmp/job'
+ p['NAME']='MonJob'
+ p['OUTFILE']=[('/tmp/stdout', 'stdout'), ('/tmp/stderr', 'stderr')]
+ job.setParametre(p)
+ # ... et de son environnement
+ job.setEnvironnement({})
+ print job
+
+ # Appel au catalogue de BatchManager pour accéder au serveur cli70cu
+ # Instanciation du catalogue (quasi-singleton)
+ c=BatchManagerCatalog()
+ # Instanciation d'une Factory de BatchManager de type 'PBS'
+ # fbm=c('PBS')
+
+ # Creation d'un BatchManager de type PBS sur le serveur cli70cu
+ bm=c('PBS')('cli70cu')
+
+ # Soumission du job au BatchManager
+ jobid=bm.submitJob(job)
+ print jobid
+
+ # Interrogation de l'etat du job
+ jobid.queryJob()
+
+ # On attend que le job soit termine
+ try:
+ while 1: jinfo = jobid.queryJob()
+ except:
+ print "Job", jobid, "is done"
+
+ pass
+
+if __name__ == "__main__":
+ work()
+ pass
+
+
+
--- /dev/null
+# Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+# CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License as published by the Free Software Foundation; either
+# version 2.1 of the License.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with this library; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+#
+# See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+#
+#
+#
+# File : Makefile.in
+# Author : Paul RASCLE, EDF
+# Module : SALOME
+# $Header$
+
+top_srcdir=@top_srcdir@
+top_builddir=../..
+srcdir=@srcdir@
+VPATH=.:@srcdir@:@top_srcdir@/idl
+
+
+@COMMENCE@
+
+# Libraries targets
+
+LIB = libBatch_Swigcmodule.la
+LIB_SRC =
+
+SWIG_DEF = libBatch_Swig.i
+EXPORT_PYSCRIPTS = libBatch_Swig.py Batch_test.py
+
+CPPFLAGS += $(PYTHON_INCLUDES) $(OPENPBS_INCLUDES)
+
+LDFLAGS += $(OPENPBS_LIBDIR)
+
+LIBS += $(PYTHON_LIBS) $(OPENPBS_LIBS) -lSalomeBatch
+
+@CONCLUDE@
--- /dev/null
+/*
+ * libBatch_Swig.i :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+/* ATTENTION:
+ ==========
+ Certaines classes ont des methodes surchargees et SWIG ne gere pas bien
+ ces surcharges, d'ou un probleme d'utilisation en Python de celles-ci.
+ En bref, ça ne marche pas et il faudra corriger le probleme...
+
+ TODO : corriger le probleme de surcharge des methodes en Python
+
+ IDM.
+*/
+
+
+/* Le nom du module Python tel qu'il est importe */
+%module libBatch_Swig
+
+/* Inclusion des conversions de type */
+%include libBatch_Swig_typemap.i
+
+/* Inclusion de la gestion des exceptions */
+%include libBatch_Swig_exception.i
+
+%{
+#include "Batch_Job.hxx"
+#include "Batch_JobId.hxx"
+#include "Batch_JobInfo.hxx"
+
+#include "Batch_BatchManager.hxx"
+#include "Batch_BatchManagerCatalog.hxx"
+#include "Batch_FactBatchManager.hxx"
+using namespace Batch;
+%}
+
+/* Les classes exportees en Python */
+%include Batch_Job.hxx
+%include Batch_JobId.hxx
+%include Batch_JobInfo.hxx
+
+%include Batch_BatchManager.hxx
+%include Batch_BatchManagerCatalog.hxx
+%include Batch_FactBatchManager.hxx
+
+
+
+/* Les methodes alterJob (surchargees et mal gerees en Python) sont
+ remplacees par des methodes setParametre et setEnvironnement.
+ cf. remarque ci-dessus.
+*/
+%ignore JobId::alterJob(const Parametre & param, const Environnement & env) const;
+%ignore JobId::alterJob(const Parametre & param) const;
+%ignore JobId::alterJob(const Environnement & env) const;
--- /dev/null
+/*
+ * _exception.i :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+%exception {
+ try {
+ $action
+ }
+ catch (GenericException & ex) {
+ string msg = ex.type + " : " + ex.message;
+ PyErr_SetString(PyExc_RuntimeWarning, msg.c_str());
+ return NULL;
+ }
+ catch (...) {
+ PyErr_SetString(PyExc_RuntimeWarning, "unknown exception");
+ return NULL;
+ }
+}
+
--- /dev/null
+/*
+ * _typemap.i :
+ *
+ * Auteur : Ivan DUTKA-MALEN - EDF R&D
+ * Date : Septembre 2003
+ * Projet : SALOME 2
+ *
+ */
+
+%{
+#include <string>
+#include <list>
+#include <map>
+#include "Batch_Parametre.hxx"
+#include "Batch_PyVersatile.hxx"
+#include "Batch_JobId.hxx"
+#include "Batch_FactBatchManager.hxx"
+%}
+
+# // supprime toutes les definitions par defaut => sert au debug
+# %typemap(in) SWIGTYPE ;
+
+
+# // construction d'un dictionnaire Python a partir d'un objet BatchManagerCatalog C++
+%typemap(out) map<string, Batch::FactBatchManager *> *
+{
+ $result = PyDict_New();
+
+ // on itere sur toutes les clefs de la map
+ for(map<string, FactBatchManager *>::const_iterator it=(* $1).begin(); it!=(* $1).end(); it++) {
+ string key = (*it).first;
+ PyObject * obj = SWIG_NewPointerObj((void *) (*it).second, SWIGTYPE_p_Batch__FactBatchManager, 0);
+ PyDict_SetItem($result, PyString_FromString(key.c_str()), obj);
+ }
+}
+
+
+# // construction d'un dictionnaire Python a partir d'un objet Parametre C++
+%typemap(out) Parametre
+{
+ $result = PyDict_New();
+
+ // on itere sur toutes les clefs de la map, et on passe par la classe PyVersatile
+ // qui convertit un Versatile en PyObject et vice versa
+ for(Parametre::const_iterator it=$1.begin(); it!=$1.end(); it++) {
+ string key = (*it).first;
+ PyVersatile PyV = (*it).second;
+ PyDict_SetItem($result, PyString_FromString(key.c_str()), PyV);
+ }
+}
+
+
+# // construction d'un objet Parametre C++ a partir d'un dictionnaire Python
+%typemap(in) Parametre & (Parametre PM)
+{
+ if (!PyDict_Check($input)) {
+ PyErr_SetString(PyExc_ValueError,"Expected a dictionnary");
+ return NULL;
+ }
+
+ try {
+ // on itere sur toutes les clefs du dictionnaire, et on passe par la classe PyVersatile
+ // qui convertit un Versatile en PyObject et vice versa
+ PyObject *key, *value;
+ int pos = 0;
+ while (PyDict_Next($input, &pos, &key, &value)) {
+ string mk = PyString_AsString(key);
+ PyVersatile PyV = value;
+ PyV.setName(mk);
+ PM[mk] = PyV;
+ }
+
+ $1 = &PM; // $1 est une reference donc on lui passe une adresse
+ }
+ catch (GenericException & ex) {
+ string msg = ex.type + " : " + ex.message;
+ PyErr_SetString(PyExc_RuntimeWarning, msg.c_str());
+ return NULL;
+ }
+ catch (...) {
+ PyErr_SetString(PyExc_RuntimeWarning, "unknown exception");
+ return NULL;
+ }
+}
+
+
+# // construction d'un objet Parametre C++ a partir d'un dictionnaire Python
+%typemap(in) Parametre (Parametre PM)
+{
+ if (!PyDict_Check($input)) {
+ PyErr_SetString(PyExc_ValueError,"Expected a dictionnary");
+ return NULL;
+ }
+
+ try {
+ // on itere sur toutes les clefs du dictionnaire, et on passe par la classe PyVersatile
+ // qui convertit un Versatile en PyObject et vice versa
+ PyObject *key, *value;
+ int pos = 0;
+ while (PyDict_Next($input, &pos, &key, &value)) {
+ string mk = PyString_AsString(key);
+ PyVersatile PyV = value;
+ PyV.setName(mk);
+ PM[mk] = PyV;
+ }
+
+ $1 = PM;
+ }
+ catch (GenericException & ex) {
+ string msg = ex.type + " : " + ex.message;
+ PyErr_SetString(PyExc_RuntimeWarning, msg.c_str());
+ return NULL;
+ }
+ catch (...) {
+ PyErr_SetString(PyExc_RuntimeWarning, "unknown exception");
+ return NULL;
+ }
+}
+
+
+# // construction d'un dictionnaire Python a partir d'un objet Environnement C++
+%typemap(out) Environnement
+{
+ $result = PyDict_New();
+
+ // on itere sur toutes les clefs de la map
+ for(Environnement::const_iterator it=$1.begin(); it!=$1.end(); it++) {
+ string key = (*it).first;
+ string val = (*it).second;
+ PyDict_SetItem($result,
+ PyString_FromString(key.c_str()),
+ PyString_FromString(val.c_str()));
+ }
+}
+
+
+# // construction d'un objet Environnement C++ a partir d'un dictionnaire Python
+%typemap(in) Environnement & (Environnement E)
+{
+ if (!PyDict_Check($input)) {
+ PyErr_SetString(PyExc_ValueError,"Expected a dictionnary");
+ return NULL;
+ }
+
+ // on itere sur toutes les clefs du dictionnaire
+ PyObject *key, *value;
+ int pos = 0;
+ while (PyDict_Next($input, &pos, &key, &value)) {
+ string mk = PyString_AsString(key);
+ string val = PyString_AsString(value);
+ E[mk] = val;
+ }
+
+ $1 = &E; // $1 est une reference donc on lui passe une adresse
+}
+
+
+
+# // construction d'un objet Environnement C++ a partir d'un dictionnaire Python
+%typemap(in) Environnement (Environnement E)
+{
+ if (!PyDict_Check($input)) {
+ PyErr_SetString(PyExc_ValueError,"Expected a dictionnary");
+ return NULL;
+ }
+
+ // on itere sur toutes les clefs du dictionnaire
+ PyObject *key, *value;
+ int pos = 0;
+ while (PyDict_Next($input, &pos, &key, &value)) {
+ string mk = PyString_AsString(key);
+ string val = PyString_AsString(value);
+ E[mk] = val;
+ }
+
+ $1 = E;
+}
+
+
+
+# // construction d'une string Python a partir d'une string STL
+%typemap(python,out) string
+{
+ $result = PyString_FromString($1.c_str());
+}
+
+
+
+# // construction d'une string STL a partir d'une string Python
+#%typemap(in) string & (string S)
+#{
+## if (!PyString_Check($input)) {
+# PyErr_SetString(PyExc_ValueError,"Expected a string");
+# return NULL;
+# }
+#
+# S = string(PyString_AsString($input));
+# $1 = &S; // $1 est une reference donc on lui passe une adresse
+#}
+
+
+
+# // construction d'une string STL a partir d'une string Python
+#%typemap(in) string (string S)
+#{
+## if (!PyString_Check($input)) {
+# PyErr_SetString(PyExc_ValueError,"Expected a string");
+# return NULL;
+# }
+#
+# S = string(PyString_AsString($input));
+# $1 = S;
+#}
--- /dev/null
+// KERNEL Utils : common utils for KERNEL
+// Copyright (C) 2003 CEA
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+
+
+#include "CASCatch_SignalsHandler.h"
+#include <OSD.hxx>
+
+
+CASCatch_SignalsHandler::CASCatch_SignalsHandler(bool theFloatingSignal)
+{
+ OSD::SetSignal(theFloatingSignal);
+}
--- /dev/null
+// KERNEL Utils : common utils for KERNEL
+// Copyright (C) 2003 CEA
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+
+#ifndef _CASCATCH_SIGNALSHANDLER_H_
+#define _CASCATCH_SIGNALSHANDLER_H_
+
+
+#include "Utils_SignalsHandler.h"
+#include <Standard_ErrorHandler.hxx>
+
+class CASCatch_SignalsHandler: private Utils_SignalsHandler{
+ public:
+ CASCatch_SignalsHandler(bool theFloatingSignal = true);
+};
+
+
+#endif
--- /dev/null
+# SALOME Utils : general SALOME's definitions and tools
+#
+# Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+# CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+#
+# This library is free software; you can redistribute it and/or
+# modify it under the terms of the GNU Lesser General Public
+# License as published by the Free Software Foundation; either
+# version 2.1 of the License.
+#
+# This library is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+# Lesser General Public License for more details.
+#
+# You should have received a copy of the GNU Lesser General Public
+# License along with this library; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+#
+# See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+#
+#
+#
+# File : Makefile.in
+# Author : Marc Tajchman (CEA)
+# Module : SALOME
+# $Header$
+
+top_srcdir=@top_srcdir@
+top_builddir=../..
+srcdir=@srcdir@
+VPATH=.:@srcdir@:@top_srcdir@/idl
+
+
+@COMMENCE@
+
+# header files
+EXPORT_HEADERS= CASCatch_SignalsHandler.h
+
+# Libraries targets
+LIB = libCASCatch.la
+LIB_SRC = CASCatch_SignalsHandler.cxx
+
+CPPFLAGS += $(OCC_INCLUDES)
+CXXFLAGS += $(OCC_CXXFLAGS)
+LDFLAGS+= $(CAS_KERNEL)
+
+@CONCLUDE@
+
+
--- /dev/null
+
+top_srcdir=@top_srcdir@
+top_builddir=../..
+srcdir=@srcdir@
+VPATH=.:@srcdir@:@top_srcdir@/idl
+
+
+@COMMENCE@
+
+EXPORT_PYSCRIPTS =
+
+EXPORT_HEADERS = \
+ ReceiverFactory.hxx \
+ SenderFactory.hxx \
+ SALOMEMultiComm.hxx \
+ MultiCommException.hxx
+# Libraries targets
+
+LIB = libSalomeCommunication.la
+LIB_SRC = SALOME_Comm_i.cxx SenderFactory.cxx Receiver.cxx MultiCommException.cxx SALOMEMultiComm.cxx ReceiverFactory.cxx
+LIB_SERVER_IDL = SALOME_Comm.idl SALOME_Exception.idl
+
+# Executables targets
+BIN =
+BIN_SRC =
+BIN_SERVER_IDL =
+
+CPPFLAGS+= $(PYTHON_INCLUDES) $(MPI_INCLUDES)
+
+LDFLAGS+= -lOpUtil -lSALOMELocalTrace
+
+LIBS += -Xlinker -export-dynamic $(PYTHON_LIBS) $(MPI_LIBS)
+
+@CONCLUDE@
--- /dev/null
+#include "MultiCommException.hxx"
+
+MultiCommException::MultiCommException(const char *message)
+{
+ _message=message;
+}
+
+const char *MultiCommException::what() const
+{
+ return _message.c_str();
+}
--- /dev/null
+#ifndef _MULTICOMMEXCEPTION_HXX_
+#define _MULTICOMMEXCEPTION_HXX_
+
+#include <string>
+
+using namespace std;
+
+class MultiCommException {
+private:
+ string _message;
+public:
+ MultiCommException(const char *message);
+ const char *what() const;
+};
+
+#endif
+
--- /dev/null
+#include "Receiver.hxx"
+#include <string.h>
+
+/*!
+ return a deep copy of the array contained in the servant.
+ */
+void *Receiver::getLocalValue(long &size,SALOME_Sender_i* servant)
+{
+ const void *src=servant->getData(size);
+ long lgr=size*servant->getSizeOf();
+ void *ret=new char[lgr];
+ memcpy(ret,src,lgr);
+ return ret;
+ //return (void *)servant->getData(size);
+}
+
+void *Receiver::getValue(long &size,SALOME::Sender_ptr sender)
+{
+ SALOME_Sender_i* data=SALOME_Sender_i::find(sender);
+ if(data)
+ return getLocalValue(size,data);
+ else
+ return getDistValue(size);
+}
+
--- /dev/null
+#ifndef _RECEIVER_HXX_
+#define _RECEIVER_HXX_
+
+#include "SALOME_Comm_i.hxx"
+
+/*! Abstract class factorizing common methods of all the receivers. All of the receivers have to inheritate from it.
+ */
+class Receiver
+{
+public:
+ virtual void *getValue(long &size)=0;
+ virtual ~Receiver() {}
+protected:
+ virtual void *getValue(long &size,SALOME::Sender_ptr sender);
+ static inline void *getLocalValue(long &size,SALOME_Sender_i* servant);
+ virtual void *getDistValue(long &size)=0;
+};
+
+#endif
+
--- /dev/null
+#include "ReceiverFactory.hxx"
+#include "Receivers.hxx"
+
+#ifdef COMP_CORBA_DOUBLE
+#define CorbaDNoCopyReceiver CorbaNCNoCopyReceiver
+#define CorbaDWithCopyReceiver CorbaNCWithCopyReceiver
+#else
+#define CorbaDNoCopyReceiver CorbaWCNoCopyReceiver
+#define CorbaDWithCopyReceiver CorbaWCWithCopyReceiver
+#endif
+
+#ifdef COMP_CORBA_LONG
+#define CorbaINoCopyReceiver CorbaNCNoCopyReceiver
+#define CorbaIWithCopyReceiver CorbaNCWithCopyReceiver
+#else
+#define CorbaINoCopyReceiver CorbaWCNoCopyReceiver
+#define CorbaIWithCopyReceiver CorbaWCWithCopyReceiver
+#endif
+
+#ifdef HAVE_SOCKET
+#include <rpc/xdr.h>
+#endif
+
+/*!
+ This method performs the transfert with the remote sender given. If it fails with this sender it tries with an another protocol (CORBA by default).
+ */
+void *ReceiverFactory::getValue(SALOME::Sender_ptr sender,long &size)throw(MultiCommException)
+{
+ void *ret;
+ try{
+ ret=getValueOneShot(sender,size);
+ }
+ catch(MultiCommException&)
+ {
+ SALOME::Sender_ptr newSender=sender->buildOtherWithProtocol(SALOME::CORBA_);
+ MESSAGE("PROTOCOL CHANGED TO CORBA");
+ sender->release();
+ CORBA::release(sender);
+ ret=getValueOneShot(newSender,size);
+ }
+ return ret;
+}
+
+/*!
+ This method performs the transfert with the remote sender given. If it fails an exception is thrown.
+ */
+void *ReceiverFactory::getValueOneShot(SALOME::Sender_ptr sender,long &size)throw(MultiCommException)
+{
+ SALOME::CorbaDoubleNCSender_ptr cncD_ptr;
+ SALOME::CorbaDoubleCSender_ptr cwcD_ptr;
+ SALOME::CorbaLongNCSender_ptr cncL_ptr;
+ SALOME::CorbaLongCSender_ptr cwcL_ptr;
+#ifdef HAVE_MPI2
+ SALOME::MPISender_ptr mpi_ptr=SALOME::MPISender::_narrow(sender);
+#endif
+#ifdef HAVE_SOCKET
+ SALOME::SocketSender_ptr sock_ptr=SALOME::SocketSender::_narrow(sender);
+#endif
+ switch(sender->getTypeOfDataTransmitted())
+ {
+ case SALOME::DOUBLE_:
+ cncD_ptr=SALOME::CorbaDoubleNCSender::_narrow(sender);
+ cwcD_ptr=SALOME::CorbaDoubleCSender::_narrow(sender);
+ if(!CORBA::is_nil(cncD_ptr))
+ {
+ CORBA::release(sender);
+ CorbaDNoCopyReceiver<double,CORBA::Double,SALOME::vectorOfDouble_var,SALOME::CorbaDoubleNCSender_ptr> rec(cncD_ptr);
+ return rec.getValue(size);
+ }
+ else if(!CORBA::is_nil(cwcD_ptr))
+ {
+ CORBA::release(sender);
+ CorbaDWithCopyReceiver<double,CORBA::Double,SALOME::vectorOfDouble_var,SALOME::CorbaDoubleCSender_ptr> rec(cwcD_ptr);
+ return rec.getValue(size);
+ }
+#ifdef HAVE_MPI2
+ else if(!CORBA::is_nil(mpi_ptr))
+ {
+ CORBA::release(sender);
+ MPIReceiver<double,MPI_DOUBLE> rec(mpi_ptr);
+ return rec.getValue(size);
+ }
+#endif
+#ifdef HAVE_SOCKET
+ else if(!CORBA::is_nil(sock_ptr))
+ {
+ CORBA::release(sender);
+ SocketReceiver<double,xdr_double> rec(sock_ptr);
+ return rec.getValue(size);
+ }
+#endif
+ else
+ {
+ throw MultiCommException("Unknown sender protocol");
+ return 0;
+ }
+ case SALOME::INT_:
+ cncL_ptr=SALOME::CorbaLongNCSender::_narrow(sender);
+ cwcL_ptr=SALOME::CorbaLongCSender::_narrow(sender);
+ if(!CORBA::is_nil(cncL_ptr))
+ {
+ CORBA::release(sender);
+ CorbaINoCopyReceiver<int,CORBA::Long,SALOME::vectorOfLong_var,SALOME::CorbaLongNCSender_ptr> rec(cncL_ptr);
+ return rec.getValue(size);
+ }
+ else if(!CORBA::is_nil(cwcL_ptr))
+ {
+ CORBA::release(sender);
+ CorbaIWithCopyReceiver<int,CORBA::Long,SALOME::vectorOfLong_var,SALOME::CorbaLongCSender_ptr> rec(cwcL_ptr);
+ return rec.getValue(size);
+ }
+#ifdef HAVE_MPI2
+ else if(!CORBA::is_nil(mpi_ptr))
+ {
+ CORBA::release(sender);
+ MPIReceiver<int,MPI_INT> rec(mpi_ptr);
+ return rec.getValue(size);
+ }
+#endif
+#ifdef HAVE_SOCKET
+ else if(!CORBA::is_nil(sock_ptr))
+ {
+ CORBA::release(sender);
+ SocketReceiver<int,xdr_int> rec(sock_ptr);
+ return rec.getValue(size);
+ }
+#endif
+ else
+ {
+ throw MultiCommException("Unknown sender protocol");
+ return 0;
+ }
+ default:
+ throw MultiCommException("unknown type of data transfered");
+ return 0;
+ }
+}
+
--- /dev/null
+#ifndef _RECEIVERFACTORY_HXX_
+#define _RECEIVERFACTORY_HXX_
+
+#include <SALOMEconfig.h>
+#include CORBA_SERVER_HEADER(SALOME_Comm)
+#include "MultiCommException.hxx"
+
+/*!
+ This class internally builds a receiver associated with the sender given. It also performs transfert completely and clean up the objects.
+ This is the only class used client side of an array.
+ */
+class ReceiverFactory
+{
+public:
+ static void *getValue(SALOME::Sender_ptr sender,long &size)throw(MultiCommException);
+private:
+ static void *getValueOneShot(SALOME::Sender_ptr sender,long &size)throw(MultiCommException);
+};
+
+#endif
+
--- /dev/null
+#include "poa.h"
+#include "utilities.h"
+
+#define TAILLE_SPLIT 100000
+#define TIMEOUT 20
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaNCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::CorbaNCNoCopyReceiver(CorbaSender mySender):_mySender(mySender){
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaNCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::~CorbaNCNoCopyReceiver(){
+ _mySender->release();
+ CORBA::release(_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaNCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getDistValue(long &size)
+{
+ TSeqCorba seq=_mySender->send();
+ size=seq->length();
+ return seq->get_buffer(1);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaNCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getValue(long &size)
+{
+ return Receiver::getValue(size,_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaNCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::CorbaNCWithCopyReceiver(CorbaSender mySender):_mySender(mySender){
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaNCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::~CorbaNCWithCopyReceiver(){
+ _mySender->release();
+ CORBA::release(_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaNCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getDistValue(long &size){
+ size=_mySender->getSize();
+ long n;
+ T *ret=new T[size];
+ T *iter=ret;
+ for(long i=0;i<size;i+=TAILLE_SPLIT)
+ {
+ if(size-i>TAILLE_SPLIT)
+ n=TAILLE_SPLIT;
+ else
+ n=size-i;
+ TSeqCorba seq=_mySender->sendPart(i,n);
+ T *seqd=(T *)seq->get_buffer(0);
+ for(long j=0;j<n;j++)
+ *iter++=*seqd++;
+ }
+ return ret;
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaNCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getValue(long &size)
+{
+ return Receiver::getValue(size,_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaWCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::CorbaWCNoCopyReceiver(CorbaSender mySender):_mySender(mySender){
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaWCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::~CorbaWCNoCopyReceiver(){
+ _mySender->release();
+ CORBA::release(_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaWCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getDistValue(long &size){
+ size=_mySender->getSize();
+ long n;
+ T *ret=new T[size];
+ T *iter=ret;
+ for(long i=0;i<size;i+=TAILLE_SPLIT)
+ {
+ if(size-i>TAILLE_SPLIT)
+ n=TAILLE_SPLIT;
+ else
+ n=size-i;
+ TSeqCorba seq=_mySender->sendPart(i,n);
+ TCorba *seqd=seq->get_buffer(0);
+ for(long j=0;j<n;j++)
+ *iter++=*seqd++;
+ }
+ return ret;
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaWCNoCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getValue(long &size)
+{
+ return Receiver::getValue(size,_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaWCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::CorbaWCWithCopyReceiver(CorbaSender mySender):_mySender(mySender){
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+CorbaWCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::~CorbaWCWithCopyReceiver(){
+ _mySender->release();
+ CORBA::release(_mySender);
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaWCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getDistValue(long &size){
+ size=_mySender->getSize();
+ long n;
+ T *ret=new T[size];
+ T *iter=ret;
+ for(long i=0;i<size;i+=TAILLE_SPLIT)
+ {
+ if(size-i>TAILLE_SPLIT)
+ n=TAILLE_SPLIT;
+ else
+ n=size-i;
+ TSeqCorba seq=_mySender->sendPart(i,n);
+ TCorba *seqd=seq->get_buffer(0);
+ for(long j=0;j<n;j++)
+ *iter++=*seqd++;
+ }
+ return ret;
+}
+
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+void *CorbaWCWithCopyReceiver<T,TCorba,TSeqCorba,CorbaSender>::getValue(long &size)
+{
+ return Receiver::getValue(size,_mySender);
+}
+
+#ifdef HAVE_MPI2
+
+template<class T,MPI_Datatype T2>
+MPIReceiver<T,T2>::MPIReceiver(SALOME::MPISender_ptr mySender):_mySender(mySender){
+}
+
+template<class T,MPI_Datatype T2>
+MPIReceiver<T,T2>::~MPIReceiver(){
+ _mySender->release();
+ CORBA::release(_mySender);
+}
+
+template<class T,MPI_Datatype T2>
+void *MPIReceiver<T,T2>::getDistValue(long &size){
+ int i=0;
+ int myproc;
+ int sproc;
+ MPI_Status status;
+ MPI_Comm com;
+ char port_name_clt [MPI_MAX_PORT_NAME];
+ float telps, tuser, tsys, tcpu;
+ T *_v;
+ long _n;
+
+
+ CORBA::Any a;
+ MPI_Comm_rank(MPI_COMM_WORLD, &myproc);
+ SALOME::MPISender::param_var p =_mySender->getParam();
+ _mySender->send();
+ sproc = p->myproc;
+ MPI_Errhandler_set(MPI_COMM_WORLD, MPI_ERRORS_RETURN);
+ while ( i != TIMEOUT && MPI_Lookup_name((char*)p->service,MPI_INFO_NULL,port_name_clt) != MPI_SUCCESS) {
+ i++;
+ }
+ MPI_Errhandler_set(MPI_COMM_WORLD, MPI_ERRORS_ARE_FATAL);
+ if ( i == TIMEOUT ) {
+ MPI_Finalize();
+ exit(-1);
+ }
+ else{
+ // Connect to service, get the inter-communicator server
+ // Attention MPI_Comm_connect est un appel collectif :
+ // - Si lancement mpirun -c n -----> uniquement MPI_COMM_SELF fonctionne
+ // - Si lancement client_server&client_server ----> MPI_COMM_WORLD fonctionne
+
+ // TIMEOUT is inefficient since MPI_Comm_Connect doesn't return if we asked for
+ // a service that has been unpublished !
+ MPI_Errhandler_set(MPI_COMM_WORLD, MPI_ERRORS_RETURN);
+ i = 0;
+ while ( i != TIMEOUT && MPI_Comm_connect(port_name_clt, MPI_INFO_NULL, 0, MPI_COMM_WORLD, &com)!=MPI_SUCCESS ) {
+ i++;
+ }
+ MPI_Errhandler_set(MPI_COMM_WORLD, MPI_ERRORS_ARE_FATAL);
+ if ( i == TIMEOUT ) {
+ MPI_Finalize();
+ exit(-1);
+ }
+ }
+ MPI_Recv( &_n, 1, MPI_LONG, sproc,p->tag1,com,&status);
+ _v = new T[_n];
+ MPI_Recv( _v, _n, T2, sproc,p->tag2,com,&status);
+ _mySender->close(p);
+ MPI_Comm_disconnect( &com );
+ size=_n;
+ return _v;
+}
+
+template<class T,MPI_Datatype T2>
+void *MPIReceiver<T,T2>::getValue(long &size)
+{
+ return Receiver::getValue(size,_mySender);
+}
+
+#endif
+
+#ifdef HAVE_SOCKET
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+#include <netdb.h>
+#include <unistd.h>
+#include <rpc/xdr.h>
+
+template<class T,int (*myFunc)(XDR*,T*)>
+SocketReceiver<T,myFunc>::SocketReceiver(SALOME::SocketSender_ptr mySender) : _mySender(mySender)
+{
+ _clientSockfd = -1;
+ _senderDestruc=true;
+}
+
+template<class T,int (*myFunc)(XDR*,T*)>
+SocketReceiver<T,myFunc>::~SocketReceiver()
+{
+ if(_senderDestruc)
+ {
+ _mySender->release();
+ CORBA::release(_mySender);
+ }
+}
+
+template<class T,int (*myFunc)(XDR*,T*)>
+void *SocketReceiver<T,myFunc>::getValue(long &size)
+{
+ return Receiver::getValue(size,_mySender);
+}
+
+template<class T,int (*myFunc)(XDR*,T*)>
+void* SocketReceiver<T,myFunc>::getDistValue(long &size)
+{
+ int n=0, m;
+ T *v;
+ XDR xp; /* pointeur sur le decodeur XDR */
+
+ try{
+ initCom();
+
+ SALOME::SocketSender::param_var p = _mySender->getParam();
+
+ size = p->lend - p->lstart + 1;
+ v = new T[size];
+
+ connectCom(p->internet_address, p->myport);
+
+ _mySender->send();
+
+ xdrmem_create(&xp,(char*)v,size*sizeof(T),XDR_DECODE );
+ while( n < size*sizeof(T) ){
+ m = read(_clientSockfd, (char*)v+n, size*sizeof(T)-n);
+ if( m < 0 ){
+ closeCom();
+ delete [] v;
+ SALOME::ExceptionStruct es;
+ es.type = SALOME::COMM;
+ es.text = "error read Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ n += m;
+ }
+ xdr_vector( &xp, (char*)v, size, sizeof(T), (xdrproc_t)myFunc);
+ xdr_destroy( &xp );
+
+ _mySender->endOfCom();
+ closeCom();
+ }
+ catch(SALOME::SALOME_Exception &ex){
+ if( ex.details.type == SALOME::COMM )
+ {
+ _senderDestruc=false;
+ cout << ex.details.text << endl;
+ throw MultiCommException("Unknown sender protocol");
+ }
+ else
+ throw ex;
+ }
+
+ return v;
+}
+
+template<class T,int (*myFunc)(XDR*,T*)>
+void SocketReceiver<T,myFunc>::initCom()
+{
+ try{
+ _mySender->initCom();
+
+ /* Ouverture de la socket */
+ _clientSockfd = socket(AF_INET, SOCK_STREAM, 0);
+ if (_clientSockfd < 0) {
+ closeCom();
+ SALOME::ExceptionStruct es;
+ es.type = SALOME::COMM;
+ es.text = "error Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ }
+ catch(SALOME::SALOME_Exception &ex){
+ if( ex.details.type == SALOME::COMM )
+ {
+ _senderDestruc=false;
+ cout << ex.details.text << endl;
+ throw MultiCommException("Unknown sender protocol");
+ }
+ else
+ throw ex;
+ }
+
+}
+
+template<class T,int (*myFunc)(XDR*,T*)>
+void SocketReceiver<T,myFunc>::connectCom(const char *dest_address, int port)
+{
+ struct sockaddr_in serv_addr;
+ struct hostent * server;
+ SALOME::ExceptionStruct es;
+
+ try{
+ /* reception of the host structure on the remote process */
+ server = gethostbyname(dest_address);
+ if( server == NULL ) {
+ closeCom();
+ es.type = SALOME::COMM;
+ es.text = "error unknown host Socket exception";
+ _senderDestruc=false;
+ throw SALOME::SALOME_Exception(es);
+ }
+
+ /* Initialisation of the socket structure */
+ bzero((char*)&serv_addr,sizeof(serv_addr));
+ serv_addr.sin_family = AF_INET;
+ serv_addr.sin_addr.s_addr = INADDR_ANY;
+ bcopy((char *)server->h_addr,
+ (char *)&serv_addr.sin_addr.s_addr,
+ server->h_length);
+ serv_addr.sin_port = htons(port);
+
+ if( connect(_clientSockfd, (struct sockaddr *) & serv_addr, sizeof(struct sockaddr)) < 0 ){
+ closeCom();
+ es.type = SALOME::COMM;
+ es.text = "error connect Socket exception";
+ _senderDestruc=false;
+ throw SALOME::SALOME_Exception(es);
+ }
+
+ _mySender->acceptCom();
+
+ }
+ catch(SALOME::SALOME_Exception &ex){
+ if( ex.details.type == SALOME::COMM )
+ {
+ _senderDestruc=false;
+ cout << ex.details.text << endl;
+ throw MultiCommException("Unknown sender protocol");
+ }
+ else
+ throw ex;
+ }
+
+}
+
+
+template<class T,int (*myFunc)(XDR*,T*)>
+void SocketReceiver<T,myFunc>::closeCom()
+{
+ _mySender->closeCom();
+ if( _clientSockfd >= 0 ){
+ close(_clientSockfd);
+ _clientSockfd = -1;
+ }
+
+}
+
+#endif
--- /dev/null
+#ifndef _RECEIVERS_HXX_
+#define _RECEIVERS_HXX_
+
+#include "SALOME_Comm_i.hxx"
+#include "Receiver.hxx"
+#ifdef HAVE_MPI2
+#include "mpi.h"
+#endif
+
+/*!
+ Receiver used for transfert with CORBA when no copy is required remotely and locally.
+ */
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+class CorbaNCNoCopyReceiver : public Receiver
+{
+private:
+ CorbaSender _mySender;
+public:
+ CorbaNCNoCopyReceiver(CorbaSender mySender);
+ ~CorbaNCNoCopyReceiver();
+ void *getValue(long &size);
+private:
+ void *getDistValue(long &size);
+};
+
+/*!
+ Receiver used for transfert with CORBA when copy is not required remotely but required locally.
+ */
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+class CorbaNCWithCopyReceiver : public Receiver
+{
+private:
+ CorbaSender _mySender;
+public:
+ CorbaNCWithCopyReceiver(CorbaSender mySender);
+ ~CorbaNCWithCopyReceiver();
+ void *getValue(long &size);
+private:
+ void *getDistValue(long &size);
+};
+
+/*!
+ Receiver used for transfert with CORBA when copy is required remotely but not required locally.
+ */
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+class CorbaWCNoCopyReceiver : public Receiver
+{
+private:
+ CorbaSender _mySender;
+public:
+ CorbaWCNoCopyReceiver(CorbaSender mySender);
+ ~CorbaWCNoCopyReceiver();
+ void *getValue(long &size);
+private:
+ void *getDistValue(long &size);
+};
+
+/*!
+ Receiver used for transfert with CORBA when copy is required both remotely and locally.
+ */
+template<class T,class TCorba,class TSeqCorba,class CorbaSender>
+class CorbaWCWithCopyReceiver : public Receiver
+{
+private:
+ CorbaSender _mySender;
+public:
+ CorbaWCWithCopyReceiver(CorbaSender mySender);
+ ~CorbaWCWithCopyReceiver();
+ void *getValue(long &size);
+private:
+ void *getDistValue(long &size);
+};
+
+#ifdef HAVE_MPI2
+/*!
+ Receiver for MPI transfert.
+ */
+template<class T,MPI_Datatype T2>
+class MPIReceiver : public Receiver
+{
+private:
+ SALOME::MPISender_ptr _mySender;
+public:
+ MPIReceiver(SALOME::MPISender_ptr mySender);
+ ~MPIReceiver();
+ void *getValue(long &size);
+private:
+ void *getDistValue(long &size);
+};
+#endif
+
+#ifdef HAVE_SOCKET
+
+class XDR;
+
+/*!
+ Receiver for transfert with sockets.
+ */
+template<class T,int (*myFunc)(XDR*,T*)>
+class SocketReceiver : public Receiver
+{
+private:
+ SALOME::SocketSender_ptr _mySender;
+ int _clientSockfd;
+ bool _senderDestruc;
+public:
+ SocketReceiver(SALOME::SocketSender_ptr mySender);
+ ~SocketReceiver();
+ void *getValue(long &size);
+private:
+ void *getDistValue(long &size);
+ void initCom();
+ void connectCom(const char *, int);
+ void closeCom();
+};
+#endif
+
+#include "Receivers.cxx"
+
+#endif
+
--- /dev/null
+#include "SALOMEMultiComm.hxx"
+
+SALOMEMultiComm::SALOMEMultiComm():_type(SALOME::CORBA_)
+{
+}
+
+SALOMEMultiComm::SALOMEMultiComm(SALOME::TypeOfCommunication type):_type(type)
+{
+}
+
+void SALOMEMultiComm::setProtocol(SALOME::TypeOfCommunication type)
+{
+ _type=type;
+}
+
+SALOME::TypeOfCommunication SALOMEMultiComm::getProtocol() const
+{
+ return _type;
+}
+
+
--- /dev/null
+#ifndef _SALOMEMULTICOMM_HXX_
+#define _SALOMEMULTICOMM_HXX_
+
+#include <SALOMEconfig.h>
+#include CORBA_SERVER_HEADER(SALOME_Comm)
+
+/*!
+ Class is designed to ease the use of multi communication.\n
+ Simply inherite from it your servant class you want to emit data with senders.
+ */
+class SALOMEMultiComm : public virtual POA_SALOME::MultiCommClass {
+protected:
+ SALOME::TypeOfCommunication _type;
+public:
+ SALOMEMultiComm();
+ SALOMEMultiComm(SALOME::TypeOfCommunication type);
+ virtual void setProtocol(SALOME::TypeOfCommunication type);
+ SALOME::TypeOfCommunication getProtocol() const;
+};
+
+#endif
--- /dev/null
+#include <rpc/xdr.h>
+#include "SALOME_Comm_i.hxx"
+#include "poa.h"
+#include "omnithread.h"
+#include "Utils_SINGLETON.hxx"
+#include "Utils_ORB_INIT.hxx"
+#include "utilities.h"
+
+#include "SenderFactory.hxx"
+
+CORBA::ORB_var &getGlobalORB(){
+ ORB_INIT &init = *SINGLETON_<ORB_INIT>::Instance();
+ CORBA::ORB_var &orb = init(0,0);
+ return orb;
+}
+
+/*! Return the C++ data associated to the array to transmit.
+ Used when sender and receiver are collocalized.
+ */
+const void *SALOME_Sender_i::getData(long &size) const{
+ size=_lgrTabToSend;
+ return _tabToSend;
+}
+
+/*! Return the sizeof() of each component of the generic array
+ */
+int SALOME_Sender_i::getSizeOf() const {
+ return _sizeOf;
+}
+
+/*! Unique constructor */
+SALOME_Sender_i::SALOME_Sender_i(SALOME::TypeOfDataTransmitted type,const void *tabToSend,long lgrTabToSend,int sizeOf):_tabToSend(tabToSend),_lgrTabToSend(lgrTabToSend),_type(type),_sizeOf(sizeOf){
+}
+
+/*! Method to establish if the CORBA object refered by pCorba is collocalised.\n
+ If it is, the pointer to the servant that incarnates the CORBA object is returned.
+*/
+SALOME_Sender_i *SALOME_Sender_i::find(SALOME::Sender_ptr pCorba){
+ PortableServer::ServantBase *ret;
+ try {
+ ret=PortableServer::POA::_the_root_poa()->reference_to_servant(pCorba);
+ }
+ catch(...){
+ return 0;
+ }
+ ret->_remove_ref();
+ return dynamic_cast<SALOME_Sender_i *>(ret);
+}
+
+/*! Method for the remote destroy of the current servant. This method is used by the receiver to destroy the sender when the transfert is complete.
+ */
+void SALOME_Sender_i::release()
+{
+ PortableServer::ObjectId_var oid = _default_POA()->servant_to_id(this);
+ _default_POA()->deactivate_object(oid);
+ _remove_ref();
+}
+
+/*! Return the type of the element that compose the array. Used by receiverfactory to build the correct receiver.
+ */
+SALOME::TypeOfDataTransmitted SALOME_Sender_i::getTypeOfDataTransmitted()
+{
+ return _type;
+}
+
+/*! Return a new sender of the same array but with an another protocol.
+ */
+SALOME::Sender_ptr SALOME_Sender_i::buildOtherWithProtocol(SALOME::TypeOfCommunication type)
+{
+ return SenderFactory::buildSender(type,this);
+}
+
+SALOME_CorbaDoubleNCSender_i::SALOME_CorbaDoubleNCSender_i(const double *tabToSend,long lgrTabToSend):SALOME_Sender_i(SALOME::DOUBLE_,tabToSend,lgrTabToSend,sizeof(double)){
+}
+
+SALOME_CorbaDoubleNCSender_i::~SALOME_CorbaDoubleNCSender_i(){
+}
+
+CORBA::ULong SALOME_CorbaDoubleNCSender_i::getSize(){
+ CORBA::ULong ret=_lgrTabToSend;
+ return ret;
+}
+
+SALOME::vectorOfDouble* SALOME_CorbaDoubleNCSender_i::sendPart(CORBA::ULong offset, CORBA::ULong length){
+ SALOME::vectorOfDouble_var c1 = new SALOME::vectorOfDouble(length,length,(CORBA::Double *)((double *)_tabToSend+(long)offset),0);
+ return c1._retn();
+}
+
+SALOME::vectorOfDouble* SALOME_CorbaDoubleNCSender_i::send(){
+ SALOME::vectorOfDouble_var c1 = new SALOME::vectorOfDouble(_lgrTabToSend,_lgrTabToSend,(CORBA::Double *)_tabToSend,0);
+ return c1._retn();
+}
+
+SALOME_CorbaDoubleCSender_i::SALOME_CorbaDoubleCSender_i(const double *tabToSend,long lgrTabToSend):SALOME_Sender_i(SALOME::DOUBLE_,tabToSend,lgrTabToSend,sizeof(double)){
+}
+
+SALOME_CorbaDoubleCSender_i::~SALOME_CorbaDoubleCSender_i(){
+}
+
+CORBA::ULong SALOME_CorbaDoubleCSender_i::getSize(){
+ CORBA::ULong ret=_lgrTabToSend;
+ return ret;
+}
+
+SALOME::vectorOfDouble* SALOME_CorbaDoubleCSender_i::sendPart(CORBA::ULong offset, CORBA::ULong length){
+ SALOME::vectorOfDouble_var c1 = new SALOME::vectorOfDouble;
+ c1->length(length);
+ for (long i=0; i<length; i++)
+ c1[i] = ((double *)_tabToSend)[i+offset];
+ return c1._retn();
+}
+
+////////////////////////
+
+SALOME_CorbaLongNCSender_i::SALOME_CorbaLongNCSender_i(const int *tabToSend,long lgrTabToSend):SALOME_Sender_i(SALOME::INT_,tabToSend,lgrTabToSend,sizeof(int)){
+}
+
+SALOME_CorbaLongNCSender_i::~SALOME_CorbaLongNCSender_i(){
+}
+
+CORBA::ULong SALOME_CorbaLongNCSender_i::getSize(){
+ CORBA::ULong ret=_lgrTabToSend;
+ return ret;
+}
+
+SALOME::vectorOfLong* SALOME_CorbaLongNCSender_i::sendPart(CORBA::ULong offset, CORBA::ULong length){
+ SALOME::vectorOfLong_var c1 = new SALOME::vectorOfLong(length,length,(CORBA::Long *)((long *)_tabToSend+(long)offset),0);
+ return c1._retn();
+}
+
+SALOME::vectorOfLong* SALOME_CorbaLongNCSender_i::send(){
+ SALOME::vectorOfLong_var c1 = new SALOME::vectorOfLong(_lgrTabToSend,_lgrTabToSend,(CORBA::Long *)_tabToSend,0);
+ return c1._retn();
+}
+
+SALOME_CorbaLongCSender_i::SALOME_CorbaLongCSender_i(const int *tabToSend,long lgrTabToSend):SALOME_Sender_i(SALOME::INT_,tabToSend,lgrTabToSend,sizeof(int)){
+}
+
+SALOME_CorbaLongCSender_i::~SALOME_CorbaLongCSender_i(){
+}
+
+CORBA::ULong SALOME_CorbaLongCSender_i::getSize(){
+ CORBA::ULong ret=_lgrTabToSend;
+ return ret;
+}
+
+SALOME::vectorOfLong* SALOME_CorbaLongCSender_i::sendPart(CORBA::ULong offset, CORBA::ULong length){
+ SALOME::vectorOfLong_var c1 = new SALOME::vectorOfLong;
+ c1->length(length);
+ for (long i=0; i<length; i++)
+ c1[i] = ((long *)_tabToSend)[i+offset];
+ return c1._retn();
+}
+
+#ifdef HAVE_MPI2
+
+unsigned long SALOME_MPISender_i::_tag1=0;
+
+unsigned long SALOME_MPISender_i::_tag2=1;
+
+SALOME_MPISender_i::SALOME_MPISender_i(SALOME::TypeOfDataTransmitted type,const void *tabToSend,long lgrTabToSend,int sizeOf):SALOME_Sender_i(type,tabToSend,lgrTabToSend,sizeOf){
+ _portName=new char[MPI_MAX_PORT_NAME];
+}
+
+SALOME_MPISender_i::~SALOME_MPISender_i(){
+ delete [] _portName;
+}
+
+SALOME::MPISender::param* SALOME_MPISender_i::getParam()
+{
+ char stag[12];
+ int myproc,i=0;
+
+ SALOME::MPISender::param_var p = new SALOME::MPISender::param;
+ MPI_Comm_rank(MPI_COMM_WORLD,&_cproc);
+ p->myproc = _cproc;
+ p->tag1 = _tag1;
+ _tag1Inst=_tag1;
+ p->tag2 =_tag2;
+ _tag2Inst=_tag2;
+ std::string service("toto_");
+ sprintf(stag,"%d_",_tag1);
+ service += stag;
+ sprintf(stag,"%d_",p->tag2);
+ service += stag;
+ p->service = CORBA::string_dup(service.c_str());
+ MPI_Open_port(MPI_INFO_NULL, _portName);
+ MPI_Errhandler_set(MPI_COMM_WORLD,MPI_ERRORS_RETURN);
+ while ( i != TIMEOUT && MPI_Publish_name((char*)service.c_str(),MPI_INFO_NULL,_portName) != MPI_SUCCESS) {
+ i++;
+ }
+ MPI_Errhandler_set(MPI_COMM_WORLD,MPI_ERRORS_ARE_FATAL);
+ if ( i == TIMEOUT ) {
+ MPI_Close_port(_portName);
+ MPI_Finalize();
+ exit(-1);
+ }
+ _tag1 += 2;
+ _tag2 += 2;
+ return p._retn();
+}
+
+void SALOME_MPISender_i::send()
+{
+ _argsForThr=new (void *)[8];
+ _argsForThr[0]=_portName;
+ _argsForThr[1]=&_lgrTabToSend;
+ _argsForThr[2]=(void *)_tabToSend;
+ _argsForThr[3]=&_cproc;
+ _argsForThr[4]=&_tag1Inst;
+ _argsForThr[5]=&_tag2Inst;
+ _argsForThr[6]=&_com;
+ _argsForThr[7]=&_type;
+
+ _newThr=new omni_thread(SALOME_MPISender_i::myThread,_argsForThr);
+ _newThr->start();
+}
+
+void* SALOME_MPISender_i::myThread(void *args)
+{
+ void **argsTab=(void **)args;
+ long *lgrTabToSend=(long *)argsTab[1];
+ int *cproc=(int *)argsTab[3];
+ int *tag1=(int *)argsTab[4];
+ int *tag2=(int *)argsTab[5];
+ MPI_Comm *com=(MPI_Comm *)argsTab[6];
+ SALOME::TypeOfDataTransmitted *type=(SALOME::TypeOfDataTransmitted *)argsTab[7];
+
+ MPI_Comm_accept((char *)argsTab[0],MPI_INFO_NULL,0,MPI_COMM_SELF,com);
+ MPI_Send(lgrTabToSend,1,MPI_LONG,*cproc,*tag1,*com);
+ switch(*type)
+ {
+ case SALOME::DOUBLE_:
+ MPI_Send(argsTab[2],*lgrTabToSend,MPI_DOUBLE,*cproc,*tag2,*com);
+ break;
+ case SALOME::INT_:
+ MPI_Send(argsTab[2],*lgrTabToSend,MPI_INT,*cproc,*tag2,*com);
+ }
+ omni_thread::exit();
+}
+
+void SALOME_MPISender_i::close(const SALOME::MPISender::param& p)
+{
+ std::string service(p.service);
+ const char *st=p.service;
+ void *r;
+ _newThr->join(&r);
+ MPI_Comm_free(&_com);
+ MPI_Unpublish_name((char *)service.c_str(),MPI_INFO_NULL,_portName);
+ MPI_Close_port(_portName);
+ delete [] _argsForThr;
+}
+
+#endif
+
+#ifdef HAVE_SOCKET
+
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+#include <netdb.h>
+#include <unistd.h>
+
+SALOME_SocketSender_i::SALOME_SocketSender_i(SALOME::TypeOfDataTransmitted type,const void *tabToSend,long lgrTabToSend,int sizeOf):SALOME_Sender_i(type,tabToSend,lgrTabToSend,sizeOf){
+ _IPAddress = inetAddress();
+ _serverSockfd = -1;
+ _clientSockfd = -1;
+}
+
+SALOME_SocketSender_i::~SALOME_SocketSender_i(){
+}
+
+std::string SALOME_SocketSender_i::inetAddress()
+{
+ char s[256];
+ char t[INET_ADDRSTRLEN+1];
+ struct hostent *host;
+ struct in_addr saddr;
+
+ gethostname(s, 255);
+
+ *t = '\0';
+
+ saddr.s_addr = inet_addr(s);
+ if (saddr.s_addr != -1)
+ inet_ntop(AF_INET, &saddr, t, INET_ADDRSTRLEN);
+ else {
+ host = gethostbyname(s);
+ if (host != NULL)
+ inet_ntop(AF_INET, (struct in_addr *) *host->h_addr_list,
+ t, INET_ADDRSTRLEN);
+ }
+ return std::string(t);
+}
+
+SALOME::SocketSender::param * SALOME_SocketSender_i::getParam()
+{
+
+ SALOME::SocketSender::param_var p = new SALOME::SocketSender::param;
+
+ p->lstart = 0;
+ p->lend = _lgrTabToSend - 1;
+ p->myport = _port;
+ p->internet_address = CORBA::string_dup(_IPAddress.c_str());
+
+ return p._retn();
+}
+
+void SALOME_SocketSender_i::send()
+{
+ _argsForThr=new void *[6];
+ _argsForThr[0]=&_serverSockfd;
+ _argsForThr[1]=&_clientSockfd;
+ _argsForThr[2]=&_lgrTabToSend;
+ _argsForThr[3]=(void *)_tabToSend;
+ _argsForThr[4]=&_errorFlag;
+ _argsForThr[5]=&_type;
+
+ _newThr=new omni_thread(SALOME_SocketSender_i::myThread,_argsForThr);
+ _newThr->start();
+}
+
+void* SALOME_SocketSender_i::myThread(void *args)
+{
+ int n=0, m;
+ void **argsTab=(void **)args;
+ int *serverSockfd=(int *)argsTab[0];
+ int *clientSockfd=(int *)argsTab[1];
+ long *lgrTabToSend=(long *)argsTab[2];
+ void *tabToSend=argsTab[3];
+ bool *errorFlag=(bool*)argsTab[4];
+ SALOME::TypeOfDataTransmitted *type=(SALOME::TypeOfDataTransmitted *)argsTab[5];
+
+ XDR xp; /* pointeur sur le decodeur XDR */
+
+ switch(*type)
+ {
+ case SALOME::DOUBLE_:
+ xdrmem_create(&xp,(char*)tabToSend,(*lgrTabToSend)*sizeof(double),XDR_ENCODE );
+ xdr_vector( &xp, (char*)tabToSend, *lgrTabToSend, sizeof(double), (xdrproc_t)xdr_double );
+
+ *errorFlag = false;
+ while( n < *lgrTabToSend*sizeof(double) ){
+ m = write(*clientSockfd, (char*)tabToSend+n, *lgrTabToSend*sizeof(double)-n);
+ if( m < 0 ){
+ if( *clientSockfd >= 0 ){
+ ::close(*clientSockfd);
+ *clientSockfd = -1;
+ }
+ if( *serverSockfd >= 0 ){
+ ::close(*serverSockfd);
+ *serverSockfd = -1;
+ }
+ *errorFlag = true;
+ }
+ n += m;
+ }
+ xdr_destroy( &xp );
+
+ xdrmem_create(&xp,(char*)tabToSend,(*lgrTabToSend)*sizeof(double),XDR_DECODE );
+ xdr_vector( &xp, (char*)tabToSend, *lgrTabToSend, sizeof(double), (xdrproc_t)xdr_double );
+ xdr_destroy( &xp );
+ break;
+ case SALOME::INT_:
+ xdrmem_create(&xp,(char*)tabToSend,(*lgrTabToSend)*sizeof(int),XDR_ENCODE );
+ xdr_vector( &xp, (char*)tabToSend, *lgrTabToSend, sizeof(int), (xdrproc_t)xdr_int );
+
+ *errorFlag = false;
+ while( n < *lgrTabToSend*sizeof(int) ){
+ m = write(*clientSockfd, (char*)tabToSend+n, *lgrTabToSend*sizeof(int)-n);
+ if( m < 0 ){
+ if( *clientSockfd >= 0 ){
+ ::close(*clientSockfd);
+ *clientSockfd = -1;
+ }
+ if( *serverSockfd >= 0 ){
+ ::close(*serverSockfd);
+ *serverSockfd = -1;
+ }
+ *errorFlag = true;
+ }
+ n += m;
+ }
+ xdr_destroy( &xp );
+
+ xdrmem_create(&xp,(char*)tabToSend,(*lgrTabToSend)*sizeof(int),XDR_DECODE );
+ xdr_vector( &xp, (char*)tabToSend, *lgrTabToSend, sizeof(int), (xdrproc_t)xdr_int );
+ xdr_destroy( &xp );
+ }
+}
+
+void SALOME_SocketSender_i::initCom() throw(SALOME::SALOME_Exception)
+{
+ struct sockaddr_in serv_addr;
+ socklen_t n;
+ SALOME::ExceptionStruct es;
+
+ /* Ouverture de la socket */
+ _serverSockfd = socket(AF_INET , SOCK_STREAM , 0);
+ if(_serverSockfd < 0) {
+ es.type = SALOME::COMM;
+ es.text = "error Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ /* Socket structure initialisation*/
+ bzero((char*)&serv_addr,sizeof(serv_addr));
+ serv_addr.sin_family = AF_INET;
+ serv_addr.sin_port = 0; /* asking for a free port */
+ serv_addr.sin_addr.s_addr = INADDR_ANY;
+
+ /* Association of socket with a port */
+ if( ::bind(_serverSockfd, (struct sockaddr *) & serv_addr,
+ sizeof(struct sockaddr)) < 0 ) {
+ closeCom();
+ es.type = SALOME::COMM;
+ es.text = "error bind Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ /* Listening to the allocated port */
+ if( listen(_serverSockfd, 10) < 0 ) {
+ closeCom();
+ es.type = SALOME::COMM;
+ es.text = "error listen Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ /* Retrieving port number*/
+ if( getsockname(_serverSockfd, (struct sockaddr *) & serv_addr, &n) < 0 ){
+ closeCom();
+ es.type = SALOME::COMM;
+ es.text = "error getName Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ _port = htons(serv_addr.sin_port);
+ SCRUTE(_port);
+}
+
+void SALOME_SocketSender_i::acceptCom() throw(SALOME::SALOME_Exception)
+{
+ socklen_t sin_size;
+ int new_fd;
+ struct sockaddr_in client_addr;
+ SALOME::ExceptionStruct es;
+
+ sin_size = sizeof(struct sockaddr_in);
+
+ _clientSockfd = accept(_serverSockfd, (struct sockaddr *)&client_addr, &sin_size);
+ if( _clientSockfd < 0 ){
+ closeCom();
+ es.type = SALOME::COMM;
+ es.text = "error accept Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+}
+
+void SALOME_SocketSender_i::closeCom()
+{
+ if( _clientSockfd >= 0 ){
+ ::close(_clientSockfd);
+ _clientSockfd = -1;
+ }
+ if( _serverSockfd >= 0 ){
+ ::close(_serverSockfd);
+ _serverSockfd = -1;
+ }
+
+}
+
+void SALOME_SocketSender_i::endOfCom()
+{
+ void *r;
+ _newThr->join(&r);
+ if(_errorFlag)
+ {
+ SALOME::ExceptionStruct es;
+ es.type = SALOME::COMM;
+ es.text = "error write Socket exception";
+ throw SALOME::SALOME_Exception(es);
+ }
+ delete [] _argsForThr;
+}
+
+#endif
--- /dev/null
+#ifndef _SALOME_COMM_I_HXX_
+#define _SALOME_COMM_I_HXX_
+
+#include <set.h>
+#include <string>
+#include <SALOMEconfig.h>
+#include CORBA_SERVER_HEADER(SALOME_Comm)
+#ifdef HAVE_MPI2
+#include "mpi.h"
+#endif
+
+#define TIMEOUT 20
+
+using namespace std;
+
+/*!
+ Generic servant class for senders that factorizes all the common methods and attributes necessary to senders.
+ All servant classes for senders have to inheritate from it.
+ */
+class SALOME_Sender_i : public virtual POA_SALOME::Sender,
+ public PortableServer::RefCountServantBase {
+protected:
+ /*! Pointer to the generic array to transmit*/
+ const void *_tabToSend;
+ /*! Length of the generic array to transmit*/
+ long _lgrTabToSend;
+ /*! it represents the sizeof() of each component of the generic array:\n
+ Practically in terms of bytes the size to be transmitted is _lgrTabToSend*_sizeOf
+ */
+ int _sizeOf;
+ /*! Type the component of the array*/
+ SALOME::TypeOfDataTransmitted _type;
+
+ SALOME_Sender_i(SALOME::TypeOfDataTransmitted type,const void *tabToSend,long lgrTabToSend,int sizeOf);
+public:
+ const void *getData(long &size) const;
+ int getSizeOf() const;
+ void release();
+ SALOME::TypeOfDataTransmitted getTypeOfDataTransmitted();
+ SALOME::Sender_ptr buildOtherWithProtocol(SALOME::TypeOfCommunication type);
+ static SALOME_Sender_i *find(SALOME::Sender_ptr pCorba);
+};
+
+/*! Servant class for CORBA sender for double* when no copy of array _tabToSend is required, that is to say double and CORBA::Double are binary equal.
+ */
+class SALOME_CorbaDoubleNCSender_i : public POA_SALOME::CorbaDoubleNCSender,
+ public SALOME_Sender_i
+{
+public:
+ SALOME_CorbaDoubleNCSender_i(const double *tabToSend,long lgrTabToSend);
+ ~SALOME_CorbaDoubleNCSender_i();
+ CORBA::ULong getSize();
+ SALOME::vectorOfDouble* sendPart(CORBA::ULong offset, CORBA::ULong length);
+ SALOME::vectorOfDouble* send();
+};
+
+/*! Servant class for CORBA sender for double* when copy of array _tabToSend is required, that is to say double and CORBA::Double are NOT binary equal.
+ */
+class SALOME_CorbaDoubleCSender_i : public POA_SALOME::CorbaDoubleCSender,
+ public SALOME_Sender_i
+{
+public:
+ SALOME_CorbaDoubleCSender_i(const double *tabToSend,const long lgrTabToSend);
+ ~SALOME_CorbaDoubleCSender_i();
+ CORBA::ULong getSize();
+ SALOME::vectorOfDouble* sendPart(CORBA::ULong offset, CORBA::ULong length);
+};
+
+/*! Servant class for CORBA sender for int* when no copy of array _tabToSend is required, that is to say int and CORBA::Long are binary equal.
+ */
+class SALOME_CorbaLongNCSender_i : public POA_SALOME::CorbaLongNCSender,
+ public SALOME_Sender_i
+{
+public:
+ SALOME_CorbaLongNCSender_i(const int *tabToSend,const long lgrTabToSend);
+ ~SALOME_CorbaLongNCSender_i();
+ CORBA::ULong getSize();
+ SALOME::vectorOfLong* sendPart(CORBA::ULong offset, CORBA::ULong length);
+ SALOME::vectorOfLong* send();
+};
+
+/*! Servant class for CORBA sender for int* when copy of array _tabToSend is required, that is to say int and CORBA::Long are NOT binary equal.
+ */
+class SALOME_CorbaLongCSender_i : public POA_SALOME::CorbaLongCSender,
+ public SALOME_Sender_i
+{
+public:
+ SALOME_CorbaLongCSender_i(const int *tabToSend,long lgrTabToSend);
+ ~SALOME_CorbaLongCSender_i();
+ CORBA::ULong getSize();
+ SALOME::vectorOfLong* sendPart(CORBA::ULong offset, CORBA::ULong length);
+ SALOME::CorbaLongCSender_ptr _this();
+};
+
+#ifdef HAVE_MPI2
+
+/*! Servant class of sender using MPI2.
+ */
+class SALOME_MPISender_i : public POA_SALOME::MPISender,
+ public SALOME_Sender_i
+{
+private:
+ static unsigned long _tag1;
+ static unsigned long _tag2;
+ /*! Name of the port opened*/
+ char *_portName;
+ int _cproc;
+ /*! Tag 1 that identifies the transfert*/
+ int _tag1Inst;
+ /*! Tag 2 that identifies the transfert*/
+ int _tag2Inst;
+ /*! MPI communicator*/
+ MPI_Comm _com;
+ /*! Array of pointer for asynchronous invocation with omnithread*/
+ void **_argsForThr;
+ /*! Pointer to thread created on asynchronous invocation*/
+ omni_thread *_newThr;
+public:
+ SALOME_MPISender_i(SALOME::TypeOfDataTransmitted type,const void *tabToSend,long lgrTabToSend,int sizeOf);
+ ~SALOME_MPISender_i();
+ SALOME::MPISender::param* getParam();
+ void send();
+ void close(const SALOME::MPISender::param& p);
+private:
+ static void* myThread(void *args);
+};
+
+#endif
+
+#ifdef HAVE_SOCKET
+
+/*! Servant class of sender using Sockets.
+ */
+class SALOME_SocketSender_i : public POA_SALOME::SocketSender,
+ public SALOME_Sender_i
+{
+private:
+ int _serverSockfd;
+ int _clientSockfd;
+ int _port;
+ std::string _IPAddress;
+ void **_argsForThr;
+ omni_thread *_newThr;
+ bool _errorFlag;
+public:
+ SALOME_SocketSender_i(SALOME::TypeOfDataTransmitted type,const void *tabToSend,long lgrTabToSend,int sizeOf);
+ ~SALOME_SocketSender_i();
+ SALOME::SocketSender::param* getParam();
+ void send();
+ void initCom() throw(SALOME::SALOME_Exception);
+ void acceptCom() throw(SALOME::SALOME_Exception);
+ void endOfCom();
+ void closeCom();
+private:
+ static void* myThread(void *args);
+ std::string inetAddress();
+};
+
+#endif
+
+#endif
+
--- /dev/null
+#include "SenderFactory.hxx"
+#include "utilities.h"
+#include "SALOMEMultiComm.hxx"
+#include "SALOME_Comm_i.hxx"
+
+#ifdef COMP_CORBA_DOUBLE
+#define SALOME_CorbaDoubleSender SALOME_CorbaDoubleNCSender_i
+#else
+#define SALOME_CorbaDoubleSender SALOME_CorbaDoubleCSender_i
+#endif
+
+#ifdef COMP_CORBA_LONG
+#define SALOME_CorbaLongSender SALOME_CorbaLongNCSender_i
+#else
+#define SALOME_CorbaLongSender SALOME_CorbaLongCSender_i
+#endif
+
+SALOME::Sender_ptr SenderFactory::buildSender(SALOMEMultiComm &multiCommunicator,const double *tab,long lgr)throw(MultiCommException){
+ switch(multiCommunicator.getProtocol())
+ {
+ case SALOME::CORBA_:
+ {
+ SALOME_CorbaDoubleSender * retc=new SALOME_CorbaDoubleSender(tab,lgr);
+ return retc->_this();
+ }
+#ifdef HAVE_MPI2
+ case SALOME::MPI_:
+ {
+ SALOME_MPISender_i* retm=new SALOME_MPISender_i(SALOME::DOUBLE_,tab,lgr,sizeof(double));
+ return retm->_this();
+ }
+#endif
+#ifdef HAVE_SOCKET
+ case SALOME::SOCKET_:
+ {
+ SALOME_SocketSender_i* rets=new SALOME_SocketSender_i(SALOME::DOUBLE_,tab,lgr,sizeof(double));
+ return rets->_this();
+ }
+#endif
+ default:
+ {
+ multiCommunicator.setProtocol(SALOME::CORBA_);
+ MESSAGE("PROTOCOL CHANGED TO CORBA");
+ SALOME_CorbaDoubleSender * retc=new SALOME_CorbaDoubleSender(tab,lgr);
+ return retc->_this();
+ }
+// throw MultiCommException("Communication protocol not implemented");
+ }
+}
+
+SALOME::Sender_ptr SenderFactory::buildSender(SALOMEMultiComm &multiCommunicator,const int *tab,long lgr)throw(MultiCommException){
+ switch(multiCommunicator.getProtocol())
+ {
+ case SALOME::CORBA_:
+ {
+ SALOME_CorbaLongSender * retc=new SALOME_CorbaLongSender(tab,lgr);
+ return retc->_this();
+ }
+#ifdef HAVE_MPI2
+ case SALOME::MPI_:
+ {
+ SALOME_MPISender_i* retm=new SALOME_MPISender_i(SALOME::INT_,tab,lgr,sizeof(int));
+ return retm->_this();
+ }
+#endif
+#ifdef HAVE_SOCKET
+ case SALOME::SOCKET_:
+ {
+ SALOME_SocketSender_i* rets=new SALOME_SocketSender_i(SALOME::INT_,tab,lgr,sizeof(int));
+ return rets->_this();
+ }
+#endif
+ default:
+ {
+ multiCommunicator.setProtocol(SALOME::CORBA_);
+ SALOME_CorbaLongSender * retc=new SALOME_CorbaLongSender(tab,lgr);
+ return retc->_this();
+ }
+// throw MultiCommException("Communication protocol not implemented");
+ }
+ }
+
+SALOME::Sender_ptr SenderFactory::buildSender(SALOME::TypeOfCommunication NewType,SALOME_Sender_i *src)
+{
+ SALOMEMultiComm mc(NewType);
+ long n;
+ const void *data=src->getData(n);
+ switch(src->getTypeOfDataTransmitted())
+ {
+ case SALOME::DOUBLE_:
+ return buildSender(mc,(const double *)data,n);
+ case SALOME::INT_:
+ return buildSender(mc,(const int *)data,n);
+ }
+
+}
+
+
--- /dev/null
+#ifndef _SENDERFACTORY_HXX_
+#define _SENDERFACTORY_HXX_
+
+#include "MultiCommException.hxx"
+#include <SALOMEconfig.h>
+#include CORBA_SERVER_HEADER(SALOME_Comm)
+
+class SALOMEMultiComm;
+
+class SALOME_Sender_i;
+
+/*!
+ This class implements the factory pattern of GoF by making a sender by giving an array and a communicator.It completely hides the type of sender from the user.
+ */
+class SenderFactory
+{
+public:
+ static SALOME::Sender_ptr buildSender(SALOMEMultiComm &multiCommunicator,const double *tab,long lgr) throw(MultiCommException);
+ static SALOME::Sender_ptr buildSender(SALOMEMultiComm &multiCommunicator,const int *tab,long lgr) throw(MultiCommException);
+ static SALOME::Sender_ptr buildSender(SALOME::TypeOfCommunication NewType,SALOME_Sender_i *src);
+};
+
+#endif
+
--- /dev/null
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+
+
+#include <stdexcept>
+#include <CORBA.h>
+
+#include "CASCatch_SignalsHandler.h" // CAREFUL ! position of this file is critic : see Lucien PIGNOLONI / OCC
+
+
+extern "C" void HandleServerSideSignals(CORBA::ORB_ptr theORB)
+{
+ CASCatch_SignalsHandler aSignalsHandler;
+ try {
+ theORB->run();
+ }catch(Standard_Failure){
+ Handle(Standard_Failure) aFail = Standard_Failure::Caught();
+ throw std::runtime_error(aFail->GetMessageString());
+ }
+}
--- /dev/null
+ THE Q PUBLIC LICENSE
+ version 1.0
+
+ Copyright (C) 1999-2000 Trolltech AS, Norway.
+ Everyone is permitted to copy and
+ distribute this license document.
+
+The intent of this license is to establish freedom to share and change the
+software regulated by this license under the open source model.
+
+This license applies to any software containing a notice placed by the
+copyright holder saying that it may be distributed under the terms of
+the Q Public License version 1.0. Such software is herein referred to as
+the Software. This license covers modification and distribution of the
+Software, use of third-party application programs based on the Software,
+and development of free software which uses the Software.
+
+ Granted Rights
+
+1. You are granted the non-exclusive rights set forth in this license
+ provided you agree to and comply with any and all conditions in this
+ license. Whole or partial distribution of the Software, or software
+ items that link with the Software, in any form signifies acceptance of
+ this license.
+
+2. You may copy and distribute the Software in unmodified form provided
+ that the entire package, including - but not restricted to - copyright,
+ trademark notices and disclaimers, as released by the initial developer
+ of the Software, is distributed.
+
+3. You may make modifications to the Software and distribute your
+ modifications, in a form that is separate from the Software, such as
+ patches. The following restrictions apply to modifications:
+
+ a. Modifications must not alter or remove any copyright notices in
+ the Software.
+
+ b. When modifications to the Software are released under this
+ license, a non-exclusive royalty-free right is granted to the
+ initial developer of the Software to distribute your modification
+ in future versions of the Software provided such versions remain
+ available under these terms in addition to any other license(s) of
+ the initial developer.
+
+4. You may distribute machine-executable forms of the Software or
+ machine-executable forms of modified versions of the Software, provided
+ that you meet these restrictions:
+
+ a. You must include this license document in the distribution.
+
+ b. You must ensure that all recipients of the machine-executable forms
+ are also able to receive the complete machine-readable source code
+ to the distributed Software, including all modifications, without
+ any charge beyond the costs of data transfer, and place prominent
+ notices in the distribution explaining this.
+
+ c. You must ensure that all modifications included in the
+ machine-executable forms are available under the terms of this
+ license.
+
+5. You may use the original or modified versions of the Software to
+ compile, link and run application programs legally developed by you
+ or by others.
+
+6. You may develop application programs, reusable components and other
+ software items that link with the original or modified versions of the
+ Software. These items, when distributed, are subject to the following
+ requirements:
+
+ a. You must ensure that all recipients of machine-executable forms of
+ these items are also able to receive and use the complete
+ machine-readable source code to the items without any charge
+ beyond the costs of data transfer.
+
+ b. You must explicitly license all recipients of your items to use
+ and re-distribute original and modified versions of the items in
+ both machine-executable and source code forms. The recipients must
+ be able to do so without any charges whatsoever, and they must be
+ able to re-distribute to anyone they choose.
+
+
+ c. If the items are not available to the general public, and the
+ initial developer of the Software requests a copy of the items,
+ then you must supply one.
+
+ Limitations of Liability
+
+In no event shall the initial developers or copyright holders be liable
+for any damages whatsoever, including - but not restricted to - lost
+revenue or profits or other direct, indirect, special, incidental or
+consequential damages, even if they have been advised of the possibility
+of such damages, except to the extent invariable law, if any, provides
+otherwise.
+
+ No Warranty
+
+The Software and this license document are provided AS IS with NO WARRANTY
+OF ANY KIND, INCLUDING THE WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS
+FOR A PARTICULAR PURPOSE.
+ Choice of Law
+
+This license is governed by the Laws of Norway. Disputes shall be settled
+by Oslo City Court.
--- /dev/null
+This package includes the msg2qm tool for resources compiling.
+It is a part of Qt 3.0.5 toolkit.
+The files in this package are distributed under conditions of the Q Public License.
\ No newline at end of file
--- /dev/null
+// SALOME OCCViewer : build OCC Viewer into Salome desktop
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : OCCViewer_Prs.cxx
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#include "OCCViewer_Prs.h"
+
+//==========================================================
+/*!
+ * OCCViewer_Prs::OCCViewer_Prs
+ * Default constructor
+ */
+//==========================================================
+OCCViewer_Prs::OCCViewer_Prs()
+{
+ myToActivate = true;
+}
+
+//==========================================================
+/*!
+ * OCCViewer_Prs::OCCViewer_Prs
+ * Standard constructor
+ */
+//==========================================================
+OCCViewer_Prs::OCCViewer_Prs( const Handle(AIS_InteractiveObject)& obj )
+{
+ AddObject( obj );
+}
+
+//==========================================================
+/*!
+ * OCCViewer_Prs::~OCCViewer_Prs
+ * Destructor
+ */
+//==========================================================
+OCCViewer_Prs::~OCCViewer_Prs()
+{
+ myObjects.Clear();
+}
+
+//==========================================================
+/*!
+ * OCCViewer_Prs::GetObjects
+ * Get interactive objects list
+ */
+//==========================================================
+void OCCViewer_Prs::GetObjects( AIS_ListOfInteractive& list ) const
+{
+ list = myObjects;
+}
+
+//==========================================================
+/*!
+ * OCCViewer_Prs::AddObject
+ * Add interactive object
+ */
+//==========================================================
+void OCCViewer_Prs::AddObject( const Handle(AIS_InteractiveObject)& obj )
+{
+ myObjects.Append( obj );
+}
+
+//==========================================================
+/*!
+ * OCCViewer_Prs::IsNull
+ * Return 0 if list of the interactive objects is empty
+ * [ Reimplemented from SALOME_Prs ]
+ */
+//==========================================================
+bool OCCViewer_Prs::IsNull() const
+{
+ return myObjects.IsEmpty();
+}
+
+//=================================================================
+/*!
+ * GEOM_Displayer::SetToActivate
+ * This method is used for activisation/deactivisation of
+ * objects in the moment of displaying
+*/
+//=================================================================
+void OCCViewer_Prs::SetToActivate( const bool toActivate )
+{
+ myToActivate = toActivate;
+}
+bool OCCViewer_Prs::ToActivate() const
+{
+ return myToActivate;
+}
--- /dev/null
+// SALOME OCCViewer : build OCC Viewer into Salome desktop
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : OCCViewer_Prs.h
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#ifndef OCCVIEWER_PRS_H
+#define OCCVIEWER_PRS_H
+
+#include "SALOME_Prs.h"
+
+#include <AIS_InteractiveObject.hxx>
+#include <AIS_ListOfInteractive.hxx>
+
+class OCCViewer_Prs : public SALOME_OCCPrs
+{
+public:
+ OCCViewer_Prs();
+ // Default constructor
+ OCCViewer_Prs( const Handle(AIS_InteractiveObject)& obj );
+ // Standard constructor
+ ~OCCViewer_Prs();
+ // Destructor
+
+ void GetObjects( AIS_ListOfInteractive& list ) const;
+ // Get interactive objects list
+ void AddObject( const Handle(AIS_InteractiveObject)& obj );
+ // Add interactive object
+
+ bool IsNull() const;
+ // Reimplemented from SALOME_Prs
+
+ /* This method is used for activisation/deactivisation of
+ objects in the moment of displaying */
+ void SetToActivate( const bool );
+ bool ToActivate() const;
+
+private:
+ AIS_ListOfInteractive myObjects; // list of interactive objects
+ bool myToActivate;
+};
+
+#endif
+
+
+
+
--- /dev/null
+ THE Q PUBLIC LICENSE
+ version 1.0
+
+ Copyright (C) 1999-2000 Trolltech AS, Norway.
+ Everyone is permitted to copy and
+ distribute this license document.
+
+The intent of this license is to establish freedom to share and change the
+software regulated by this license under the open source model.
+
+This license applies to any software containing a notice placed by the
+copyright holder saying that it may be distributed under the terms of
+the Q Public License version 1.0. Such software is herein referred to as
+the Software. This license covers modification and distribution of the
+Software, use of third-party application programs based on the Software,
+and development of free software which uses the Software.
+
+ Granted Rights
+
+1. You are granted the non-exclusive rights set forth in this license
+ provided you agree to and comply with any and all conditions in this
+ license. Whole or partial distribution of the Software, or software
+ items that link with the Software, in any form signifies acceptance of
+ this license.
+
+2. You may copy and distribute the Software in unmodified form provided
+ that the entire package, including - but not restricted to - copyright,
+ trademark notices and disclaimers, as released by the initial developer
+ of the Software, is distributed.
+
+3. You may make modifications to the Software and distribute your
+ modifications, in a form that is separate from the Software, such as
+ patches. The following restrictions apply to modifications:
+
+ a. Modifications must not alter or remove any copyright notices in
+ the Software.
+
+ b. When modifications to the Software are released under this
+ license, a non-exclusive royalty-free right is granted to the
+ initial developer of the Software to distribute your modification
+ in future versions of the Software provided such versions remain
+ available under these terms in addition to any other license(s) of
+ the initial developer.
+
+4. You may distribute machine-executable forms of the Software or
+ machine-executable forms of modified versions of the Software, provided
+ that you meet these restrictions:
+
+ a. You must include this license document in the distribution.
+
+ b. You must ensure that all recipients of the machine-executable forms
+ are also able to receive the complete machine-readable source code
+ to the distributed Software, including all modifications, without
+ any charge beyond the costs of data transfer, and place prominent
+ notices in the distribution explaining this.
+
+ c. You must ensure that all modifications included in the
+ machine-executable forms are available under the terms of this
+ license.
+
+5. You may use the original or modified versions of the Software to
+ compile, link and run application programs legally developed by you
+ or by others.
+
+6. You may develop application programs, reusable components and other
+ software items that link with the original or modified versions of the
+ Software. These items, when distributed, are subject to the following
+ requirements:
+
+ a. You must ensure that all recipients of machine-executable forms of
+ these items are also able to receive and use the complete
+ machine-readable source code to the items without any charge
+ beyond the costs of data transfer.
+
+ b. You must explicitly license all recipients of your items to use
+ and re-distribute original and modified versions of the items in
+ both machine-executable and source code forms. The recipients must
+ be able to do so without any charges whatsoever, and they must be
+ able to re-distribute to anyone they choose.
+
+
+ c. If the items are not available to the general public, and the
+ initial developer of the Software requests a copy of the items,
+ then you must supply one.
+
+ Limitations of Liability
+
+In no event shall the initial developers or copyright holders be liable
+for any damages whatsoever, including - but not restricted to - lost
+revenue or profits or other direct, indirect, special, incidental or
+consequential damages, even if they have been advised of the possibility
+of such damages, except to the extent invariable law, if any, provides
+otherwise.
+
+ No Warranty
+
+The Software and this license document are provided AS IS with NO WARRANTY
+OF ANY KIND, INCLUDING THE WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS
+FOR A PARTICULAR PURPOSE.
+ Choice of Law
+
+This license is governed by the Laws of Norway. Disputes shall be settled
+by Oslo City Court.
--- /dev/null
+This package includes the patch for Qt toolkit.
+The files in this package are distributed under conditions of the Q Public License.
\ No newline at end of file
--- /dev/null
+/////////////////////////////////////////////////////////////////////////////
+// Module : PatchQt
+// File : qfiledialogP.cxx
+// Description : the patch for Qt's QFileDialog class (qfiledialog.cpp)
+/////////////////////////////////////////////////////////////////////////////
+
+/****************************************************************************
+** $Id$
+**
+** Implementation of QFileDialog class
+**
+** Created : 950429
+**
+** Copyright (C) 1992-2000 Trolltech AS. All rights reserved.
+**
+** This file is part of the dialogs module of the Qt GUI Toolkit.
+**
+** This file may be distributed under the terms of the Q Public License
+** as defined by Trolltech AS of Norway and appearing in the file
+** LICENSE.QPL included in the packaging of this file.
+**
+** This file may be distributed and/or modified under the terms of the
+** GNU General Public License version 2 as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL included in the
+** packaging of this file.
+**
+** Licensees holding valid Qt Enterprise Edition or Qt Professional Edition
+** licenses may use this file in accordance with the Qt Commercial License
+** Agreement provided with the Software.
+**
+** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
+** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+**
+** See http://www.trolltech.com/pricing.html or email sales@trolltech.com for
+** information about Qt Commercial License Agreements.
+** See http://www.trolltech.com/qpl/ for QPL licensing information.
+** See http://www.trolltech.com/gpl/ for GPL licensing information.
+**
+** Contact info@trolltech.com if any conditions of this licensing are
+** not clear to you.
+**
+**********************************************************************/
+
+#include "qplatformdefs.h"
+
+// Solaris redefines connect -> __xnet_connect with _XOPEN_SOURCE_EXTENDED.
+#if defined(connect)
+#undef connect
+#endif
+
+#include "qfiledialogP.h"
+
+#ifndef QT_NO_FILEDIALOG
+
+#include "qlineedit.h"
+#include "qcombobox.h"
+#include "qlistview.h"
+#include "qlistbox.h"
+#include "qlabel.h"
+#include "qpushbutton.h"
+#include "qtoolbutton.h"
+#include "qmessagebox.h"
+#include "qapplication.h"
+#include "private/qapplication_p.h"
+#include "qlayout.h"
+#include "qbitmap.h"
+#include "qpopupmenu.h"
+#include "qwidgetstack.h"
+#include "qbuttongroup.h"
+#include "qptrvector.h"
+#include "qregexp.h"
+#include "qstrlist.h"
+#include "qtimer.h"
+#include "qvbox.h"
+#include "qhbox.h"
+#include "qtooltip.h"
+#include "qheader.h"
+#include "qdragobject.h"
+#include "qmime.h"
+#include "qprogressbar.h"
+#include "qfile.h"
+#include "qcstring.h"
+#include "qobjectlist.h"
+#include "qcheckbox.h"
+#include "qsplitter.h"
+#include "qmap.h"
+#include "qnetworkprotocol.h"
+#include "qsemimodal.h"
+#include "qpainter.h"
+#include "qcleanuphandler.h"
+#include "qstyle.h"
+#include "qcursor.h"
+
+#ifndef Q_OS_TEMP
+#include <time.h>
+#endif
+#include <ctype.h>
+#include <stdlib.h>
+
+#ifdef Q_WS_MAC
+#include "qt_mac.h"
+#undef check
+#endif
+
+#ifdef Q_WS_WIN
+#include "qt_windows.h"
+#endif
+
+/* XPM */
+static const char * const start_xpm[]={
+ "16 15 8 1",
+ "a c #cec6bd",
+ "# c #000000",
+ "e c #ffff00",
+ "b c #999999",
+ "f c #cccccc",
+ "d c #dcdcdc",
+ "c c #ffffff",
+ ". c None",
+ ".....######aaaaa",
+ "...bb#cccc##aaaa",
+ "..bcc#cccc#d#aaa",
+ ".bcef#cccc#dd#aa",
+ ".bcfe#cccc#####a",
+ ".bcef#ccccccccc#",
+ "bbbbbbbbbbbbccc#",
+ "bccccccccccbbcc#",
+ "bcefefefefee#bc#",
+ ".bcefefefefef#c#",
+ ".bcfefefefefe#c#",
+ "..bcfefefefeeb##",
+ "..bbbbbbbbbbbbb#",
+ "...#############",
+ "................"};
+
+/* XPM */
+static const char * const end_xpm[]={
+ "16 15 9 1",
+ "d c #a0a0a0",
+ "c c #c3c3c3",
+ "# c #cec6bd",
+ ". c #000000",
+ "f c #ffff00",
+ "e c #999999",
+ "g c #cccccc",
+ "b c #ffffff",
+ "a c None",
+ "......####aaaaaa",
+ ".bbbb..###aaaaaa",
+ ".bbbb.c.##aaaaaa",
+ ".bbbb....ddeeeea",
+ ".bbbbbbb.bbbbbe.",
+ ".bbbbbbb.bcfgfe.",
+ "eeeeeeeeeeeeefe.",
+ "ebbbbbbbbbbeege.",
+ "ebfgfgfgfgff.ee.",
+ "aebfgfgfgfgfg.e.",
+ "aebgfgfgfgfgf.e.",
+ "aaebgfgfgfgffe..",
+ "aaeeeeeeeeeeeee.",
+ "aaa.............",
+ "aaaaaaaaaaaaaaaa"};
+
+/* XPM */
+static const char* const open_xpm[]={
+ "16 16 6 1",
+ ". c None",
+ "b c #ffff00",
+ "d c #000000",
+ "* c #999999",
+ "c c #cccccc",
+ "a c #ffffff",
+ "................",
+ "................",
+ "...*****........",
+ "..*aaaaa*.......",
+ ".*abcbcba******.",
+ ".*acbcbcaaaaaa*d",
+ ".*abcbcbcbcbcb*d",
+ "*************b*d",
+ "*aaaaaaaaaa**c*d",
+ "*abcbcbcbcbbd**d",
+ ".*abcbcbcbcbcd*d",
+ ".*acbcbcbcbcbd*d",
+ "..*acbcbcbcbb*dd",
+ "..*************d",
+ "...ddddddddddddd",
+ "................"};
+
+/* XPM */
+static const char * const link_dir_xpm[]={
+ "16 16 10 1",
+ "h c #808080",
+ "g c #a0a0a0",
+ "d c #000000",
+ "b c #ffff00",
+ "f c #303030",
+ "# c #999999",
+ "a c #cccccc",
+ "e c #585858",
+ "c c #ffffff",
+ ". c None",
+ "................",
+ "................",
+ "..#####.........",
+ ".#ababa#........",
+ "#abababa######..",
+ "#cccccccccccc#d.",
+ "#cbababababab#d.",
+ "#cabababababa#d.",
+ "#cbababdddddddd.",
+ "#cababadccccccd.",
+ "#cbababdcececcd.",
+ "#cababadcefdfcd.",
+ "#cbababdccgdhcd.",
+ "#######dccchccd.",
+ ".dddddddddddddd.",
+ "................"};
+
+/* XPM */
+static const char * const link_file_xpm[]={
+ "16 16 10 1",
+ "h c #808080",
+ "g c #a0a0a0",
+ "d c #c3c3c3",
+ ". c #7f7f7f",
+ "c c #000000",
+ "b c #bfbfbf",
+ "f c #303030",
+ "e c #585858",
+ "a c #ffffff",
+ "# c None",
+ "################",
+ "..........######",
+ ".aaaaaaaab.#####",
+ ".aaaaaaaaba.####",
+ ".aaaaaaaacccc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaadc###",
+ ".aaaaaaaaaadc###",
+ ".aaaacccccccc###",
+ ".aaaacaaaaaac###",
+ ".aaaacaeaeaac###",
+ ".aaaacaefcfac###",
+ ".aaaacaagchac###",
+ ".ddddcaaahaac###",
+ "ccccccccccccc###"};
+
+/* XPM */
+static const char* const file_xpm[]={
+ "16 16 5 1",
+ ". c #7f7f7f",
+ "# c None",
+ "c c #000000",
+ "b c #bfbfbf",
+ "a c #ffffff",
+ "################",
+ "..........######",
+ ".aaaaaaaab.#####",
+ ".aaaaaaaaba.####",
+ ".aaaaaaaacccc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".aaaaaaaaaabc###",
+ ".bbbbbbbbbbbc###",
+ "ccccccccccccc###"};
+
+/* XPM */
+static const char * const closed_xpm[]={
+ "16 16 6 1",
+ ". c None",
+ "b c #ffff00",
+ "d c #000000",
+ "* c #999999",
+ "a c #cccccc",
+ "c c #ffffff",
+ "................",
+ "................",
+ "..*****.........",
+ ".*ababa*........",
+ "*abababa******..",
+ "*cccccccccccc*d.",
+ "*cbababababab*d.",
+ "*cabababababa*d.",
+ "*cbababababab*d.",
+ "*cabababababa*d.",
+ "*cbababababab*d.",
+ "*cabababababa*d.",
+ "*cbababababab*d.",
+ "**************d.",
+ ".dddddddddddddd.",
+ "................"};
+
+
+/* XPM */
+static const char* const cdtoparent_xpm[]={
+ "15 13 3 1",
+ ". c None",
+ "* c #000000",
+ "a c #ffff99",
+ "..*****........",
+ ".*aaaaa*.......",
+ "***************",
+ "*aaaaaaaaaaaaa*",
+ "*aaaa*aaaaaaaa*",
+ "*aaa***aaaaaaa*",
+ "*aa*****aaaaaa*",
+ "*aaaa*aaaaaaaa*",
+ "*aaaa*aaaaaaaa*",
+ "*aaaa******aaa*",
+ "*aaaaaaaaaaaaa*",
+ "*aaaaaaaaaaaaa*",
+ "***************"};
+
+
+/* XPM */
+static const char* const newfolder_xpm[] = {
+ "15 14 4 1",
+ " c None",
+ ". c #000000",
+ "+ c #FFFF00",
+ "@ c #FFFFFF",
+ " . ",
+ " ",
+ " . ",
+ " . . ",
+ " .... . . . ",
+ " .+@+@. . . ",
+ ".......... . .",
+ ".@+@+@+@+@.. ",
+ ".+@+@+@+@+. . ",
+ ".@+@+@+@+@. . ",
+ ".+@+@+@+@+. ",
+ ".@+@+@+@+@. ",
+ ".+@+@+@+@+. ",
+ "........... "};
+
+/* XPM */
+static const char* const detailedview_xpm[]={
+ "14 11 3 1",
+ ". c None",
+ "* c #000000",
+ "a c #000099",
+ ".****.***.***.",
+ "..............",
+ "aaaaaaaaaaaaaa",
+ "..............",
+ ".****.***.***.",
+ "..............",
+ ".****.***.***.",
+ "..............",
+ ".****.***.***.",
+ "..............",
+ ".****.***.***."};
+
+/* XPM */
+static const char* const previewinfoview_xpm[]={
+ "13 13 4 1",
+ ". c #00007f",
+ "a c black",
+ "# c #cec6bd",
+ "b c #000000",
+ "..#####aaaaaa",
+ ".#.#bb#a#####",
+ "...####a#bbb#",
+ "#######a#####",
+ "#######a#bb##",
+ "..#####a#####",
+ ".#.#bb#a#bbb#",
+ "...####a#####",
+ "#######a#bb##",
+ "#######a#####",
+ "..#####a#bbb#",
+ ".#.#bb#a#####",
+ "...####aaaaaa"};
+
+/* XPM */
+static const char* const previewcontentsview_xpm[]={
+ "14 13 5 1",
+ ". c #00007f",
+ "a c black",
+ "c c #7f007f",
+ "# c #cec6bd",
+ "b c #000000",
+ "..#####aaaaaaa",
+ ".#.#bb#a#####a",
+ "...####a#ccc#a",
+ "#######a#ccc#a",
+ "#######a#####a",
+ "..#####a#bbb#a",
+ ".#.#bb#a#####a",
+ "...####a#bbb#a",
+ "#######a#####a",
+ "#######a#bbb#a",
+ "..#####a#####a",
+ ".#.#bb#a#####a",
+ "...####aaaaaaa"};
+
+/* XPM */
+static const char* const mclistview_xpm[]={
+ "15 11 4 1",
+ "* c None",
+ "b c #000000",
+ ". c #000099",
+ "a c #ffffff",
+ "...*****...****",
+ ".a.*bbb*.a.*bbb",
+ "...*****...****",
+ "***************",
+ "...*****...****",
+ ".a.*bbb*.a.*bbb",
+ "...*****...****",
+ "***************",
+ "...*****...****",
+ ".a.*bbb*.a.*bbb",
+ "...*****...****"};
+
+/* XPM */
+static const char * const back_xpm [] = {
+ "13 11 3 1",
+ "a c #00ffff",
+ "# c #000000",
+ ". c None",
+ ".....#.......",
+ "....##.......",
+ "...#a#.......",
+ "..#aa########",
+ ".#aaaaaaaaaa#",
+ "#aaaaaaaaaaa#",
+ ".#aaaaaaaaaa#",
+ "..#aa########",
+ "...#a#.......",
+ "....##.......",
+ ".....#......."};
+
+static QPixmap * openFolderIcon = 0;
+static QPixmap * closedFolderIcon = 0;
+static QPixmap * detailViewIcon = 0;
+static QPixmap * multiColumnListViewIcon = 0;
+static QPixmap * cdToParentIcon = 0;
+static QPixmap * newFolderIcon = 0;
+static QPixmap * fifteenTransparentPixels = 0;
+static QPixmap * symLinkDirIcon = 0;
+static QPixmap * symLinkFileIcon = 0;
+static QPixmap * fileIcon = 0;
+static QPixmap * startCopyIcon = 0;
+static QPixmap * endCopyIcon = 0;
+static QPixmap * previewContentsViewIcon = 0;
+static QPixmap * previewInfoViewIcon = 0;
+static QPixmap *goBackIcon = 0;
+static QFileIconProviderP * fileIconProvider = 0;
+static QSize *lastSize = 0;
+static QString * workingDirectory = 0;
+
+static bool bShowHiddenFiles = FALSE;
+static int sortFilesBy = (int)QDir::Name;
+static bool sortAscending = TRUE;
+static bool detailViewMode = FALSE;
+
+static QCleanupHandler<QPixmap> qfd_cleanup_pixmap;
+static QCleanupHandler<QSize> qfd_cleanup_size;
+static QCleanupHandler<QString> qfd_cleanup_string;
+
+static bool isDirectoryMode( int m )
+{
+ return m == QFileDialogP::Directory || m == QFileDialogP::DirectoryOnly;
+}
+
+#if defined(Q_WS_WIN)
+
+class QWindowsIconProvider : public QFileIconProviderP
+{
+public:
+ QWindowsIconProvider( QObject *parent=0, const char *name=0 );
+ ~QWindowsIconProvider();
+
+ const QPixmap * pixmap( const QFileInfo &fi );
+
+private:
+ QPixmap defaultFolder;
+ QPixmap defaultFile;
+ QPixmap defaultExe;
+ QPixmap pix;
+ int pixw, pixh;
+ QMap< QString, QPixmap > cache;
+};
+#endif
+
+static void makeVariables() {
+ if ( !openFolderIcon ) {
+ workingDirectory = new QString( QDir::currentDirPath() );
+ qfd_cleanup_string.add( &workingDirectory );
+
+ openFolderIcon = new QPixmap( (const char **)open_xpm);
+ qfd_cleanup_pixmap.add( &openFolderIcon );
+ symLinkDirIcon = new QPixmap( (const char **)link_dir_xpm);
+ qfd_cleanup_pixmap.add( &symLinkDirIcon );
+ symLinkFileIcon = new QPixmap( (const char **)link_file_xpm);
+ qfd_cleanup_pixmap.add( &symLinkFileIcon );
+ fileIcon = new QPixmap( (const char **)file_xpm);
+ qfd_cleanup_pixmap.add( &fileIcon );
+ closedFolderIcon = new QPixmap( (const char **)closed_xpm);
+ qfd_cleanup_pixmap.add( &closedFolderIcon );
+ detailViewIcon = new QPixmap( (const char **)detailedview_xpm);
+ qfd_cleanup_pixmap.add( &detailViewIcon );
+ multiColumnListViewIcon = new QPixmap( (const char **)mclistview_xpm);
+ qfd_cleanup_pixmap.add( &multiColumnListViewIcon );
+ cdToParentIcon = new QPixmap( (const char **)cdtoparent_xpm);
+ qfd_cleanup_pixmap.add( &cdToParentIcon );
+ newFolderIcon = new QPixmap( (const char **)newfolder_xpm);
+ qfd_cleanup_pixmap.add( &newFolderIcon );
+ previewInfoViewIcon
+ = new QPixmap( (const char **)previewinfoview_xpm );
+ qfd_cleanup_pixmap.add( &previewInfoViewIcon );
+ previewContentsViewIcon
+ = new QPixmap( (const char **)previewcontentsview_xpm );
+ qfd_cleanup_pixmap.add( &previewContentsViewIcon );
+ startCopyIcon = new QPixmap( (const char **)start_xpm );
+ qfd_cleanup_pixmap.add( &startCopyIcon );
+ endCopyIcon = new QPixmap( (const char **)end_xpm );
+ qfd_cleanup_pixmap.add( &endCopyIcon );
+ goBackIcon = new QPixmap( (const char **)back_xpm );
+ qfd_cleanup_pixmap.add( &goBackIcon );
+ fifteenTransparentPixels = new QPixmap( closedFolderIcon->width(), 1 );
+ qfd_cleanup_pixmap.add( &fifteenTransparentPixels );
+ QBitmap m( fifteenTransparentPixels->width(), 1 );
+ m.fill( Qt::color0 );
+ fifteenTransparentPixels->setMask( m );
+ bShowHiddenFiles = FALSE;
+ sortFilesBy = (int)QDir::Name;
+ detailViewMode = FALSE;
+#if defined(Q_WS_WIN)
+ if ( !fileIconProvider )
+ fileIconProvider = new QWindowsIconProvider( qApp );
+#endif
+ }
+}
+
+QFDProgressAnimation::QFDProgressAnimation( QWidget *parent )
+ : QWidget( parent, "qt_progressanimation" )
+{
+ setFixedSize( 300, 50 );
+ step = -1;
+ next();
+ timer = new QTimer( this );
+ connect( timer, SIGNAL( timeout() ),
+ this, SLOT( next() ) );
+}
+
+void QFDProgressAnimation::start()
+{
+ timer->start( 150, FALSE );
+}
+
+void QFDProgressAnimation::next()
+{
+ ++step;
+ if ( step > 10 )
+ step = 0;
+ repaint();
+}
+
+void QFDProgressAnimation::paintEvent( QPaintEvent * )
+{
+ erase();
+
+ QPainter p;
+ p.begin( this );
+ if ( step == 0 ) {
+ p.drawPixmap( 5, ( height() - startCopyIcon->height() ) / 2,
+ *startCopyIcon );
+ p.drawPixmap( width() - 5 - openFolderIcon->width(),
+ ( height() - openFolderIcon->height() ) / 2 , *openFolderIcon );
+ } else if ( step == 10 ) {
+ p.drawPixmap( 5, ( height() - openFolderIcon->height() ) / 2,
+ *openFolderIcon );
+ p.drawPixmap( width() - 5 - endCopyIcon->width(),
+ ( height() - endCopyIcon->height() ) / 2 , *endCopyIcon );
+ } else {
+ p.drawPixmap( 5, ( height() - openFolderIcon->height() ) / 2,
+ *openFolderIcon );
+ p.drawPixmap( width() - 5 - openFolderIcon->width(),
+ ( height() - openFolderIcon->height() ) / 2 , *openFolderIcon );
+ int x = 10 + openFolderIcon->width();
+ int w = width() - 2 * x;
+ int s = w / 9;
+ p.drawPixmap( x + s * step, ( height() - fileIcon->height() ) / 2 - fileIcon->height(),
+ *fileIcon );
+ }
+}
+
+QFDProgressDialog::QFDProgressDialog( QWidget *parent, const QString &fn, int steps )
+ : QDialog( parent, "", TRUE )
+{
+#ifndef QT_NO_WIDGET_TOPEXTRA
+ setCaption( QFileDialogP::tr( "Copy or Move a File" ) );
+#endif
+ QVBoxLayout *layout = new QVBoxLayout( this );
+ layout->setSpacing( 5 );
+ layout->setMargin( 5 );
+
+ animation = new QFDProgressAnimation( this );
+ layout->addWidget( animation );
+
+ layout->addWidget( new QLabel( QFileDialogP::tr( "Read: %1" ).arg( fn ),
+ this, "qt_read_lbl" ) );
+ readBar = new QProgressBar( steps, this, "qt_readbar" );
+ readBar->reset();
+ readBar->setProgress( 0 );
+ layout->addWidget( readBar );
+ writeLabel = new QLabel( QFileDialogP::tr( "Write: %1" ).arg( QString::null ),
+ this, "qt_write_lbl" );
+ layout->addWidget( writeLabel );
+ writeBar = new QProgressBar( steps, this, "qt_writebar" );
+ writeBar->reset();
+ writeBar->setProgress( 0 );
+ layout->addWidget( writeBar );
+
+ QPushButton *b = new QPushButton( QFileDialogP::tr( "Cancel" ), this,
+ "qt_cancel_btn" );
+ b->setFixedSize( b->sizeHint() );
+ layout->addWidget( b );
+ connect( b, SIGNAL( clicked() ),
+ this, SIGNAL( cancelled() ) );
+
+ animation->start();
+}
+
+void QFDProgressDialog::setReadProgress( int p )
+{
+ readBar->setProgress( p );
+}
+
+void QFDProgressDialog::setWriteProgress( int p )
+{
+ writeBar->setProgress( p );
+}
+
+void QFDProgressDialog::setWriteLabel( const QString &s )
+{
+ writeLabel->setText( QFileDialogP::tr( "Write: %1" ).arg( s ) );
+}
+
+/************************************************************************
+ *
+ * Private QFileDialogP members
+ *
+ ************************************************************************/
+
+class QFileDialogPrivate {
+public:
+ ~QFileDialogPrivate();
+
+ QStringList history;
+
+ bool geometryDirty;
+ QComboBox * paths;
+ QComboBox * types;
+ QLabel * pathL;
+ QLabel * fileL;
+ QLabel * typeL;
+
+ QVBoxLayout * topLevelLayout;
+ QHBoxLayout *buttonLayout, *leftLayout, *rightLayout;
+ QPtrList<QHBoxLayout> extraWidgetsLayouts;
+ QPtrList<QLabel> extraLabels;
+ QPtrList<QWidget> extraWidgets;
+ QPtrList<QWidget> extraButtons;
+ QPtrList<QButton> toolButtons;
+
+ QWidgetStack * stack;
+
+ QToolButton * cdToParent, *newFolder, * detailView, * mcView,
+ *previewInfo, *previewContents, *goBack;
+ QButtonGroup * modeButtons;
+
+ QString currentFileName;
+ QListViewItem *last;
+
+ struct File: public QListViewItem {
+ File( QFileDialogPrivate * dlgp,
+ const QUrlInfo * fi, QListViewItem * parent )
+ : QListViewItem( parent, dlgp->last ), info( *fi ), d(dlgp), i( 0 ), hasMimePixmap( FALSE )
+ { setup(); dlgp->last = this; }
+ File( QFileDialogPrivate * dlgp,
+ const QUrlInfo * fi, QListView * parent )
+ : QListViewItem( parent, dlgp->last ), info( *fi ), d(dlgp), i( 0 ), hasMimePixmap( FALSE )
+ { setup(); dlgp->last = this; }
+ File( QFileDialogPrivate * dlgp,
+ const QUrlInfo * fi, QListView * parent, QListViewItem * after )
+ : QListViewItem( parent, after ), info( *fi ), d(dlgp), i( 0 ), hasMimePixmap( FALSE )
+ { setup(); if ( !nextSibling() ) dlgp->last = this; }
+ ~File();
+
+ QString text( int column ) const;
+ const QPixmap * pixmap( int ) const;
+
+ QUrlInfo info;
+ QFileDialogPrivate * d;
+ QListBoxItem *i;
+ bool hasMimePixmap;
+ };
+
+ class MCItem: public QListBoxItem {
+ public:
+ MCItem( QListBox *, QListViewItem * item );
+ MCItem( QListBox *, QListViewItem * item, QListBoxItem *after );
+ QString text() const;
+ const QPixmap *pixmap() const;
+ int height( const QListBox * ) const;
+ int width( const QListBox * ) const;
+ void paint( QPainter * );
+ QListViewItem * i;
+ };
+
+ class UrlInfoList : public QPtrList<QUrlInfo> {
+ public:
+ UrlInfoList() { setAutoDelete( TRUE ); }
+ int compareItems( QPtrCollection::Item n1, QPtrCollection::Item n2 ) {
+ if ( !n1 || !n2 )
+ return 0;
+
+ QUrlInfo *i1 = ( QUrlInfo *)n1;
+ QUrlInfo *i2 = ( QUrlInfo *)n2;
+
+ if ( i1->isDir() && !i2->isDir() )
+ return -1;
+ if ( !i1->isDir() && i2->isDir() )
+ return 1;
+
+ if ( i1->name() == ".." )
+ return -1;
+ if ( i2->name() == ".." )
+ return 1;
+
+#if defined(Q_OS_WIN32)
+ if ( sortFilesBy == QDir::Name ) {
+ QString name1 = i1->name().lower();
+ QString name2 = i2->name().lower();
+ return name1.compare( name2 );
+ }
+#endif
+ if ( QUrlInfo::equal( *i1, *i2, sortFilesBy ) )
+ return 0;
+ else if ( QUrlInfo::greaterThan( *i1, *i2, sortFilesBy ) )
+ return 1;
+ else if ( QUrlInfo::lessThan( *i1, *i2, sortFilesBy ) )
+ return -1;
+ // can't happen...
+ return 0;
+ }
+ QUrlInfo *operator[]( int i ) {
+ return at( i );
+ }
+ };
+
+ UrlInfoList sortedList;
+ QPtrList<File> pendingItems;
+
+ QFileListBox * moreFiles;
+
+ QFileDialogP::Mode mode;
+
+ QString rw;
+ QString ro;
+ QString wo;
+ QString inaccessible;
+
+ QString symLinkToFile;
+ QString file;
+ QString symLinkToDir;
+ QString dir;
+ QString symLinkToSpecial;
+ QString special;
+ QWidgetStack *preview;
+ bool infoPreview, contentsPreview;
+ QSplitter *splitter;
+ QUrlOperator url, oldUrl;
+ QWidget *infoPreviewWidget, *contentsPreviewWidget;
+ QFilePreviewP *infoPreviewer, *contentsPreviewer;
+ bool hadDotDot;
+
+ bool ignoreNextKeyPress;
+ // ignores the next refresh operation in case the user forced a selection
+ bool ignoreNextRefresh;
+ QFDProgressDialog *progressDia;
+ bool checkForFilter;
+ bool ignoreReturn;
+ bool ignoreStop;
+
+ QTimer *mimeTypeTimer;
+ const QNetworkOperation *currListChildren;
+
+ // this is similar to QUrl::encode but does encode "*" and
+ // doesn't encode whitespaces
+ static QString encodeFileName( const QString& fName ) {
+
+ QString newStr;
+ QCString cName = fName.utf8();
+ const QCString sChars(
+#ifdef Q_WS_WIN
+ "#%"
+#else
+ "<>#@\"&%$:,;?={}|^~[]\'`\\*"
+#endif
+ );
+
+ int len = cName.length();
+ if ( !len )
+ return QString::null;
+ for ( int i = 0; i < len ;++i ) {
+ uchar inCh = (uchar)cName[ i ];
+ if ( inCh >= 128 || sChars.contains(inCh) )
+ {
+ newStr += QChar( '%' );
+ ushort c = inCh / 16;
+ c += c > 9 ? 'A' - 10 : '0';
+ newStr += c;
+ c = inCh % 16;
+ c += c > 9 ? 'A' - 10 : '0';
+ newStr += c;
+ } else {
+ newStr += inCh;
+ }
+ }
+ return newStr;
+ }
+
+};
+
+QFileDialogPrivate::~QFileDialogPrivate()
+{
+ delete modeButtons;
+}
+
+
+
+/************************************************************************
+ *
+ * Internal class QRenameEdit
+ *
+ ************************************************************************/
+
+void QRenameEdit::keyPressEvent( QKeyEvent *e )
+{
+ if ( e->key() == Key_Escape )
+ emit escapePressed();
+ else
+ QLineEdit::keyPressEvent( e );
+ e->accept();
+}
+
+void QRenameEdit::focusOutEvent( QFocusEvent * )
+{
+ emit escapePressed();
+}
+
+/************************************************************************
+ *
+ * Internal class QFileListBox
+ *
+ ************************************************************************/
+
+QFileListBox::QFileListBox( QWidget *parent, QFileDialogP *dlg )
+ : QListBox( parent, "filelistbox" ), filedialog( dlg ),
+ renaming( FALSE ), renameItem( 0 ), mousePressed( FALSE ),
+ firstMousePressEvent( TRUE )
+{
+ changeDirTimer = new QTimer( this );
+ QVBox *box = new QVBox( viewport(), "qt_vbox" );
+ box->setFrameStyle( QFrame::Box | QFrame::Plain );
+ lined = new QRenameEdit( box );
+ lined->setFixedHeight( lined->sizeHint().height() );
+ box->hide();
+ box->setBackgroundMode( PaletteBase );
+ renameTimer = new QTimer( this );
+ connect( lined, SIGNAL( returnPressed() ),
+ this, SLOT (rename() ) );
+ connect( lined, SIGNAL( escapePressed() ),
+ this, SLOT( cancelRename() ) );
+ connect( renameTimer, SIGNAL( timeout() ),
+ this, SLOT( doubleClickTimeout() ) );
+ connect( changeDirTimer, SIGNAL( timeout() ),
+ this, SLOT( changeDirDuringDrag() ) );
+ connect( this, SIGNAL( contentsMoving( int, int ) ),
+ this, SLOT( contentsMoved( int, int ) ) );
+ viewport()->setAcceptDrops( TRUE );
+ dragItem = 0;
+}
+
+void QFileListBox::show()
+{
+ setBackgroundMode( PaletteBase );
+ viewport()->setBackgroundMode( PaletteBase );
+ QListBox::show();
+}
+
+void QFileListBox::keyPressEvent( QKeyEvent *e )
+{
+ if ( ( e->key() == Key_Enter ||
+ e->key() == Key_Return ) &&
+ renaming )
+ return;
+
+ QString keyPressed = ((QKeyEvent *)e)->text().lower();
+ QChar keyChar = keyPressed[0];
+ if ( keyChar.isLetterOrNumber() ) {
+ QListBoxItem * i = 0;
+ if ( currentItem() )
+ i = item( currentItem() );
+ else
+ i = firstItem();
+ if ( i->next() )
+ i = i->next();
+ else
+ i = firstItem();
+ while ( i != item( currentItem() ) ) {
+ QString it = text( index( i ) );
+ if ( it[0].lower() == keyChar ) {
+ clearSelection();
+ setCurrentItem( i );
+ } else {
+ if ( i->next() )
+ i = i->next();
+ else
+ i = firstItem();
+ }
+ }
+ }
+ cancelRename();
+ QListBox::keyPressEvent( e );
+}
+
+void QFileListBox::viewportMousePressEvent( QMouseEvent *e )
+{
+ pressPos = e->pos();
+ mousePressed = FALSE;
+
+ bool didRename = renaming;
+
+ cancelRename();
+ if ( !hasFocus() && !viewport()->hasFocus() )
+ setFocus();
+
+ if ( e->button() != LeftButton ) {
+ QListBox::viewportMousePressEvent( e );
+ firstMousePressEvent = FALSE;
+ return;
+ }
+
+ int i = currentItem();
+ bool wasSelected = FALSE;
+ if ( i != -1 )
+ wasSelected = item( i )->isSelected();
+ QListBox::viewportMousePressEvent( e );
+
+ QFileDialogPrivate::MCItem *i1 = (QFileDialogPrivate::MCItem*)item( currentItem() );
+ if ( i1 )
+ mousePressed = !( (QFileDialogPrivate::File*)i1->i )->info.isDir();
+
+ if ( itemAt( e->pos() ) != item( i ) ) {
+ firstMousePressEvent = FALSE;
+ return;
+ }
+
+ if ( !firstMousePressEvent && !didRename && i == currentItem() && currentItem() != -1 &&
+ wasSelected && filedialog->mode() != QFileDialogP::ExistingFiles &&
+ QUrlInfo( filedialog->d->url, "." ).isWritable() && item( currentItem() )->text() != ".." ) {
+ renameTimer->start( QApplication::doubleClickInterval(), TRUE );
+ renameItem = item( i );
+ }
+
+ firstMousePressEvent = FALSE;
+}
+
+void QFileListBox::viewportMouseReleaseEvent( QMouseEvent *e )
+{
+ dragItem = 0;
+ QListBox::viewportMouseReleaseEvent( e );
+ mousePressed = FALSE;
+}
+
+void QFileListBox::viewportMouseDoubleClickEvent( QMouseEvent *e )
+{
+ renameTimer->stop();
+ QListBox::viewportMouseDoubleClickEvent( e );
+}
+
+void QFileListBox::viewportMouseMoveEvent( QMouseEvent *e )
+{
+ if ( !dragItem )
+ dragItem = itemAt( e->pos() );
+ renameTimer->stop();
+#ifndef QT_NO_DRAGANDDROP
+ if ( ( pressPos - e->pos() ).manhattanLength() > QApplication::startDragDistance() && mousePressed ) {
+ QListBoxItem *item = dragItem;
+ dragItem = 0;
+ if ( item ) {
+ if ( !itemRect( item ).contains( e->pos() ) )
+ return;
+ QUriDrag* drag = new QUriDrag( viewport() );
+ drag->setUnicodeUris( filedialog->selectedFiles() );
+
+ if ( lined->parentWidget()->isVisible() )
+ cancelRename();
+
+ connect( drag, SIGNAL( destroyed() ),
+ this, SLOT( dragObjDestroyed() ) );
+ drag->drag();
+
+ mousePressed = FALSE;
+ }
+ } else
+#endif
+ {
+ QListBox::viewportMouseMoveEvent( e );
+ }
+
+}
+
+void QFileListBox::dragObjDestroyed()
+{
+#ifndef QT_NO_DRAGANDDROP
+ //#######
+ //filedialog->rereadDir();
+#endif
+}
+
+#ifndef QT_NO_DRAGANDDROP
+void QFileListBox::viewportDragEnterEvent( QDragEnterEvent *e )
+{
+ startDragUrl = filedialog->d->url;
+ startDragDir = filedialog->dirPath();
+ currDropItem = 0;
+
+ if ( !QUriDrag::canDecode( e ) ) {
+ e->ignore();
+ return;
+ }
+
+ QStringList l;
+ QUriDrag::decodeLocalFiles( e, l );
+ urls = (int)l.count();
+
+ if ( acceptDrop( e->pos(), e->source() ) ) {
+ e->accept();
+ setCurrentDropItem( e->pos() );
+ } else {
+ e->ignore();
+ setCurrentDropItem( QPoint( -1, -1 ) );
+ }
+
+ oldDragPos = e->pos();
+}
+
+void QFileListBox::viewportDragMoveEvent( QDragMoveEvent *e )
+{
+ if ( acceptDrop( e->pos(), e->source() ) ) {
+ switch ( e->action() ) {
+ case QDropEvent::Copy:
+ e->acceptAction();
+ break;
+ case QDropEvent::Move:
+ e->acceptAction();
+ break;
+ case QDropEvent::Link:
+ break;
+ default:
+ break;
+ }
+ if ( oldDragPos != e->pos() )
+ setCurrentDropItem( e->pos() );
+ } else {
+ changeDirTimer->stop();
+ e->ignore();
+ setCurrentDropItem( QPoint( -1, -1 ) );
+ }
+
+ oldDragPos = e->pos();
+}
+
+void QFileListBox::viewportDragLeaveEvent( QDragLeaveEvent * )
+{
+ changeDirTimer->stop();
+ setCurrentDropItem( QPoint( -1, -1 ) );
+//########
+// if ( startDragDir != filedialog->d->url )
+// filedialog->setUrl( startDragUrl );
+}
+
+void QFileListBox::viewportDropEvent( QDropEvent *e )
+{
+ changeDirTimer->stop();
+
+ if ( !QUriDrag::canDecode( e ) ) {
+ e->ignore();
+ return;
+ }
+
+ QStrList l;
+ QUriDrag::decode( e, l );
+
+ bool move = e->action() == QDropEvent::Move;
+// bool supportAction = move || e->action() == QDropEvent::Copy;
+
+ QUrlOperator dest;
+ if ( currDropItem )
+ dest = QUrlOperator( filedialog->d->url, QFileDialogPrivate::encodeFileName( currDropItem->text() ) );
+ else
+ dest = filedialog->d->url;
+ QStringList lst;
+ for ( uint i = 0; i < l.count(); ++i ) {
+ lst << l.at( i );
+ }
+
+ filedialog->d->url.copy( lst, dest, move );
+
+ // ##### what is supportAction for?
+ e->acceptAction();
+ currDropItem = 0;
+}
+
+bool QFileListBox::acceptDrop( const QPoint &pnt, QWidget *source )
+{
+ QListBoxItem *item = itemAt( pnt );
+ if ( !item || item && !itemRect( item ).contains( pnt ) ) {
+ if ( source == viewport() && startDragDir == filedialog->dirPath() )
+ return FALSE;
+ return TRUE;
+ }
+
+ QUrlInfo fi( filedialog->d->url, item->text() );
+
+ if ( fi.isDir() && itemRect( item ).contains( pnt ) )
+ return TRUE;
+ return FALSE;
+}
+
+void QFileListBox::setCurrentDropItem( const QPoint &pnt )
+{
+ changeDirTimer->stop();
+
+ QListBoxItem *item = 0;
+ if ( pnt != QPoint( -1, -1 ) )
+ item = itemAt( pnt );
+ if ( item && !QUrlInfo( filedialog->d->url, item->text() ).isDir() )
+ item = 0;
+ if ( item && !itemRect( item ).contains( pnt ) )
+ item = 0;
+
+ currDropItem = item;
+ if ( currDropItem )
+ setCurrentItem( currDropItem );
+ changeDirTimer->start( 750 );
+}
+#endif // QT_NO_DRAGANDDROP
+
+void QFileListBox::changeDirDuringDrag()
+{
+#ifndef QT_NO_DRAGANDDROP
+ if ( !currDropItem )
+ return;
+ changeDirTimer->stop();
+ QUrl u( filedialog->d->url, QFileDialogPrivate::encodeFileName(currDropItem->text()) );
+ filedialog->setDir( u );
+ currDropItem = 0;
+#endif
+}
+
+void QFileListBox::doubleClickTimeout()
+{
+ startRename();
+ renameTimer->stop();
+}
+
+void QFileListBox::startRename( bool check )
+{
+ if ( check && ( !renameItem || renameItem != item( currentItem() ) ) )
+ return;
+
+ int i = currentItem();
+ setSelected( i, TRUE );
+ QRect r = itemRect( item( i ) );
+ int bdr = item( i )->pixmap() ?
+ item( i )->pixmap()->width() : 16;
+ int x = r.x() + bdr;
+ int y = r.y();
+ int w = item( i )->width( this ) - bdr;
+ int h = QMAX( lined->height() + 2, r.height() );
+ y = y + r.height() / 2 - h / 2;
+
+ lined->parentWidget()->setGeometry( x, y, w + 6, h );
+ lined->setFocus();
+ lined->setText( item( i )->text() );
+ lined->selectAll();
+ lined->setFrame( FALSE );
+ lined->parentWidget()->show();
+ viewport()->setFocusProxy( lined );
+ renaming = TRUE;
+}
+
+void QFileListBox::clear()
+{
+ cancelRename();
+ QListBox::clear();
+}
+
+void QFileListBox::rename()
+{
+ if ( !lined->text().isEmpty() ) {
+ QString file = currentText();
+
+ if ( lined->text() != file )
+ filedialog->d->url.rename( file, lined->text() );
+ }
+ cancelRename();
+}
+
+void QFileListBox::cancelRename()
+{
+ renameItem = 0;
+ lined->parentWidget()->hide();
+ viewport()->setFocusProxy( this );
+ renaming = FALSE;
+ updateItem( currentItem() );
+ if ( lined->hasFocus() )
+ viewport()->setFocus();
+}
+
+void QFileListBox::contentsMoved( int, int )
+{
+ changeDirTimer->stop();
+#ifndef QT_NO_DRAGANDDROP
+ setCurrentDropItem( QPoint( -1, -1 ) );
+#endif
+}
+
+/************************************************************************
+ *
+ * Internal class QFileListView
+ *
+ ************************************************************************/
+
+QFileDialogQFileListView::QFileDialogQFileListView( QWidget *parent, QFileDialogP *dlg )
+ : QListView( parent, "qt_filedlg_listview" ), renaming( FALSE ), renameItem( 0 ),
+ filedialog( dlg ), mousePressed( FALSE ),
+ firstMousePressEvent( TRUE )
+{
+ changeDirTimer = new QTimer( this );
+ QVBox *box = new QVBox( viewport(), "qt_vbox" );
+ box->setFrameStyle( QFrame::Box | QFrame::Plain );
+ lined = new QRenameEdit( box );
+ lined->setFixedHeight( lined->sizeHint().height() );
+ box->hide();
+ box->setBackgroundMode( PaletteBase );
+ renameTimer = new QTimer( this );
+ connect( lined, SIGNAL( returnPressed() ),
+ this, SLOT (rename() ) );
+ connect( lined, SIGNAL( escapePressed() ),
+ this, SLOT( cancelRename() ) );
+ header()->setMovingEnabled( FALSE );
+ connect( renameTimer, SIGNAL( timeout() ),
+ this, SLOT( doubleClickTimeout() ) );
+ connect( changeDirTimer, SIGNAL( timeout() ),
+ this, SLOT( changeDirDuringDrag() ) );
+ disconnect( header(), SIGNAL( sectionClicked( int ) ),
+ this, SLOT( changeSortColumn( int ) ) );
+ connect( header(), SIGNAL( sectionClicked( int ) ),
+ this, SLOT( changeSortColumn2( int ) ) );
+ connect( this, SIGNAL( contentsMoving( int, int ) ),
+ this, SLOT( contentsMoved( int, int ) ) );
+
+ viewport()->setAcceptDrops( TRUE );
+ sortcolumn = 0;
+ ascending = TRUE;
+ dragItem = 0;
+}
+
+void QFileDialogQFileListView::setSorting( int column, bool increasing )
+{
+ if ( column == -1 ) {
+ QListView::setSorting( column, increasing );
+ return;
+ }
+
+ sortAscending = ascending = increasing;
+ sortcolumn = column;
+ switch ( column ) {
+ case 0:
+ sortFilesBy = QDir::Name;
+ break;
+ case 1:
+ sortFilesBy = QDir::Size;
+ break;
+ case 3:
+ sortFilesBy = QDir::Time;
+ break;
+ default:
+ sortFilesBy = QDir::Name; // #### ???
+ break;
+ }
+
+ filedialog->resortDir();
+}
+
+void QFileDialogQFileListView::changeSortColumn2( int column )
+{
+ int lcol = header()->mapToLogical( column );
+ setSorting( lcol, sortcolumn == lcol ? !ascending : TRUE );
+}
+
+void QFileDialogQFileListView::keyPressEvent( QKeyEvent *e )
+{
+ if ( ( e->key() == Key_Enter ||
+ e->key() == Key_Return ) &&
+ renaming )
+ return;
+
+ QString keyPressed = e->text().lower();
+ QChar keyChar = keyPressed[0];
+ if ( keyChar.isLetterOrNumber() ) {
+ QListViewItem * i = 0;
+ if ( currentItem() )
+ i = currentItem();
+ else
+ i = firstChild();
+ if ( i->nextSibling() )
+ i = i->nextSibling();
+ else
+ i = firstChild();
+ while ( i != currentItem() ) {
+ QString it = i->text(0);
+ if ( it[0].lower() == keyChar ) {
+ clearSelection();
+ ensureItemVisible( i );
+ setCurrentItem( i );
+ } else {
+ if ( i->nextSibling() )
+ i = i->nextSibling();
+ else
+ i = firstChild();
+ }
+ }
+ return;
+ }
+
+ cancelRename();
+ QListView::keyPressEvent( e );
+}
+
+void QFileDialogQFileListView::viewportMousePressEvent( QMouseEvent *e )
+{
+ pressPos = e->pos();
+ mousePressed = FALSE;
+
+ bool didRename = renaming;
+ cancelRename();
+ if ( !hasFocus() && !viewport()->hasFocus() )
+ setFocus();
+
+ if ( e->button() != LeftButton ) {
+ QListView::viewportMousePressEvent( e );
+ firstMousePressEvent = FALSE;
+ return;
+ }
+
+ QListViewItem *i = currentItem();
+ QListView::viewportMousePressEvent( e );
+
+ QFileDialogPrivate::File *i1 = (QFileDialogPrivate::File*)currentItem();
+ if ( i1 )
+ mousePressed = !i1->info.isDir();
+
+ if ( itemAt( e->pos() ) != i ||
+ e->x() + contentsX() > columnWidth( 0 ) ) {
+ firstMousePressEvent = FALSE;
+ return;
+ }
+
+ if ( !firstMousePressEvent && !didRename && i == currentItem() && currentItem() &&
+ filedialog->mode() != QFileDialogP::ExistingFiles &&
+ QUrlInfo( filedialog->d->url, "." ).isWritable() && currentItem()->text( 0 ) != ".." ) {
+ renameTimer->start( QApplication::doubleClickInterval(), TRUE );
+ renameItem = currentItem();
+ }
+
+ firstMousePressEvent = FALSE;
+}
+
+void QFileDialogQFileListView::viewportMouseDoubleClickEvent( QMouseEvent *e )
+{
+ renameTimer->stop();
+ QListView::viewportMouseDoubleClickEvent( e );
+}
+
+void QFileDialogQFileListView::viewportMouseReleaseEvent( QMouseEvent *e )
+{
+ QListView::viewportMouseReleaseEvent( e );
+ mousePressed = FALSE;
+ dragItem = 0;
+}
+
+void QFileDialogQFileListView::viewportMouseMoveEvent( QMouseEvent *e )
+{
+ renameTimer->stop();
+ if ( !dragItem )
+ dragItem = itemAt( e->pos() );
+#ifndef QT_NO_DRAGANDDROP
+ if ( ( pressPos - e->pos() ).manhattanLength() > QApplication::startDragDistance() && mousePressed ) {
+ QListViewItem *item = dragItem;
+ dragItem = 0;
+ if ( item ) {
+ QUriDrag* drag = new QUriDrag( viewport() );
+ drag->setUnicodeUris( filedialog->selectedFiles() );
+
+ if ( lined->isVisible() )
+ cancelRename();
+
+ connect( drag, SIGNAL( destroyed() ),
+ this, SLOT( dragObjDestroyed() ) );
+ drag->drag();
+
+ mousePressed = FALSE;
+ }
+ }
+#endif
+}
+
+void QFileDialogQFileListView::dragObjDestroyed()
+{
+#ifndef QT_NO_DRAGANDDROP
+ //######
+ //filedialog->rereadDir();
+#endif
+}
+
+#ifndef QT_NO_DRAGANDDROP
+void QFileDialogQFileListView::viewportDragEnterEvent( QDragEnterEvent *e )
+{
+ startDragUrl = filedialog->d->url;
+ startDragDir = filedialog->dirPath();
+ currDropItem = 0;
+
+ if ( !QUriDrag::canDecode( e ) ) {
+ e->ignore();
+ return;
+ }
+
+ QStringList l;
+ QUriDrag::decodeLocalFiles( e, l );
+ urls = (int)l.count();
+
+ if ( acceptDrop( e->pos(), e->source() ) ) {
+ e->accept();
+ setCurrentDropItem( e->pos() );
+ } else {
+ e->ignore();
+ setCurrentDropItem( QPoint( -1, -1 ) );
+ }
+
+ oldDragPos = e->pos();
+}
+
+void QFileDialogQFileListView::viewportDragMoveEvent( QDragMoveEvent *e )
+{
+ if ( acceptDrop( e->pos(), e->source() ) ) {
+ if ( oldDragPos != e->pos() )
+ setCurrentDropItem( e->pos() );
+ switch ( e->action() ) {
+ case QDropEvent::Copy:
+ e->acceptAction();
+ break;
+ case QDropEvent::Move:
+ e->acceptAction();
+ break;
+ case QDropEvent::Link:
+ break;
+ default:
+ break;
+ }
+ } else {
+ changeDirTimer->stop();
+ e->ignore();
+ setCurrentDropItem( QPoint( -1, -1 ) );
+ }
+
+ oldDragPos = e->pos();
+}
+
+void QFileDialogQFileListView::viewportDragLeaveEvent( QDragLeaveEvent * )
+{
+ changeDirTimer->stop();
+ setCurrentDropItem( QPoint( -1, -1 ) );
+//########
+// if ( startDragDir != filedialog->d->url )
+// filedialog->setUrl( startDragUrl );
+}
+
+void QFileDialogQFileListView::viewportDropEvent( QDropEvent *e )
+{
+ changeDirTimer->stop();
+
+ if ( !QUriDrag::canDecode( e ) ) {
+ e->ignore();
+ return;
+ }
+
+ QStringList l;
+ QUriDrag::decodeToUnicodeUris( e, l );
+
+ bool move = e->action() == QDropEvent::Move;
+// bool supportAction = move || e->action() == QDropEvent::Copy;
+
+ QUrlOperator dest;
+ if ( currDropItem )
+ dest = QUrlOperator( filedialog->d->url, QFileDialogPrivate::encodeFileName( currDropItem->text( 0 ) ) );
+ else
+ dest = filedialog->d->url;
+ filedialog->d->url.copy( l, dest, move );
+
+ // ##### what is supportAction for?
+ e->acceptAction();
+ currDropItem = 0;
+}
+
+bool QFileDialogQFileListView::acceptDrop( const QPoint &pnt, QWidget *source )
+{
+ QListViewItem *item = itemAt( pnt );
+ if ( !item || item && !itemRect( item ).contains( pnt ) ) {
+ if ( source == viewport() && startDragDir == filedialog->dirPath() )
+ return FALSE;
+ return TRUE;
+ }
+
+ QUrlInfo fi( filedialog->d->url, item->text( 0 ) );
+
+ if ( fi.isDir() && itemRect( item ).contains( pnt ) )
+ return TRUE;
+ return FALSE;
+}
+
+void QFileDialogQFileListView::setCurrentDropItem( const QPoint &pnt )
+{
+ changeDirTimer->stop();
+
+ QListViewItem *item = itemAt( pnt );
+ if ( pnt == QPoint( -1, -1 ) )
+ item = 0;
+ if ( item && !QUrlInfo( filedialog->d->url, item->text( 0 ) ).isDir() )
+ item = 0;
+
+ if ( item && !itemRect( item ).contains( pnt ) )
+ item = 0;
+
+ currDropItem = item;
+
+ if ( currDropItem )
+ setCurrentItem( currDropItem );
+
+ changeDirTimer->start( 750 );
+}
+#endif // QT_NO_DRAGANDDROP
+
+void QFileDialogQFileListView::changeDirDuringDrag()
+{
+#ifndef QT_NO_DRAGANDDROP
+ if ( !currDropItem )
+ return;
+ changeDirTimer->stop();
+ QUrl u( filedialog->d->url, QFileDialogPrivate::encodeFileName(currDropItem->text( 0 ) ) );
+ filedialog->setDir( u );
+ currDropItem = 0;
+#endif // QT_NO_DRAGANDDROP
+}
+
+
+void QFileDialogQFileListView::doubleClickTimeout()
+{
+ startRename();
+ renameTimer->stop();
+}
+
+void QFileDialogQFileListView::startRename( bool check )
+{
+ if ( check && ( !renameItem || renameItem != currentItem() ) )
+ return;
+
+ QListViewItem *i = currentItem();
+ setSelected( i, TRUE );
+
+ QRect r = itemRect( i );
+ int bdr = i->pixmap( 0 ) ?
+ i->pixmap( 0 )->width() : 16;
+ int x = r.x() + bdr;
+ int y = r.y();
+ int w = columnWidth( 0 ) - bdr;
+ int h = QMAX( lined->height() + 2, r.height() );
+ y = y + r.height() / 2 - h / 2;
+
+ lined->parentWidget()->setGeometry( x, y, w + 6, h );
+ lined->setFocus();
+ lined->setText( i->text( 0 ) );
+ lined->selectAll();
+ lined->setFrame( FALSE );
+ lined->parentWidget()->show();
+ viewport()->setFocusProxy( lined );
+ renaming = TRUE;
+}
+
+void QFileDialogQFileListView::clear()
+{
+ cancelRename();
+ QListView::clear();
+}
+
+void QFileDialogQFileListView::rename()
+{
+ if ( !lined->text().isEmpty() ) {
+ QString file = currentItem()->text( 0 );
+
+ if ( lined->text() != file )
+ filedialog->d->url.rename( file, lined->text() );
+ }
+ cancelRename();
+}
+
+void QFileDialogQFileListView::cancelRename()
+{
+ renameItem = 0;
+ lined->parentWidget()->hide();
+ viewport()->setFocusProxy( this );
+ renaming = FALSE;
+ if ( currentItem() )
+ currentItem()->repaint();
+ if ( lined->hasFocus() )
+ viewport()->setFocus();
+}
+
+void QFileDialogQFileListView::contentsMoved( int, int )
+{
+ changeDirTimer->stop();
+#ifndef QT_NO_DRAGANDDROP
+ setCurrentDropItem( QPoint( -1, -1 ) );
+#endif
+}
+
+
+QFileDialogPrivate::File::~File()
+{
+ if ( d->pendingItems.findRef( this ) )
+ d->pendingItems.removeRef( this );
+}
+
+QString QFileDialogPrivate::File::text( int column ) const
+{
+ makeVariables();
+
+ switch( column ) {
+ case 0:
+ return info.name();
+ case 1:
+ if ( info.isFile() )
+ return QString::number(info.size());
+ else
+ return QString::fromLatin1("");
+ case 2:
+ if ( info.isFile() && info.isSymLink() ) {
+ return d->symLinkToFile;
+ } else if ( info.isFile() ) {
+ return d->file;
+ } else if ( info.isDir() && info.isSymLink() ) {
+ return d->symLinkToDir;
+ } else if ( info.isDir() ) {
+ return d->dir;
+ } else if ( info.isSymLink() ) {
+ return d->symLinkToSpecial;
+ } else {
+ return d->special;
+ }
+ case 3: {
+ return info.lastModified().toString( Qt::LocalDate );
+ }
+ case 4:
+ if ( info.isReadable() )
+ return info.isWritable() ? d->rw : d->ro;
+ else
+ return info.isWritable() ? d->wo : d->inaccessible;
+ }
+
+ return QString::fromLatin1("<--->");
+}
+
+const QPixmap * QFileDialogPrivate::File::pixmap( int column ) const
+{
+ if ( column ) {
+ return 0;
+ } else if ( QListViewItem::pixmap( column ) ) {
+ return QListViewItem::pixmap( column );
+ } else if ( info.isSymLink() ) {
+ if ( info.isFile() )
+ return symLinkFileIcon;
+ else
+ return symLinkDirIcon;
+ } else if ( info.isDir() ) {
+ return closedFolderIcon;
+ } else if ( info.isFile() ) {
+ return fileIcon;
+ } else {
+ return fifteenTransparentPixels;
+ }
+}
+
+QFileDialogPrivate::MCItem::MCItem( QListBox * lb, QListViewItem * item )
+ : QListBoxItem()
+{
+ i = item;
+ if ( lb )
+ lb->insertItem( this );
+}
+
+QFileDialogPrivate::MCItem::MCItem( QListBox * lb, QListViewItem * item, QListBoxItem *after )
+ : QListBoxItem()
+{
+ i = item;
+ if ( lb )
+ lb->insertItem( this, after );
+}
+
+QString QFileDialogPrivate::MCItem::text() const
+{
+ return i->text( 0 );
+}
+
+
+const QPixmap *QFileDialogPrivate::MCItem::pixmap() const
+{
+ return i->pixmap( 0 );
+}
+
+
+int QFileDialogPrivate::MCItem::height( const QListBox * lb ) const
+{
+ if ( pixmap() )
+ return QMAX( lb->fontMetrics().height(), pixmap()->height()) + 2;
+
+ return lb->fontMetrics().height() + 2;
+}
+
+
+int QFileDialogPrivate::MCItem::width( const QListBox * lb ) const
+{
+ QFontMetrics fm = lb->fontMetrics();
+ int w = 2;
+ if ( pixmap() )
+ w += pixmap()->width() + 4;
+ else
+ w += 18;
+ w += fm.width( text() );
+ w += -fm.minLeftBearing();
+ w += -fm.minRightBearing();
+ w += 6;
+ return w;
+}
+
+
+void QFileDialogPrivate::MCItem::paint( QPainter * ptr )
+{
+ QFontMetrics fm = ptr->fontMetrics();
+
+ int h;
+
+ if ( pixmap() )
+ h = QMAX( fm.height(), pixmap()->height()) + 2;
+ else
+ h = fm.height() + 2;
+
+ const QPixmap * pm = pixmap();
+ if ( pm )
+ ptr->drawPixmap( 2, 1, *pm );
+
+ ptr->drawText( pm ? pm->width() + 4 : 22, h - fm.descent() - 2,
+ text() );
+}
+
+static QStringList makeFiltersList( const QString &filter )
+{
+ if ( filter.isEmpty() )
+ return QStringList();
+
+ int i = filter.find( ";;", 0 );
+ QString sep( ";;" );
+ if ( i == -1 ) {
+ if ( filter.find( "\n", 0 ) != -1 ) {
+ sep = "\n";
+ i = filter.find( sep, 0 );
+ }
+ }
+
+ return QStringList::split( sep, filter );
+}
+
+/*!
+ \class QFileDialogP qfiledialog.h
+ \brief The QFileDialogP class provides dialogs that allow users to select files or directories.
+ \ingroup dialogs
+ \mainclass
+
+ The QFileDialogP class enables a user to traverse their file system in
+ order to select one or many files or a directory.
+
+ The easiest way to create a QFileDialogP is to use the static
+ functions. On Windows, these static functions will call the native
+ Windows file dialog and on Mac OS X, these static function will call
+ the native Mac OS X file dialog.
+
+ \code
+ QString s = QFileDialogP::getOpenFileName(
+ "/home",
+ "Images (*.png *.xpm *.jpg)",
+ this,
+ "open file dialog"
+ "Choose a file" );
+ \endcode
+
+ In the above example, a modal QFileDialogP is created using a static
+ function. The startup directory is set to "/home". The file filter
+ is set to "Images (*.png *.xpm *.jpg)". The parent of the file dialog
+ is set to \e this and it is given the identification name - "open file
+ dialog". The caption at the top of file dialog is set to "Choose a
+ file".
+
+ You can create your own QFileDialogP without using the static
+ functions. By calling setMode(), you can set what can be returned by
+ the QFileDialogP.
+
+ \code
+ QFileDialogP* fd = new QFileDialogP( this, "file dialog", TRUE );
+ fd->setMode( QFileDialogP::AnyFile );
+ \endcode
+
+ In the above example, the mode of the file dialog is set to \c
+ AnyFile, meaning that the user can select any file, or even specify a
+ file that doesn't exist. This mode is useful for creating a "File Save
+ As" file dialog. Use \c ExistingFile if the user must select an
+ existing file or \c Directory if only a directory may be selected.
+ (See the \l QFileDialogP::Mode enum for the complete list of modes.)
+
+ You can retrieve the dialog's mode with mode(). Use setFilter() to set
+ the dialog's file filter, e.g.
+
+ \code
+ fd->setFilter( "Images (*.png *.xpm *.jpg)" );
+ \endcode
+
+ In the above example, the filter is set to "Images (*.png *.xpm
+ *.jpg)", this means that only files with the extension \c png, \c xpm
+ or \c jpg will be shown in the QFileDialogP. You can apply
+ several filters by using setFilters() and add additional filters with
+ addFilter(). Use setSelectedFilter() to select one of the filters
+ you've given as the file dialog's default filter. Whenever the user
+ changes the filter the filterSelected() signal is emitted.
+
+ The file dialog has two view modes, QFileDialogP::List which simply
+ lists file and directory names and QFileDialogP::Detail which
+ displays additional information alongside each name, e.g. file size,
+ modification date, etc. Set the mode with setViewMode().
+
+ \code
+ fd->setViewMode( QFileDialogP::Detail );
+ \endcode
+
+ The last important function you will need to use when creating your
+ own file dialog is selectedFile().
+
+ \code
+ QString fileName;
+ if ( fd->exec() == QDialog::Accepted )
+ fileName = fd->selectedFile();
+ \endcode
+
+ In the above example, a modal file dialog is created and shown. If
+ the user clicked OK, then the file they selected is put in \c
+ fileName.
+
+ If you are using the \c ExistingFiles mode then you will need to use
+ selectedFiles() which will return the selected files in a QStringList.
+
+ The dialog's working directory can be set with setDir(). The display
+ of hidden files is controlled with setShowHiddenFiles(). The dialog
+ can be forced to re-read the directory with rereadDir() and re-sort
+ the directory with resortDir(). All the files in the current directory
+ can be selected with selectAll().
+
+ \section1 Creating and using preview widgets
+
+ There are two kinds of preview widgets that can be used with
+ QFileDialogPs: \e content preview widgets and \e information preview
+ widgets. They are created and used in the same way except that the
+ function names differ, e.g. setContentsPreview() and setInfoPreview().
+
+ A preview widget is a widget that is placed inside a QFileDialogP so
+ that the user can see either the contents of the file, or information
+ about the file.
+
+ \code
+ class Preview : public QLabel, public QFilePreviewP
+ {
+ public:
+ Preview( QWidget *parent=0 ) : QLabel( parent ) {}
+
+ void previewUrl( const QUrl &u )
+ {
+ QString path = u.path();
+ QPixmap pix( path );
+ if ( pix.isNull() )
+ setText( "This is not a pixmap" );
+ else
+ setPixmap( pix );
+ }
+ };
+ \endcode
+
+ In the above snippet, we create a preview widget which inherits from
+ QLabel and QFilePreviewP. File preview widgets \e must inherit from
+ QFilePreviewP.
+
+ Inside the class we reimplement QFilePreviewP::previewUrl(), this is
+ where we determine what happens when a file is selected. In the
+ above example we only show a preview of the file if it is a valid
+ pixmap. Here's how to make a file dialog use a preview widget:
+
+ \code
+ Preview* p = new Preview;
+
+ QFileDialogP* fd = new QFileDialogP( this );
+ fd->setContentsPreviewEnabled( TRUE );
+ fd->setContentsPreview( p, p );
+ fd->setPreviewMode( QFileDialogP::Contents );
+ fd->show();
+ \endcode
+
+ The first line creates an instance of our preview widget. We then
+ create our file dialog and call setContentsPreviewEnabled( TRUE ),
+ this tell the file dialog to preview the contents of the currently
+ selected file. We then call setContentsPreview() -- note that we pass
+ the same preview widget twice. Finally, before showing the file
+ dialog, we call setPreviewMode() setting the mode to \e Contents which
+ will show the contents preview of the file that the user has selected.
+
+ If you create another preview widget that is used for displaying
+ information about a file, create it in the same way as the contents
+ preview widget and call setInfoPreviewEnabled(), and
+ setInfoPreview(). Then the user will be able to switch between the
+ two preview modes.
+
+ For more information about creating a QFilePreviewP widget see
+ \l{QFilePreviewP}.
+
+ <img src=qfiledlg-m.png> <img src=qfiledlg-w.png>
+
+*/
+
+
+/*! \enum QFileDialogP::Mode
+
+ This enum is used to indicate what the user may select in the file
+ dialog, i.e. what the dialog will return if the user clicks OK.
+
+ \value AnyFile The name of a file, whether it exists or not.
+ \value ExistingFile The name of a single existing file.
+ \value Directory The name of a directory. Both files and directories
+ are displayed.
+ \value DirectoryOnly The name of a directory. The file dialog will only display directories.
+ \value ExistingFiles The names of zero or more existing files.
+
+ See setMode().
+*/
+
+/*!
+ \enum QFileDialogP::ViewMode
+
+ This enum describes the view mode of the file dialog, i.e. what
+ information about each file will be displayed.
+
+ \value List Display file and directory names with icons.
+ \value Detail Display file and directory names with icons plus
+ additional information, such as file size and modification date.
+
+ See setViewMode().
+*/
+
+/*!
+ \enum QFileDialogP::PreviewMode
+
+ This enum describes the preview mode of the file dialog.
+
+ \value NoPreview No preview is shown at all.
+ \value Contents Show a preview of the contents of the current file
+ using the contents preview widget.
+ \value Info Show information about the current file using the
+ info preview widget.
+
+ See setPreviewMode(), setContentsPreview() and setInfoPreview().
+*/
+
+/*!
+ \fn void QFileDialogP::detailViewSelectionChanged()
+ \internal
+*/
+
+/*!
+ \fn void QFileDialogP::listBoxSelectionChanged()
+ \internal
+*/
+
+extern const char qt_file_dialog_filter_reg_exp[] =
+ "([a-zA-Z0-9 ]*)\\(([a-zA-Z0-9_.*? +;#\\[\\]]*)\\)$";
+
+/*!
+ Constructs a file dialog called \a name, with the parent, \a parent.
+ If \a modal is TRUE then the file dialog is modal; otherwise it is
+ modeless.
+*/
+
+QFileDialogP::QFileDialogP( QWidget *parent, const char *name, bool modal )
+ : QDialog( parent, name, modal,
+ (modal ?
+ (WStyle_Customize | WStyle_DialogBorder | WStyle_Title | WStyle_SysMenu) : 0) )
+{
+ init();
+ d->mode = ExistingFile;
+ d->types->insertItem( tr( "All Files (*)" ) );
+ emit dirEntered( d->url.dirPath() );
+ rereadDir();
+}
+
+
+/*!
+ Constructs a file dialog called \a name with the parent, \a parent.
+ If \a modal is TRUE then the file dialog is modal; otherwise it is
+ modeless.
+
+ If \a dirName is specified then it will be used as the dialog's
+ working directory, i.e. it will be the directory that is shown when
+ the dialog appears. If \a filter is specified it will be used as the
+ dialog's file filter.
+
+*/
+
+QFileDialogP::QFileDialogP( const QString& dirName, const QString & filter,
+ QWidget *parent, const char *name, bool modal )
+ : QDialog( parent, name, modal,
+ (modal ?
+ (WStyle_Customize | WStyle_DialogBorder | WStyle_Title | WStyle_SysMenu) : 0) )
+{
+ init();
+ d->mode = ExistingFile;
+ rereadDir();
+ if ( !dirName.isEmpty() )
+ setSelection( dirName );
+ else if ( workingDirectory && !workingDirectory->isEmpty() )
+ setDir( *workingDirectory );
+
+ if ( !filter.isEmpty() ) {
+ setFilters( filter );
+ if ( !dirName.isEmpty() ) {
+ int dotpos = dirName.find( QChar('.'), 0, FALSE );
+ if ( dotpos != -1 ) {
+ for ( int b=0 ; b<d->types->count() ; b++ ) {
+ if ( d->types->text(b).contains( dirName.right( dirName.length() - dotpos ) ) ) {
+ d->types->setCurrentItem( b );
+ setFilter( d->types->text( b ) );
+ return;
+ }
+ }
+ }
+ }
+ } else {
+ d->types->insertItem( tr( "All Files (*)" ) );
+ }
+}
+
+
+/*!
+ \internal
+ Initializes the file dialog.
+*/
+
+void QFileDialogP::init()
+{
+ setSizeGripEnabled( TRUE );
+ d = new QFileDialogPrivate();
+ d->mode = AnyFile;
+ d->last = 0;
+ d->moreFiles = 0;
+ d->infoPreview = FALSE;
+ d->contentsPreview = FALSE;
+ d->hadDotDot = FALSE;
+ d->ignoreNextKeyPress = FALSE;
+ d->progressDia = 0;
+ d->checkForFilter = FALSE;
+ d->ignoreReturn = FALSE;
+ d->ignoreNextRefresh = FALSE;
+ d->ignoreStop = FALSE;
+ d->pendingItems.setAutoDelete( FALSE );
+ d->mimeTypeTimer = new QTimer( this );
+ connect( d->mimeTypeTimer, SIGNAL( timeout() ),
+ this, SLOT( doMimeTypeLookup() ) );
+
+ d->url = QUrlOperator( QDir::currentDirPath() );
+ d->oldUrl = d->url;
+ d->currListChildren = 0;
+
+ connect( &d->url, SIGNAL( start( QNetworkOperation * ) ),
+ this, SLOT( urlStart( QNetworkOperation * ) ) );
+ connect( &d->url, SIGNAL( finished( QNetworkOperation * ) ),
+ this, SLOT( urlFinished( QNetworkOperation * ) ) );
+ connect( &d->url, SIGNAL( newChildren( const QValueList<QUrlInfo> &, QNetworkOperation * ) ),
+ this, SLOT( insertEntry( const QValueList<QUrlInfo> &, QNetworkOperation * ) ) );
+ connect( &d->url, SIGNAL( removed( QNetworkOperation * ) ),
+ this, SLOT( removeEntry( QNetworkOperation * ) ) );
+ connect( &d->url, SIGNAL( createdDirectory( const QUrlInfo &, QNetworkOperation * ) ),
+ this, SLOT( createdDirectory( const QUrlInfo &, QNetworkOperation * ) ) );
+ connect( &d->url, SIGNAL( itemChanged( QNetworkOperation * ) ),
+ this, SLOT( itemChanged( QNetworkOperation * ) ) );
+ connect( &d->url, SIGNAL( dataTransferProgress( int, int, QNetworkOperation * ) ),
+ this, SLOT( dataTransferProgress( int, int, QNetworkOperation * ) ) );
+
+ nameEdit = new QLineEdit( this, "name/filter editor" );
+ nameEdit->setMaxLength( 255 ); //_POSIX_MAX_PATH
+ connect( nameEdit, SIGNAL(textChanged(const QString&)),
+ this, SLOT(fileNameEditDone()) );
+ nameEdit->installEventFilter( this );
+
+ d->splitter = new QSplitter( this, "qt_splitter" );
+
+ d->stack = new QWidgetStack( d->splitter, "files and more files" );
+
+ d->splitter->setSizePolicy( QSizePolicy( QSizePolicy::Expanding, QSizePolicy::Expanding ) );
+
+ files = new QFileDialogQFileListView( d->stack, this );
+ QFontMetrics fm = fontMetrics();
+ files->addColumn( tr("Name") );
+ files->addColumn( tr("Size") );
+ files->setColumnAlignment( 1, AlignRight );
+ files->addColumn( tr("Type") );
+ files->addColumn( tr("Date") );
+ files->addColumn( tr("Attributes") );
+ files->header()->setStretchEnabled( TRUE, 0 );
+
+ files->setMinimumSize( 50, 25 + 2*fm.lineSpacing() );
+
+ connect( files, SIGNAL( selectionChanged() ),
+ this, SLOT( detailViewSelectionChanged() ) );
+ connect( files, SIGNAL(currentChanged(QListViewItem *)),
+ this, SLOT(updateFileNameEdit(QListViewItem *)) );
+ connect( files, SIGNAL(doubleClicked(QListViewItem *)),
+ this, SLOT(selectDirectoryOrFile(QListViewItem *)) );
+ connect( files, SIGNAL(returnPressed(QListViewItem *)),
+ this, SLOT(selectDirectoryOrFile(QListViewItem *)) );
+ connect( files, SIGNAL(rightButtonPressed(QListViewItem *,
+ const QPoint &, int)),
+ this, SLOT(popupContextMenu(QListViewItem *,
+ const QPoint &, int)) );
+
+ files->installEventFilter( this );
+ files->viewport()->installEventFilter( this );
+
+ d->moreFiles = new QFileListBox( d->stack, this );
+ d->moreFiles->setRowMode( QListBox::FitToHeight );
+ d->moreFiles->setVariableWidth( TRUE );
+
+ connect( d->moreFiles, SIGNAL(selected(QListBoxItem *)),
+ this, SLOT(selectDirectoryOrFile(QListBoxItem *)) );
+ connect( d->moreFiles, SIGNAL( selectionChanged() ),
+ this, SLOT( listBoxSelectionChanged() ) );
+ connect( d->moreFiles, SIGNAL(highlighted(QListBoxItem *)),
+ this, SLOT(updateFileNameEdit(QListBoxItem *)) );
+ connect( d->moreFiles, SIGNAL( rightButtonPressed( QListBoxItem *, const QPoint & ) ),
+ this, SLOT( popupContextMenu( QListBoxItem *, const QPoint & ) ) );
+
+ d->moreFiles->installEventFilter( this );
+ d->moreFiles->viewport()->installEventFilter( this );
+
+ okB = new QPushButton( tr("OK"), this, "OK" ); //### Or "Save (see other "OK")
+ okB->setDefault( TRUE );
+ okB->setEnabled( FALSE );
+ connect( okB, SIGNAL(clicked()), this, SLOT(okClicked()) );
+ cancelB = new QPushButton( tr("Cancel") , this, "Cancel" );
+ connect( cancelB, SIGNAL(clicked()), this, SLOT(cancelClicked()) );
+
+ d->paths = new QComboBox( TRUE, this, "directory history/editor" );
+ d->paths->setDuplicatesEnabled( FALSE );
+ d->paths->setInsertionPolicy( QComboBox::NoInsertion );
+ const QFileInfoList * rootDrives = QDir::drives();
+ QFileInfoListIterator it( *rootDrives );
+ QFileInfo *fi;
+ makeVariables();
+
+ while ( (fi = it.current()) != 0 ) {
+ ++it;
+ d->paths->insertItem( *openFolderIcon, fi->absFilePath() );
+ }
+
+ if ( !!QDir::homeDirPath() ) {
+ if ( !d->paths->listBox()->findItem( QDir::homeDirPath() ) )
+ d->paths->insertItem( *openFolderIcon, QDir::homeDirPath() );
+ }
+
+ connect( d->paths, SIGNAL(activated(const QString&)),
+ this, SLOT(setDir(const QString&)) );
+
+ d->paths->installEventFilter( this );
+ QObjectList *ol = d->paths->queryList( "QLineEdit" );
+ if ( ol && ol->first() )
+ ( (QLineEdit*)ol->first() )->installEventFilter( this );
+ delete ol;
+
+ d->geometryDirty = TRUE;
+ d->types = new QComboBox( TRUE, this, "file types" );
+ d->types->setDuplicatesEnabled( FALSE );
+ d->types->setEditable( FALSE );
+ connect( d->types, SIGNAL(activated(const QString&)),
+ this, SLOT(setFilter(const QString&)) );
+ connect( d->types, SIGNAL(activated(const QString&)),
+ this, SIGNAL(filterSelected(const QString&)) );
+
+ d->pathL = new QLabel( d->paths, tr("Look &in:"), this, "qt_looin_lbl" );
+ d->fileL = new QLabel( nameEdit, tr("File &name:"), this, "qt_filename_lbl" );
+ d->typeL = new QLabel( d->types, tr("File &type:"), this, "qt_filetype_lbl" );
+
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP ) {
+ d->goBack = new QToolButton( this, "go back" );
+ d->goBack->setAutoRaise( TRUE );
+ d->goBack->setEnabled( FALSE );
+ d->goBack->setFocusPolicy( TabFocus );
+ connect( d->goBack, SIGNAL( clicked() ),
+ this, SLOT( goBack() ) );
+ QToolTip::add( d->goBack, tr( "Back" ) );
+ d->goBack->setIconSet( *goBackIcon );
+ } else {
+ d->goBack = 0;
+ }
+#else
+ d->goBack = 0;
+#endif
+
+ d->cdToParent = new QToolButton( this, "cd to parent" );
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP )
+ d->cdToParent->setAutoRaise( TRUE );
+#endif
+ d->cdToParent->setFocusPolicy( TabFocus );
+#ifndef QT_NO_TOOLTIP
+ QToolTip::add( d->cdToParent, tr( "One directory up" ) );
+#endif
+ d->cdToParent->setIconSet( *cdToParentIcon );
+ connect( d->cdToParent, SIGNAL(clicked()),
+ this, SLOT(cdUpClicked()) );
+
+ d->newFolder = new QToolButton( this, "new folder" );
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP )
+ d->newFolder->setAutoRaise( TRUE );
+#endif
+ d->newFolder->setFocusPolicy( TabFocus );
+#ifndef QT_NO_TOOLTIP
+ QToolTip::add( d->newFolder, tr( "Create New Folder" ) );
+#endif
+ d->newFolder->setIconSet( *newFolderIcon );
+ connect( d->newFolder, SIGNAL(clicked()),
+ this, SLOT(newFolderClicked()) );
+
+ d->modeButtons = new QButtonGroup( 0, "invisible group" );
+ connect( d->modeButtons, SIGNAL(destroyed()),
+ this, SLOT(modeButtonsDestroyed()) );
+ d->modeButtons->setExclusive( TRUE );
+ connect( d->modeButtons, SIGNAL(clicked(int)),
+ d->stack, SLOT(raiseWidget(int)) );
+ connect( d->modeButtons, SIGNAL(clicked(int)),
+ this, SLOT(changeMode(int)) );
+
+ d->mcView = new QToolButton( this, "mclistbox view" );
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP )
+ d->mcView->setAutoRaise( TRUE );
+#endif
+ d->mcView->setFocusPolicy( TabFocus );
+#ifndef QT_NO_TOOLTIP
+ QToolTip::add( d->mcView, tr( "List View" ) );
+#endif
+ d->mcView->setIconSet( *multiColumnListViewIcon );
+ d->mcView->setToggleButton( TRUE );
+ d->stack->addWidget( d->moreFiles, d->modeButtons->insert( d->mcView ) );
+ d->detailView = new QToolButton( this, "list view" );
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP )
+ d->detailView->setAutoRaise( TRUE );
+#endif
+ d->detailView->setFocusPolicy( TabFocus );
+#ifndef QT_NO_TOOLTIP
+ QToolTip::add( d->detailView, tr( "Detail View" ) );
+#endif
+ d->detailView->setIconSet( *detailViewIcon );
+ d->detailView->setToggleButton( TRUE );
+ d->stack->addWidget( files, d->modeButtons->insert( d->detailView ) );
+
+ d->previewInfo = new QToolButton( this, "preview info view" );
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP )
+ d->previewInfo->setAutoRaise( TRUE );
+#endif
+ d->previewInfo->setFocusPolicy( TabFocus );
+#ifndef QT_NO_TOOLTIP
+ QToolTip::add( d->previewInfo, tr( "Preview File Info" ) );
+#endif
+ d->previewInfo->setIconSet( *previewInfoViewIcon );
+ d->previewInfo->setToggleButton( TRUE );
+ d->modeButtons->insert( d->previewInfo );
+
+ d->previewContents = new QToolButton( this, "preview info view" );
+#if defined(Q_WS_WIN)
+ if ( qt_winver == Qt::WV_2000 || qt_winver == Qt::WV_XP )
+ d->previewContents->setAutoRaise( TRUE );
+#endif
+ d->previewContents->setFocusPolicy( TabFocus );
+#ifndef QT_NO_TOOLTIP
+ QToolTip::add( d->previewContents, tr( "Preview File Contents" ) );
+#endif
+ d->previewContents->setIconSet( *previewContentsViewIcon );
+ d->previewContents->setToggleButton( TRUE );
+ d->modeButtons->insert( d->previewContents );
+
+ connect( d->detailView, SIGNAL( clicked() ),
+ d->moreFiles, SLOT( cancelRename() ) );
+ connect( d->detailView, SIGNAL( clicked() ),
+ files, SLOT( cancelRename() ) );
+ connect( d->mcView, SIGNAL( clicked() ),
+ d->moreFiles, SLOT( cancelRename() ) );
+ connect( d->mcView, SIGNAL( clicked() ),
+ files, SLOT( cancelRename() ) );
+
+ d->stack->raiseWidget( d->moreFiles );
+ d->mcView->setOn( TRUE );
+
+ QHBoxLayout *lay = new QHBoxLayout( this );
+ lay->setMargin( 6 );
+ d->leftLayout = new QHBoxLayout( lay, 5 );
+ d->topLevelLayout = new QVBoxLayout( (QWidget*)0, 5 );
+ lay->addLayout( d->topLevelLayout, 1 );
+ d->extraWidgetsLayouts.setAutoDelete( FALSE );
+ d->extraLabels.setAutoDelete( FALSE );
+ d->extraWidgets.setAutoDelete( FALSE );
+ d->extraButtons.setAutoDelete( FALSE );
+ d->toolButtons.setAutoDelete( FALSE );
+
+ QHBoxLayout * h;
+
+ d->preview = new QWidgetStack( d->splitter, "qt_preview" );
+
+ d->infoPreviewWidget = new QWidget( d->preview, "qt_preview_info" );
+ d->contentsPreviewWidget = new QWidget( d->preview, "qt_preview_contents" );
+ d->infoPreviewer = d->contentsPreviewer = 0;
+
+ h = new QHBoxLayout( 0 );
+ d->buttonLayout = h;
+ d->topLevelLayout->addLayout( h );
+ h->addWidget( d->pathL );
+ h->addSpacing( 8 );
+ h->addWidget( d->paths );
+ h->addSpacing( 8 );
+ if ( d->goBack )
+ h->addWidget( d->goBack );
+ h->addWidget( d->cdToParent );
+ h->addSpacing( 2 );
+ h->addWidget( d->newFolder );
+ h->addSpacing( 4 );
+ h->addWidget( d->mcView );
+ h->addWidget( d->detailView );
+ h->addWidget( d->previewInfo );
+ h->addWidget( d->previewContents );
+
+ d->topLevelLayout->addWidget( d->splitter );
+
+ h = new QHBoxLayout();
+ d->topLevelLayout->addLayout( h );
+ h->addWidget( d->fileL );
+ h->addWidget( nameEdit );
+ h->addSpacing( 15 );
+ h->addWidget( okB );
+
+ h = new QHBoxLayout();
+ d->topLevelLayout->addLayout( h );
+ h->addWidget( d->typeL );
+ h->addWidget( d->types );
+ h->addSpacing( 15 );
+ h->addWidget( cancelB );
+
+ d->rightLayout = new QHBoxLayout( lay, 5 );
+ d->topLevelLayout->setStretchFactor( d->mcView, 1 );
+ d->topLevelLayout->setStretchFactor( files, 1 );
+
+ updateGeometries();
+
+ if ( d->goBack ) {
+ setTabOrder( d->paths, d->goBack );
+ setTabOrder( d->goBack, d->cdToParent );
+ } else {
+ setTabOrder( d->paths, d->cdToParent );
+ }
+ setTabOrder( d->cdToParent, d->newFolder );
+ setTabOrder( d->newFolder, d->mcView );
+ setTabOrder( d->mcView, d->detailView );
+ setTabOrder( d->detailView, d->moreFiles );
+ setTabOrder( d->moreFiles, files );
+ setTabOrder( files, nameEdit );
+ setTabOrder( nameEdit, d->types );
+ setTabOrder( d->types, okB );
+ setTabOrder( okB, cancelB );
+
+ d->rw = tr( "Read-write" );
+ d->ro = tr( "Read-only" );
+ d->wo = tr( "Write-only" );
+ d->inaccessible = tr( "Inaccessible" );
+
+ d->symLinkToFile = tr( "Symlink to File" );
+ d->symLinkToDir = tr( "Symlink to Directory" );
+ d->symLinkToSpecial = tr( "Symlink to Special" );
+ d->file = tr( "File" );
+ d->dir = tr( "Dir" );
+ d->special = tr( "Special" );
+
+ if ( !lastSize ) {
+ QRect screen = QApplication::desktop()->screenGeometry( QApplication::desktop()->screenNumber( pos() ) );
+ if ( screen.width() < 1024 ||
+ screen.height() < 768 ) {
+ resize( QMIN(screen.width(),420),
+ QMIN(screen.height(),236) );
+ } else {
+ QSize s( files->sizeHint() );
+ s = QSize( s.width() + 300, s.height() + 82 );
+
+ if ( s.width() * 3 > screen.width() * 2 )
+ s.setWidth( screen.width() * 2 / 3 );
+
+ if ( s.height() * 3 > screen.height() * 2 )
+ s.setHeight( screen.height() * 2 / 3 );
+ else if ( s.height() * 3 < screen.height() )
+ s.setHeight( screen.height() / 3 );
+
+ resize( s );
+ }
+ lastSize = new QSize;
+ qfd_cleanup_size.add( &lastSize );
+ *lastSize = size();
+ } else
+ resize( *lastSize );
+
+ if ( detailViewMode ) {
+ d->stack->raiseWidget( files );
+ d->mcView->setOn( FALSE );
+ d->detailView->setOn( TRUE );
+ }
+
+ d->preview->hide();
+ nameEdit->setFocus();
+
+ connect( nameEdit, SIGNAL( returnPressed() ),
+ this, SLOT( fileNameEditReturnPressed() ) );
+}
+
+/*!
+ \internal
+*/
+
+void QFileDialogP::fileNameEditReturnPressed()
+{
+ d->oldUrl = d->url;
+ if ( !isDirectoryMode( d->mode ) ) {
+ okClicked();
+ } else {
+ d->currentFileName = QString::null;
+ if ( nameEdit->text().isEmpty() ) {
+ emit fileSelected( selectedFile() );
+ accept();
+ } else {
+ QUrlInfo f;
+ QFileDialogPrivate::File * c
+ = (QFileDialogPrivate::File *)files->currentItem();
+ if ( c && files->isSelected(c) )
+ f = c->info;
+ else
+ f = QUrlInfo( d->url, nameEdit->text() );
+ if ( f.isDir() ) {
+ setUrl( QUrlOperator( d->url, QFileDialogPrivate::encodeFileName(nameEdit->text() + "/" ) ) );
+ d->checkForFilter = TRUE;
+ trySetSelection( TRUE, d->url, TRUE );
+ d->checkForFilter = FALSE;
+ }
+ }
+ nameEdit->setText( QString::null );
+ d->ignoreReturn = TRUE;
+ }
+}
+
+/*!
+ \internal
+ Changes the preview mode to the mode specified at \a id.
+*/
+
+void QFileDialogP::changeMode( int id )
+{
+ if ( !d->infoPreview && !d->contentsPreview )
+ return;
+
+ QButton *btn = (QButton*)d->modeButtons->find( id );
+ if ( !btn )
+ return;
+
+ if ( btn == d->previewContents && !d->contentsPreview )
+ return;
+ if ( btn == d->previewInfo && !d->infoPreview )
+ return;
+
+ if ( btn != d->previewContents && btn != d->previewInfo ) {
+ d->preview->hide();
+ } else {
+ if ( files->currentItem() ) {
+ if ( d->infoPreviewer )
+ d->infoPreviewer->previewUrl( QUrl( d->url, files->currentItem()->text( 0 ) ) );
+ if ( d->contentsPreviewer )
+ d->contentsPreviewer->previewUrl( QUrl( d->url, files->currentItem()->text( 0 ) ) );
+ }
+ if ( btn == d->previewInfo )
+ d->preview->raiseWidget( d->infoPreviewWidget );
+ else
+ d->preview->raiseWidget( d->contentsPreviewWidget );
+ d->preview->show();
+ }
+}
+
+/*!
+ Destroys the file dialog.
+*/
+
+QFileDialogP::~QFileDialogP()
+{
+ // since clear might call setContentsPos which would emit
+ // a signal and thus cause a recompute of sizes...
+ files->blockSignals( TRUE );
+ d->moreFiles->blockSignals( TRUE );
+ files->clear();
+ d->moreFiles->clear();
+ d->moreFiles->blockSignals( FALSE );
+ files->blockSignals( FALSE );
+ if ( QApplication::overrideCursor() )
+ QApplication::restoreOverrideCursor();
+ delete d;
+ d = 0;
+}
+
+
+/*!
+ \property QFileDialogP::selectedFile
+
+ \brief the name of the selected file
+
+ If a file was selected selectedFile contains the file's name including
+ its absolute path; otherwise selectedFile is empty.
+
+ \sa QString::isEmpty(), selectedFiles, selectedFilter
+*/
+
+QString QFileDialogP::selectedFile() const
+{
+ QString s = d->currentFileName;
+ // remove the protocol because we do not want to encode it...
+ QString prot = QUrl( s ).protocol();
+ if ( !prot.isEmpty() ) {
+ prot += ":";
+ s.remove( 0, prot.length() );
+ }
+ QUrl u( prot + QFileDialogPrivate::encodeFileName( s ) );
+ if ( u.isLocalFile() ) {
+ QString s = u.toString();
+ if ( s.left( 5 ) == "file:" )
+ s.remove( 0, 5 );
+ return s;
+ }
+ return d->currentFileName;
+}
+
+/*!
+ \property QFileDialogP::selectedFilter
+
+ \brief the filter which the user has selected in the file dialog
+
+ \sa filterSelected(), selectedFiles, selectedFile
+*/
+
+QString QFileDialogP::selectedFilter() const
+{
+ return d->types->currentText();
+}
+
+/*! \overload
+
+ Sets the current filter selected in the file dialog to the
+ \a{n}-th filter in the filter list.
+
+ \sa filterSelected(), selectedFilter(), selectedFiles(), selectedFile()
+*/
+
+void QFileDialogP::setSelectedFilter( int n )
+{
+ d->types->setCurrentItem( n );
+ QString f = d->types->currentText();
+ QRegExp r( QString::fromLatin1(qt_file_dialog_filter_reg_exp) );
+ int index = r.search( f );
+ if ( index >= 0 )
+ f = r.cap( 2 );
+ d->url.setNameFilter( f );
+ rereadDir();
+}
+
+/*!
+ Sets the current filter selected in the file dialog to the first
+ one that contains the text \a mask.
+*/
+
+void QFileDialogP::setSelectedFilter( const QString& mask )
+{
+ int n;
+
+ for ( n = 0; n < d->types->count(); n++ ) {
+ if ( d->types->text( n ).contains( mask, FALSE ) ) {
+ d->types->setCurrentItem( n );
+ QString f = mask;
+ QRegExp r( QString::fromLatin1(qt_file_dialog_filter_reg_exp) );
+ int index = r.search( f );
+ if ( index >= 0 )
+ f = r.cap( 2 );
+ d->url.setNameFilter( f );
+ rereadDir();
+ return;
+ }
+ }
+}
+
+/*!
+ \property QFileDialogP::selectedFiles
+
+ \brief the list of selected files
+
+ If one or more files are selected, selectedFiles contains their
+ names including their absolute paths. If no files are selected or
+ the mode isn't ExistingFiles selectedFiles is an empty list.
+
+ It is more convenient to use selectedFile() if the mode is
+ \c ExistingFile, \c Directory or \c DirectoryOnly.
+
+ Note that if you want to iterate over the list, you should
+ iterate over a copy, e.g.
+ \code
+ QStringList list = myFileDialog.selectedFiles();
+ QStringList::Iterator it = list.begin();
+ while( it != list.end() ) {
+ myProcessing( *it );
+ ++it;
+ }
+ \endcode
+
+ \sa selectedFile, selectedFilter, QValueList::empty()
+*/
+
+QStringList QFileDialogP::selectedFiles() const
+{
+ QStringList lst;
+
+ if ( mode() == ExistingFiles ) {
+ QStringList selectedLst;
+ QString selectedFiles = nameEdit->text();
+ selectedFiles.truncate( selectedFiles.findRev( '\"' ) );
+ selectedLst = selectedLst.split( QString("\" "), selectedFiles );
+ for ( QStringList::Iterator it = selectedLst.begin(); it != selectedLst.end(); ++it ) {
+ QUrl u;
+ if ( (*it)[0] == '\"' ) {
+ u = QUrl( d->url, QFileDialogPrivate::encodeFileName( (*it).mid(1) ) );
+ } else {
+ u = QUrl( d->url, QFileDialogPrivate::encodeFileName( (*it) ) );
+ }
+ if ( u.isLocalFile() ) {
+ QString s = u.toString();
+ if ( s.left( 5 ) == "file:" )
+ s.remove( 0, 5 );
+ lst << s;
+ } else {
+ lst << u.toString();
+ }
+ }
+ }
+
+ return lst;
+}
+
+/*!
+ Sets the default selection to \a filename. If \a filename is
+ absolute, setDir() is also called to set the file dialog's working
+ directory to the filename's directory.
+
+ \omit
+ Only for external use. Not useful inside QFileDialogP.
+ \endomit
+*/
+
+void QFileDialogP::setSelection( const QString & filename )
+{
+ d->oldUrl = d->url;
+ QString nf = d->url.nameFilter();
+ if ( QUrl::isRelativeUrl( filename ) )
+ d->url = QUrlOperator( d->url, QFileDialogPrivate::encodeFileName( filename ) );
+ else
+ d->url = QUrlOperator( filename );
+ d->url.setNameFilter( nf );
+ d->checkForFilter = TRUE;
+ bool isDirOk;
+ bool isDir = d->url.isDir( &isDirOk );
+ if ( !isDirOk )
+ isDir = d->url.path().right( 1 ) == "/";
+ if ( !isDir ) {
+ QUrlOperator u( d->url );
+ d->url.setPath( d->url.dirPath() );
+ trySetSelection( FALSE, u, TRUE );
+ d->ignoreNextRefresh = TRUE;
+ nameEdit->selectAll();
+ rereadDir();
+ emit dirEntered( d->url.dirPath() );
+ } else {
+ if ( !d->url.path().isEmpty() &&
+ d->url.path().right( 1 ) != "/" ) {
+ QString p = d->url.path();
+ p += "/";
+ d->url.setPath( p );
+ }
+ trySetSelection( TRUE, d->url, FALSE );
+ rereadDir();
+ emit dirEntered( d->url.dirPath() );
+ nameEdit->setText( QString::fromLatin1("") );
+ }
+ d->checkForFilter = FALSE;
+}
+
+/*!
+ \property QFileDialogP::dirPath
+
+ \brief the file dialog's working directory
+
+ \sa dir(), setDir()
+*/
+
+QString QFileDialogP::dirPath() const
+{
+ return d->url.dirPath();
+}
+
+
+/*!
+
+ Sets the filter used in the file dialog to \a newFilter.
+
+ If \a newFilter contains a pair of parentheses containing one or more
+ of <em><b>anything*something</b></em> separated by spaces or by
+ semi-colons then only the text contained in the parentheses is used as
+ the filter. This means that these calls are all equivalent:
+
+ \code
+ fd->setFilter( "All C++ files (*.cpp *.cc *.C *.cxx *.c++)" );
+ fd->setFilter( "*.cpp *.cc *.C *.cxx *.c++" );
+ fd->setFilter( "All C++ files (*.cpp;*.cc;*.C;*.cxx;*.c++)" );
+ fd->setFilter( "*.cpp;*.cc;*.C;*.cxx;*.c++" );
+ \endcode
+
+ \sa setFilters()
+*/
+
+void QFileDialogP::setFilter( const QString & newFilter )
+{
+ if ( newFilter.isEmpty() )
+ return;
+ QString f = newFilter;
+ QRegExp r( QString::fromLatin1(qt_file_dialog_filter_reg_exp) );
+ int index = r.search( f );
+ if ( index >= 0 )
+ f = r.cap( 2 );
+ d->url.setNameFilter( f );
+ if ( d->types->count() == 1 ) {
+ d->types->clear();
+ d->types->insertItem( newFilter );
+ } else {
+ for ( int i = 0; i < d->types->count(); ++i ) {
+ if ( d->types->text( i ).left( newFilter.length() ) == newFilter ) {
+ d->types->setCurrentItem( i );
+ break;
+ }
+ }
+ }
+ rereadDir();
+}
+
+
+/*! \overload
+ Sets the file dialog's working directory to \a pathstr.
+
+ \sa dir()
+*/
+
+void QFileDialogP::setDir( const QString & pathstr )
+{
+ QString dr = pathstr;
+ if ( dr.isEmpty() )
+ return;
+
+#if defined(Q_OS_UNIX)
+ if ( dr.length() && dr[0] == '~' ) {
+ struct passwd *pw;
+ int i;
+
+ i = 0;
+ while( i < (int)dr.length() && dr[i] != '/' )
+ i++;
+ QCString user;
+ if ( i == 1 ) {
+ user = ::getlogin();
+ if ( !user )
+ user = getenv( "LOGNAME" );
+ } else
+ user = dr.mid( 1, i-1 ).local8Bit();
+ dr = dr.mid( i, dr.length() );
+ pw = ::getpwnam( user );
+ if ( pw )
+ dr.prepend( QString::fromLocal8Bit(pw->pw_dir) );
+ }
+#endif
+
+ setUrl( dr );
+}
+
+/*!
+ Returns the current directory shown in the file dialog.
+
+ The ownership of the QDir pointer is transferred to the caller, so
+ it must be deleted by the caller when no longer required.
+
+ \sa setDir()
+*/
+
+const QDir *QFileDialogP::dir() const
+{
+ if ( d->url.isLocalFile() )
+ return new QDir( d->url.path() );
+ else
+ return 0;
+}
+
+/*!
+ Sets the file dialog's working directory to \a dir.
+ \sa dir()
+*/
+
+void QFileDialogP::setDir( const QDir &dir )
+{
+ d->oldUrl = d->url;
+ QString nf( d->url.nameFilter() );
+ d->url = dir.canonicalPath();
+ d->url.setNameFilter( nf );
+ QUrlInfo i( d->url, nameEdit->text() );
+ d->checkForFilter = TRUE;
+ trySetSelection( i.isDir(), QUrlOperator( d->url, QFileDialogPrivate::encodeFileName(nameEdit->text() ) ), FALSE );
+ d->checkForFilter = FALSE;
+ rereadDir();
+ emit dirEntered( d->url.path() );
+}
+
+/*!
+ Sets the file dialog's working directory to the directory specified at \a url.
+
+ \sa url()
+*/
+
+void QFileDialogP::setUrl( const QUrlOperator &url )
+{
+ QString nf = d->url.nameFilter();
+
+ d->url = QUrl( d->url, url.toString( FALSE, FALSE ) );
+ d->url.setNameFilter( nf );
+
+ d->checkForFilter = TRUE;
+ if ( !d->url.isDir() ) {
+ QUrlOperator u = d->url;
+ d->url.setPath( d->url.dirPath() );
+ trySetSelection( FALSE, u, FALSE );
+ rereadDir();
+ emit dirEntered( d->url.dirPath() );
+ QString fn = u.fileName();
+ nameEdit->setText( fn );
+ } else {
+ trySetSelection( TRUE, d->url, FALSE );
+ rereadDir();
+ emit dirEntered( d->url.dirPath() );
+ }
+ d->checkForFilter = FALSE;
+}
+
+/*!
+ \property QFileDialogP::showHiddenFiles
+
+ \brief whether hidden files are shown in the file dialog
+
+ The default is FALSE, i.e. don't show hidden files.
+*/
+
+void QFileDialogP::setShowHiddenFiles( bool s )
+{
+ if ( s == bShowHiddenFiles )
+ return;
+
+ bShowHiddenFiles = s;
+ rereadDir();
+}
+
+bool QFileDialogP::showHiddenFiles() const
+{
+ return bShowHiddenFiles;
+}
+
+/*!
+ Rereads the current directory shown in the file dialog.
+
+ The only time you will need to call this function is if the contents of
+ the directory change and you wish to refresh the file dialog to reflect
+ the change.
+
+ \sa resortDir()
+*/
+
+void QFileDialogP::rereadDir()
+{
+ if ( !QApplication::overrideCursor() )
+ QApplication::setOverrideCursor( QCursor( Qt::WaitCursor ) );
+ d->pendingItems.clear();
+ if ( d->mimeTypeTimer->isActive() )
+ d->mimeTypeTimer->stop();
+ d->currListChildren = d->url.listChildren();
+}
+
+
+/*!
+ \fn void QFileDialogP::fileHighlighted( const QString& )
+
+ This signal is emitted when the user highlights a file.
+
+ \sa fileSelected(), filesSelected()
+*/
+
+/*!
+ \fn void QFileDialogP::fileSelected( const QString& )
+
+ This signal is emitted when the user selects a file.
+
+ \sa filesSelected(), fileHighlighted(), selectedFile()
+*/
+
+/*!
+ \fn void QFileDialogP::filesSelected( const QStringList& )
+
+ This signal is emitted when the user selects one or more files in \e
+ ExistingFiles mode.
+
+ \sa fileSelected(), fileHighlighted(), selectedFiles()
+*/
+
+/*!
+ \fn void QFileDialogP::dirEntered( const QString& )
+
+ This signal is emitted when the user enters a directory.
+
+ \sa dir()
+*/
+
+/*!
+ \fn void QFileDialogP::filterSelected( const QString& )
+
+ This signal is emitted when the user selects a filter.
+
+ \sa selectedFilter()
+*/
+
+extern bool qt_resolve_symlinks; // defined in qapplication.cpp
+
+/*!
+ This is a convenience static function that returns an existing file
+ selected by the user. If the user pressed Cancel, it returns a null
+ string.
+
+ \code
+ QString s = QFileDialogP::getOpenFileName(
+ "/home",
+ "Images (*.png *.xpm *.jpg)",
+ this,
+ "open file dialog",
+ "Choose a file to open" );
+ \endcode
+
+ The function creates a modal file dialog called \a name, with
+ parent, \a parent. If a parent is not 0, the dialog will be shown
+ centered over the parent.
+
+ The file dialog's working directory will be set to \a startWith. If \a
+ startWith includes a file name, the file will be selected. The filter
+ is set to \a filter so that only those files which match the filter
+ are shown. The filter selected is set to \a selectedFilter. The parameters
+ \a startWith, \a selectedFilter and \a filter may be QString::null.
+
+ The dialog's caption is set to \a caption. If \a caption is not
+ specified then a default caption will be used.
+
+ Under Windows and Mac OS X, this static function will use the native
+ file dialog and not a QFileDialogP, unless the style of the application
+ is set to something other than the native style.
+
+ Under Unix/X11, the normal behavior of the file dialog is to resolve
+ and follow symlinks. For example, if /usr/tmp is a symlink to /var/tmp,
+ the file dialog will change to /var/tmp after entering /usr/tmp.
+ If \a resolveSymlinks is FALSE, the file dialog will treat
+ symlinks as regular directories.
+
+ \sa getOpenFileNames(), getSaveFileName(), getExistingDirectory()
+*/
+
+QString QFileDialogP::getOpenFileName( const QString & startWith,
+ const QString& filter,
+ QWidget *parent, const char* name,
+ const QString& caption,
+ QString *selectedFilter,
+ bool resolveSymlinks )
+{
+ bool save_qt_resolve_symlinks = qt_resolve_symlinks;
+ qt_resolve_symlinks = resolveSymlinks;
+
+ QStringList filters;
+ if ( !filter.isEmpty() )
+ filters = makeFiltersList( filter );
+
+ makeVariables();
+ QString initialSelection;
+ //### Problem with the logic here: If a startWith is given and a file
+ // with that name exists in D->URL, the box will be opened at D->URL instead of
+ // the last directory used ('workingDirectory').
+ //
+ // hm... isn't that problem exactly the documented behaviour? the
+ // documented behaviour sounds meaningful.
+ if ( !startWith.isEmpty() ) {
+ QUrlOperator u( startWith );
+ if ( u.isLocalFile() && QFileInfo( u.path() ).isDir() ) {
+ *workingDirectory = startWith;
+ } else {
+ if ( u.isLocalFile() ) {
+ QFileInfo fi( u.dirPath() );
+ if ( fi.exists() ) {
+ *workingDirectory = u.dirPath();
+ initialSelection = u.fileName();
+ }
+ } else {
+ *workingDirectory = u.toString();
+ initialSelection = QString::null;//u.fileName();
+ }
+ }
+ }
+
+ if ( workingDirectory->isNull() )
+ *workingDirectory = QDir::currentDirPath();
+
+#if defined(Q_WS_WIN)
+ if ( qApp->style().styleHint( QStyle::SH_GUIStyle ) == WindowsStyle )
+ return winGetOpenFileName( initialSelection, filter, workingDirectory,
+ parent, name, caption, selectedFilter );
+#elif defined(Q_WS_MAC)
+ if( ( qApp->style().inherits(QMAC_DEFAULT_STYLE) ) ) {
+ QString f = macGetOpenFileNames(filter, workingDirectory,
+ parent, name, caption, FALSE).first();
+ return f;
+ }
+#endif
+
+ QFileDialogP *dlg = new QFileDialogP( *workingDirectory, QString::null, parent, name ? name : "qt_filedlg_gofn", TRUE );
+
+#ifndef QT_NO_WIDGET_TOPEXTRA
+ if ( parent && parent->icon() && !parent->icon()->isNull() )
+ dlg->setIcon( *parent->icon() );
+ else if ( qApp->mainWidget() && qApp->mainWidget()->icon() && !qApp->mainWidget()->icon()->isNull() )
+ dlg->setIcon( *qApp->mainWidget()->icon() );
+
+ if ( !caption.isNull() )
+ dlg->setCaption( caption );
+ else
+ dlg->setCaption( QFileDialogP::tr( "Open" ) );
+#endif
+
+ dlg->setFilters( filters );
+ if ( selectedFilter )
+ dlg->setFilter( *selectedFilter );
+ dlg->setMode( QFileDialogP::ExistingFile );
+ QString result;
+ if ( !initialSelection.isEmpty() )
+ dlg->setSelection( initialSelection );
+ if ( dlg->exec() == QDialog::Accepted ) {
+ result = dlg->selectedFile();
+ *workingDirectory = dlg->d->url;
+ if ( selectedFilter )
+ *selectedFilter = dlg->selectedFilter();
+ }
+ delete dlg;
+
+ qt_resolve_symlinks = save_qt_resolve_symlinks;
+
+ return result;
+}
+
+/*!
+ This is a convenience static function that will return a file name
+ selected by the user. The file does not have to exist.
+
+ It creates a modal file dialog called \a name, with parent, \a parent.
+ If a parent is not 0, the dialog will be shown centered over the
+ parent.
+
+ \code
+ QString s = QFileDialogP::getSaveFileName(
+ "/home",
+ "Images (*.png *.xpm *.jpg)",
+ this,
+ "save file dialog"
+ "Choose a filename to save under" );
+ \endcode
+
+ The file dialog's working directory will be set to \a startWith. If \a
+ startWith includes a file name, the file will be selected. The filter
+ is set to \a filter so that only those files which match the filter
+ are shown. The filter selected is set to \a selectedFilter. The parameters
+ \a startWith, \a selectedFilter and \a filter may be QString::null.
+
+ The dialog's caption is set to \a caption. If \a caption is not
+ specified then a default caption will be used.
+
+ Under Windows and Mac OS X, this static function will use the native
+ file dialog and not a QFileDialogP, unless the style of the application
+ is set to something other than the native style.
+
+ Under Unix/X11, the normal behavior of the file dialog is to resolve
+ and follow symlinks. For example, if /usr/tmp is a symlink to /var/tmp,
+ the file dialog will change to /var/tmp after entering /usr/tmp.
+ If \a resolveSymlinks is FALSE, the file dialog will treat
+ symlinks as regular directories.
+
+ \sa getOpenFileName(), getOpenFileNames(), getExistingDirectory()
+*/
+
+QString QFileDialogP::getSaveFileName( const QString & startWith,
+ const QString& filter,
+ QWidget *parent, const char* name,
+ const QString& caption,
+ QString *selectedFilter,
+ bool resolveSymlinks)
+{
+ bool save_qt_resolve_symlinks = qt_resolve_symlinks;
+ qt_resolve_symlinks = resolveSymlinks;
+
+ QStringList filters;
+ if ( !filter.isEmpty() )
+ filters = makeFiltersList( filter );
+
+ makeVariables();
+ QString initialSelection;
+ if ( !startWith.isEmpty() ) {
+ QUrlOperator u( startWith );
+ if ( u.isLocalFile() && QFileInfo( u.path() ).isDir() ) {
+ *workingDirectory = startWith;
+ } else {
+ if ( u.isLocalFile() ) {
+ QFileInfo fi( u.dirPath() );
+ if ( fi.exists() ) {
+ *workingDirectory = u.dirPath();
+ initialSelection = u.fileName();
+ }
+ } else {
+ *workingDirectory = u.toString();
+ initialSelection = QString::null;//u.fileName();
+ }
+ }
+ }
+
+ if ( workingDirectory->isNull() )
+ *workingDirectory = QDir::currentDirPath();
+
+#if defined(Q_WS_WIN)
+ if ( qApp->style().styleHint( QStyle::SH_GUIStyle ) == WindowsStyle )
+ return winGetSaveFileName( initialSelection, filter, workingDirectory,
+ parent, name, caption, selectedFilter );
+#elif defined(Q_WS_MAC)
+ if( ( qApp->style().inherits(QMAC_DEFAULT_STYLE) ) )
+ return macGetSaveFileName( initialSelection, filter, workingDirectory,
+ parent, name, caption );
+#endif
+
+ QFileDialogP *dlg = new QFileDialogP( *workingDirectory, QString::null, parent, name ? name : "qt_filedlg_gsfn", TRUE );
+
+ Q_CHECK_PTR( dlg );
+#ifndef QT_NO_WIDGET_TOPEXTRA
+ if ( parent && parent->icon() && !parent->icon()->isNull() )
+ dlg->setIcon( *parent->icon() );
+ else if ( qApp->mainWidget() && qApp->mainWidget()->icon() && !qApp->mainWidget()->icon()->isNull() )
+ dlg->setIcon( *qApp->mainWidget()->icon() );
+
+ if ( !caption.isNull() )
+ dlg->setCaption( caption );
+ else
+ dlg->setCaption( QFileDialogP::tr( "Save As" ) );
+#endif
+
+ QString result;
+ dlg->setFilters( filters );
+ if ( selectedFilter )
+ dlg->setFilter( *selectedFilter );
+ dlg->setMode( QFileDialogP::AnyFile );
+ if ( !initialSelection.isEmpty() )
+ dlg->setSelection( initialSelection );
+ if ( dlg->exec() == QDialog::Accepted ) {
+ result = dlg->selectedFile();
+ *workingDirectory = dlg->d->url;
+ if ( selectedFilter )
+ *selectedFilter = dlg->selectedFilter();
+ }
+ delete dlg;
+
+ qt_resolve_symlinks = save_qt_resolve_symlinks;
+
+ return result;
+}
+
+/*!
+ \internal
+ Activated when the "OK" button is clicked.
+*/
+
+void QFileDialogP::okClicked()
+{
+ QString fn( nameEdit->text() );
+
+#if defined(Q_WS_WIN)
+ QFileInfo fi( d->url.path() + fn );
+ if ( fi.isSymLink() ) {
+ nameEdit->setText( fi.readLink() );
+ }
+#endif
+
+ if ( fn.contains("*") ) {
+ addFilter( fn );
+ nameEdit->blockSignals( TRUE );
+ nameEdit->setText( QString::fromLatin1("") );
+ nameEdit->blockSignals( FALSE );
+ return;
+ }
+
+ *workingDirectory = d->url;
+ detailViewMode = files->isVisible();
+ *lastSize = size();
+
+ if ( isDirectoryMode( d->mode ) ) {
+ if ( d->ignoreReturn ) {
+ d->ignoreReturn = FALSE;
+ return;
+ }
+ QUrlInfo f( d->url, nameEdit->text() );
+ if ( f.isDir() ) {
+ d->currentFileName = d->url;
+ if ( d->currentFileName.right(1) != "/" )
+ d->currentFileName += '/';
+ if ( f.name() != "." )
+ d->currentFileName += f.name();
+ accept();
+ return;
+ }
+ }
+
+ // if we're in multi-selection mode and something is selected,
+ // accept it and be done.
+ if ( mode() == ExistingFiles ) {
+ if ( ! nameEdit->text().isEmpty() ) {
+ QStringList sf = selectedFiles();
+ bool isdir = FALSE;
+ if ( sf.count() == 1 ) {
+ QUrlOperator u( d->url, sf[0] );
+ bool ok;
+ isdir = u.isDir(&ok) && ok;
+ }
+ if ( !isdir ) {
+ emit filesSelected( sf );
+ accept();
+ return;
+ }
+ }
+ }
+
+ if ( mode() == AnyFile ) {
+ QUrlOperator u( d->url, QFileDialogPrivate::encodeFileName(nameEdit->text()) );
+ if ( !u.isDir() ) {
+ d->currentFileName = u;
+ emit fileSelected( selectedFile() );
+ accept();
+ return;
+ }
+ }
+
+ if ( mode() == ExistingFile ) {
+ QUrl u( d->url, QFileDialogPrivate::encodeFileName(nameEdit->text()) );
+ if ( u.isLocalFile() ) {
+ QFileInfo f( u.path() );
+ if ( !f.exists() )
+ return;
+ } else {
+ QNetworkProtocol *p = QNetworkProtocol::getNetworkProtocol( d->url.protocol() );
+ if ( p && (p->supportedOperations()&QNetworkProtocol::OpListChildren) ) {
+ QUrlInfo ui( d->url, nameEdit->text() );
+ if ( !ui.isValid() )
+ return;
+ }
+ }
+ }
+
+ // If selection is valid, return it, else try
+ // using selection as a directory to change to.
+ if ( !d->currentFileName.isNull() && !d->currentFileName.contains( "*" ) ) {
+ emit fileSelected( selectedFile() );
+ accept();
+ } else {
+ QUrlInfo f;
+ QFileDialogPrivate::File * c
+ = (QFileDialogPrivate::File *)files->currentItem();
+ QFileDialogPrivate::MCItem * m
+ = (QFileDialogPrivate::MCItem *)d->moreFiles->item( d->moreFiles->currentItem() );
+ if ( c && files->isVisible() && files->hasFocus() ||
+ m && d->moreFiles->isVisible() && d->moreFiles->hasFocus() ) {
+ if ( c && files->isVisible() )
+ f = c->info;
+ else
+ f = ( (QFileDialogPrivate::File*)m->i )->info;
+ } else {
+ f = QUrlInfo( d->url, nameEdit->text() );
+ }
+ if ( f.isDir() ) {
+ setUrl( QUrlOperator( d->url, QFileDialogPrivate::encodeFileName(f.name() + "/" ) ) );
+ d->checkForFilter = TRUE;
+ trySetSelection( TRUE, d->url, TRUE );
+ d->checkForFilter = FALSE;
+ } else {
+ if ( !nameEdit->text().contains( "/" ) &&
+ !nameEdit->text().contains( "\\" )
+#if defined(Q_OS_WIN32)
+ && nameEdit->text()[ 1 ] != ':'
+#endif
+ )
+ addFilter( nameEdit->text() );
+ else if ( nameEdit->text()[ 0 ] == '/' ||
+ nameEdit->text()[ 0 ] == '\\'
+#if defined(Q_OS_WIN32)
+ || nameEdit->text()[ 1 ] == ':'
+#endif
+ )
+ setDir( nameEdit->text() );
+ else if ( nameEdit->text().left( 3 ) == "../" || nameEdit->text().left( 3 ) == "..\\" )
+ setDir( QUrl( d->url.toString(), QFileDialogPrivate::encodeFileName(nameEdit->text() ) ).toString() );
+ }
+ nameEdit->setText( "" );
+ }
+}
+
+/*!
+ \internal
+ Activated when the "Filter" button is clicked.
+*/
+
+void QFileDialogP::filterClicked()
+{
+ // unused
+}
+
+/*!
+ \internal
+ Activated when the "Cancel" button is clicked.
+*/
+
+void QFileDialogP::cancelClicked()
+{
+ *workingDirectory = d->url;
+ detailViewMode = files->isVisible();
+ *lastSize = size();
+ reject();
+}
+
+
+/*!\reimp
+*/
+
+void QFileDialogP::resizeEvent( QResizeEvent * e )
+{
+ QDialog::resizeEvent( e );
+ updateGeometries();
+}
+
+/*
+ \internal
+ The only correct way to try to set currentFileName
+*/
+bool QFileDialogP::trySetSelection( bool isDir, const QUrlOperator &u, bool updatelined )
+{
+ if ( !isDir && !u.path().isEmpty() && u.path().right( 1 ) == "/" )
+ isDir = TRUE;
+ if ( u.fileName().contains( "*") && d->checkForFilter ) {
+ QString fn( u.fileName() );
+ if ( fn.contains( "*" ) ) {
+ addFilter( fn );
+ d->currentFileName = QString::null;
+ d->url.setFileName( QString::null );
+ nameEdit->setText( QString::fromLatin1("") );
+ return FALSE;
+ }
+ }
+
+ if ( isDir ) {
+ if ( d->preview && d->preview->isVisible() ) {
+ if ( d->infoPreviewer )
+ d->infoPreviewer->previewUrl( u );
+ if ( d->contentsPreviewer )
+ d->contentsPreviewer->previewUrl( u );
+ }
+ }
+
+ QString old = d->currentFileName;
+
+ if ( isDirectoryMode( mode() ) ) {
+ if ( isDir )
+ d->currentFileName = u;
+ else
+ d->currentFileName = QString::null;
+ } else if ( !isDir && mode() == ExistingFiles ) {
+ d->currentFileName = u;
+ } else if ( !isDir || ( mode() == AnyFile && !isDir ) ) {
+ d->currentFileName = u;
+ } else {
+ d->currentFileName = QString::null;
+ }
+ if ( updatelined && !d->currentFileName.isEmpty() ) {
+ // If the selection is valid, or if its a directory, allow OK.
+ if ( !d->currentFileName.isNull() || isDir ) {
+ if ( u.fileName() != ".." ) {
+ QString fn = u.fileName();
+ nameEdit->setText( fn );
+ } else {
+ nameEdit->setText("");
+ }
+ } else
+ nameEdit->setText( QString::fromLatin1("") );
+ }
+
+ if ( !d->currentFileName.isNull() || isDir ) {
+ okB->setEnabled( TRUE );
+ } else if ( !isDirectoryMode( d->mode ) ) {
+ okB->setEnabled( FALSE );
+ }
+
+ if ( d->currentFileName.length() && old != d->currentFileName )
+ emit fileHighlighted( selectedFile() );
+
+ return !d->currentFileName.isNull();
+}
+
+
+/*! Make sure the minimum and maximum sizes of everything are sane.
+*/
+
+void QFileDialogP::updateGeometries()
+{
+ if ( !d || !d->geometryDirty )
+ return;
+
+ d->geometryDirty = FALSE;
+
+ QSize r, t;
+
+ // we really should have a QSize::unite()
+#define RM r.setWidth( QMAX(r.width(),t.width()) ); \
+r.setHeight( QMAX(r.height(),t.height()) )
+
+ // labels first
+ r = d->pathL->sizeHint();
+ t = d->fileL->sizeHint();
+ RM;
+ t = d->typeL->sizeHint();
+ RM;
+ d->pathL->setFixedSize( d->pathL->sizeHint() );
+ d->fileL->setFixedSize( r );
+ d->typeL->setFixedSize( r );
+
+ // single-line input areas
+ r = d->paths->sizeHint();
+ t = nameEdit->sizeHint();
+ RM;
+ t = d->types->sizeHint();
+ RM;
+ r.setWidth( t.width() * 2 / 3 );
+ t.setWidth( QWIDGETSIZE_MAX );
+ t.setHeight( r.height() );
+ d->paths->setMinimumSize( r );
+ d->paths->setMaximumSize( t );
+ nameEdit->setMinimumSize( r );
+ nameEdit->setMaximumSize( t );
+ d->types->setMinimumSize( r );
+ d->types->setMaximumSize( t );
+
+ // buttons on top row
+ r = QSize( 0, d->paths->minimumSize().height() );
+ t = QSize( 21, 20 );
+ RM;
+ if ( r.height()+1 > r.width() )
+ r.setWidth( r.height()+1 );
+ if ( d->goBack )
+ d->goBack->setFixedSize( r );
+ d->cdToParent->setFixedSize( r );
+ d->newFolder->setFixedSize( r );
+ d->mcView->setFixedSize( r );
+ d->detailView->setFixedSize( r );
+
+ QButton *b = 0;
+ if ( !d->toolButtons.isEmpty() ) {
+ for ( b = d->toolButtons.first(); b; b = d->toolButtons.next() )
+ b->setFixedSize( b->sizeHint().width(), r.height() );
+ }
+
+ if ( d->infoPreview ) {
+ d->previewInfo->show();
+ d->previewInfo->setFixedSize( r );
+ } else {
+ d->previewInfo->hide();
+ d->previewInfo->setFixedSize( QSize( 0, 0 ) );
+ }
+
+ if ( d->contentsPreview ) {
+ d->previewContents->show();
+ d->previewContents->setFixedSize( r );
+ } else {
+ d->previewContents->hide();
+ d->previewContents->setFixedSize( QSize( 0, 0 ) );
+ }
+
+ // open/save, cancel
+ r = QSize( 75, 20 );
+ t = okB->sizeHint();
+ RM;
+ t = cancelB->sizeHint();
+ RM;
+
+ okB->setFixedSize( r );
+ cancelB->setFixedSize( r );
+
+ d->topLevelLayout->activate();
+
+#undef RM
+}
+
+
+/*! Updates the file name edit box to \a newItem in the file dialog
+ when the cursor moves in the listview.
+*/
+
+void QFileDialogP::updateFileNameEdit( QListViewItem * newItem )
+{
+ if ( !newItem )
+ return;
+
+ if ( mode() == ExistingFiles ) {
+ detailViewSelectionChanged();
+ QUrl u = QUrl( d->url, QFileDialogPrivate::encodeFileName( ((QFileDialogPrivate::File*)files->currentItem())->info.name() ) );
+ QFileInfo fi( u.toString( FALSE, FALSE ) );
+ if ( !fi.isDir() )
+ emit fileHighlighted( u.toString( FALSE, FALSE ) );
+ } else if ( files->isSelected( newItem ) ) {
+ QFileDialogPrivate::File * i = (QFileDialogPrivate::File *)newItem;
+ if ( i && i->i && !i->i->isSelected() ) {
+ d->moreFiles->blockSignals( TRUE );
+ d->moreFiles->setSelected( i->i, TRUE );
+ d->moreFiles->blockSignals( FALSE );
+ }
+ // Encode the filename in case it had any special characters in it
+ QString encFile = QFileDialogPrivate::encodeFileName( newItem->text( 0 ) );
+ trySetSelection( i->info.isDir(), QUrlOperator( d->url, encFile ), TRUE );
+ }
+}
+
+void QFileDialogP::detailViewSelectionChanged()
+{
+ if ( d->mode != ExistingFiles )
+ return;
+
+ nameEdit->clear();
+ QString str;
+ QListViewItem * i = files->firstChild();
+ d->moreFiles->blockSignals( TRUE );
+ while( i ) {
+ if ( d->moreFiles && isVisible() ) {
+ if ( ( (QFileDialogPrivate::File *)i )->i->isSelected() != i->isSelected() )
+ d->moreFiles->setSelected( ( (QFileDialogPrivate::File *)i )->i, i->isSelected() );
+ }
+ if ( i->isSelected() && !( (QFileDialogPrivate::File *)i )->info.isDir() )
+ str += QString( "\"%1\" " ).arg( i->text( 0 ) );
+ i = i->nextSibling();
+ }
+ d->moreFiles->blockSignals( FALSE );
+ nameEdit->setText( str );
+ nameEdit->setCursorPosition( str.length() );
+ okB->setEnabled( TRUE );
+ if ( d->preview && d->preview->isVisible() && files->currentItem() ) {
+ QUrl u = QUrl( d->url, QFileDialogPrivate::encodeFileName( ((QFileDialogPrivate::File*)files->currentItem())->info.name() ) );
+ if ( d->infoPreviewer )
+ d->infoPreviewer->previewUrl( u );
+ if ( d->contentsPreviewer )
+ d->contentsPreviewer->previewUrl( u );
+ }
+}
+
+void QFileDialogP::listBoxSelectionChanged()
+{
+ if ( d->mode != ExistingFiles )
+ return;
+
+ if ( d->ignoreNextRefresh ) {
+ d->ignoreNextRefresh = FALSE;
+ return;
+ }
+
+ nameEdit->clear();
+ QString str;
+ QListBoxItem * i = d->moreFiles->item( 0 );
+ QListBoxItem * j = 0;
+ int index = 0;
+ files->blockSignals( TRUE );
+ while( i ) {
+ if ( files && isVisible() ) {
+ if ( ( (QFileDialogPrivate::MCItem *)i )->i->isSelected() != i->isSelected() )
+ files->setSelected( ( (QFileDialogPrivate::MCItem *)i )->i, i->isSelected() );
+ }
+ if ( d->moreFiles->isSelected( i )
+ && !( (QFileDialogPrivate::File*)( (QFileDialogPrivate::MCItem *)i )->i )->info.isDir() )
+ {
+ str += QString( "\"%1\" " ).arg( i->text() );
+ if ( j == 0 )
+ j = i;
+ }
+ i = d->moreFiles->item( ++index );
+ }
+ files->blockSignals( FALSE );
+ nameEdit->setText( str );
+ nameEdit->setCursorPosition( str.length() );
+ okB->setEnabled( TRUE );
+ if ( d->preview && d->preview->isVisible() && j ) {
+ QUrl u = QUrl( d->url,
+ QFileDialogPrivate::encodeFileName( ( (QFileDialogPrivate::File*)( (QFileDialogPrivate::MCItem*)j )->i )->info.name() ) );
+ if ( d->infoPreviewer )
+ d->infoPreviewer->previewUrl( u );
+ if ( d->contentsPreviewer )
+ d->contentsPreviewer->previewUrl( u );
+ }
+}
+
+/*! \overload */
+
+void QFileDialogP::updateFileNameEdit( QListBoxItem * newItem )
+{
+ if ( !newItem )
+ return;
+ QFileDialogPrivate::MCItem * i = (QFileDialogPrivate::MCItem *)newItem;
+ if ( d->mode != ExistingFiles && i->i ) {
+ i->i->listView()->setSelected( i->i, i->isSelected() );
+ updateFileNameEdit( i->i );
+ }
+}
+
+
+/*! Updates the dialog when the file name edit changes. */
+
+void QFileDialogP::fileNameEditDone()
+{
+ QUrlInfo f( d->url, nameEdit->text() );
+ if ( mode() != QFileDialogP::ExistingFiles ) {
+ QUrlOperator u( d->url, QFileDialogPrivate::encodeFileName( nameEdit->text() ) );
+ trySetSelection( f.isDir(), u, FALSE );
+ if ( d->preview && d->preview->isVisible() ) {
+ if ( d->infoPreviewer )
+ d->infoPreviewer->previewUrl( u );
+ if ( d->contentsPreviewer )
+ d->contentsPreviewer->previewUrl( u );
+ }
+ }
+}
+
+
+
+/*! This private slot reacts to double-clicks in the list view. The item that
+was double-clicked is specified in \a newItem */
+
+void QFileDialogP::selectDirectoryOrFile( QListViewItem * newItem )
+{
+
+ *workingDirectory = d->url;
+ detailViewMode = files->isVisible();
+ *lastSize = size();
+
+ if ( !newItem )
+ return;
+
+#if defined(Q_WS_WIN)
+ QFileInfo fi( d->url.path() + newItem->text(0) );
+ if ( fi.isSymLink() ) {
+ nameEdit->setText( fi.readLink() );
+ okClicked();
+ return;
+ }
+#endif
+
+ QFileDialogPrivate::File * i = (QFileDialogPrivate::File *)newItem;
+
+ QString oldName = nameEdit->text();
+ if ( i->info.isDir() ) {
+ setUrl( QUrlOperator( d->url, QFileDialogPrivate::encodeFileName( i->info.name() ) + "/" ) );
+ if ( isDirectoryMode( mode() ) ) {
+ QUrlInfo f ( d->url, QString::fromLatin1( "." ) );
+ trySetSelection( f.isDir(), d->url, TRUE );
+ }
+ } else if ( newItem->isSelectable() &&
+ trySetSelection( i->info.isDir(), QUrlOperator( d->url, QFileDialogPrivate::encodeFileName( i->info.name() ) ), TRUE ) ) {
+ if ( !isDirectoryMode( mode() ) ) {
+ emit fileSelected( selectedFile() );
+ accept();
+ }
+ } else if ( isDirectoryMode( d->mode ) ) {
+ d->currentFileName = d->url;
+ accept();
+ }
+ if ( !oldName.isEmpty() && !isDirectoryMode( mode() ) )
+ nameEdit->setText( oldName );
+}
+
+
+void QFileDialogP::selectDirectoryOrFile( QListBoxItem * newItem )
+{
+ if ( !newItem )
+ return;
+
+ QFileDialogPrivate::MCItem * i = (QFileDialogPrivate::MCItem *)newItem;
+ if ( i->i ) {
+ i->i->listView()->setSelected( i->i, i->isSelected() );
+ selectDirectoryOrFile( i->i );
+ }
+}
+
+
+void QFileDialogP::popupContextMenu( QListViewItem *item, const QPoint &p,
+ int )
+{
+ if ( item && d->mode == ExistingFiles )
+ return;
+ if ( item ) {
+ files->setCurrentItem( item );
+ files->setSelected( item, TRUE );
+ }
+
+ PopupAction action;
+ popupContextMenu( item ? item->text( 0 ) : QString::null, TRUE, action, p );
+
+ if ( action == PA_Open )
+ selectDirectoryOrFile( item );
+ else if ( action == PA_Rename )
+ files->startRename( FALSE );
+ else if ( action == PA_Delete )
+ deleteFile( item ? item->text( 0 ) : QString::null );
+ else if ( action == PA_Reload )
+ rereadDir();
+ else if ( action == PA_Hidden ) {
+ bShowHiddenFiles = !bShowHiddenFiles;
+ rereadDir();
+ } else if ( action == PA_SortName ) {
+ sortFilesBy = (int)QDir::Name;
+ sortAscending = TRUE;
+ resortDir();
+ } else if ( action == PA_SortSize ) {
+ sortFilesBy = (int)QDir::Size;
+ sortAscending = TRUE;
+ resortDir();
+ } else if ( action == PA_SortDate ) {
+ sortFilesBy = (int)QDir::Time;
+ sortAscending = TRUE;
+ resortDir();
+ } else if ( action == PA_SortUnsorted ) {
+ sortFilesBy = (int)QDir::Unsorted;
+ sortAscending = TRUE;
+ resortDir();
+ }
+
+}
+
+void QFileDialogP::popupContextMenu( QListBoxItem *item, const QPoint & p )
+{
+ if ( item && d->mode == ExistingFiles )
+ return;
+
+ PopupAction action;
+ popupContextMenu( item ? item->text() : QString::null, FALSE, action, p );
+
+ if ( action == PA_Open )
+ selectDirectoryOrFile( item );
+ else if ( action == PA_Rename )
+ d->moreFiles->startRename( FALSE );
+ else if ( action == PA_Delete )
+ deleteFile( item->text() );
+ else if ( action == PA_Reload )
+ rereadDir();
+ else if ( action == PA_Hidden ) {
+ bShowHiddenFiles = !bShowHiddenFiles;
+ rereadDir();
+ } else if ( action == PA_SortName ) {
+ sortFilesBy = (int)QDir::Name;
+ sortAscending = TRUE;
+ resortDir();
+ } else if ( action == PA_SortSize ) {
+ sortFilesBy = (int)QDir::Size;
+ sortAscending = TRUE;
+ resortDir();
+ } else if ( action == PA_SortDate ) {
+ sortFilesBy = (int)QDir::Time;
+ sortAscending = TRUE;
+ resortDir();
+ } else if ( action == PA_SortUnsorted ) {
+ sortFilesBy = (int)QDir::Unsorted;
+ sortAscending = TRUE;
+ resortDir();
+ }
+}
+
+void QFileDialogP::popupContextMenu( const QString &filename, bool,
+ PopupAction &action, const QPoint &p )
+{
+ action = PA_Cancel;
+
+ bool glob = filename.isEmpty();
+
+ QPopupMenu m( 0, "file dialog context menu" );
+ m.setCheckable( TRUE );
+
+ if ( !glob ) {
+ QString okt;
+ if ( QUrlInfo( d->url, filename ).isDir() ) {
+ okt = tr( "&Open" );
+ } else {
+ if ( mode() == AnyFile )
+ okt = tr( "&Save" );
+ else
+ okt = tr( "&Open" );
+ }
+ int ok = m.insertItem( okt );
+
+ m.insertSeparator();
+ int rename = m.insertItem( tr( "&Rename" ) );
+ int del = m.insertItem( tr( "&Delete" ) );
+
+ if ( filename.isEmpty() || !QUrlInfo( d->url, filename ).isWritable() ||
+ filename == ".." ) {
+ if ( filename.isEmpty() || !QUrlInfo( d->url, filename ).isReadable() )
+ m.setItemEnabled( ok, FALSE );
+ m.setItemEnabled( rename, FALSE );
+ m.setItemEnabled( del, FALSE );
+ }
+
+ if ( mode() == QFileDialogP::ExistingFiles )
+ m.setItemEnabled( rename, FALSE );
+
+ m.move( p );
+ int res = m.exec();
+
+ if ( res == ok )
+ action = PA_Open;
+ else if ( res == rename )
+ action = PA_Rename;
+ else if ( res == del )
+ action = PA_Delete;
+ } else {
+ int reload = m.insertItem( tr( "R&eload" ) );
+
+ QPopupMenu m2( 0, "sort menu" );
+
+ int sname = m2.insertItem( tr( "Sort by &Name" ) );
+ //int stype = m2.insertItem( tr( "Sort by &Type" ) );
+ int ssize = m2.insertItem( tr( "Sort by &Size" ) );
+ int sdate = m2.insertItem( tr( "Sort by &Date" ) );
+ m2.insertSeparator();
+ int sunsorted = m2.insertItem( tr( "&Unsorted" ) );
+
+ //m2.setItemEnabled( stype, FALSE );
+
+ if ( sortFilesBy == (int)QDir::Name )
+ m2.setItemChecked( sname, TRUE );
+ else if ( sortFilesBy == (int)QDir::Size )
+ m2.setItemChecked( ssize, TRUE );
+// else if ( sortFilesBy == 0x16 )
+// m2.setItemChecked( stype, TRUE );
+ else if ( sortFilesBy == (int)QDir::Time )
+ m2.setItemChecked( sdate, TRUE );
+ else if ( sortFilesBy == (int)QDir::Unsorted )
+ m2.setItemChecked( sunsorted, TRUE );
+
+ m.insertItem( tr( "Sort" ), &m2 );
+
+ m.insertSeparator();
+
+ int hidden = m.insertItem( tr( "Show &hidden files" ) );
+ m.setItemChecked( hidden, bShowHiddenFiles );
+
+ m.move( p );
+ int res = m.exec();
+
+ if ( res == reload )
+ action = PA_Reload;
+ else if ( res == hidden )
+ action = PA_Hidden;
+ else if ( res == sname )
+ action = PA_SortName;
+// else if ( res == stype )
+// action = PA_SortType;
+ else if ( res == sdate )
+ action = PA_SortDate;
+ else if ( res == ssize )
+ action = PA_SortSize;
+ else if ( res == sunsorted )
+ action = PA_SortUnsorted;
+ }
+
+}
+
+void QFileDialogP::deleteFile( const QString &filename )
+{
+ if ( filename.isEmpty() )
+ return;
+
+ QUrlInfo fi( d->url, QFileDialogPrivate::encodeFileName( filename ) );
+ QString t = tr( "the file" );
+ if ( fi.isDir() )
+ t = tr( "the directory" );
+ if ( fi.isSymLink() )
+ t = tr( "the symlink" );
+
+ if ( QMessageBox::warning( this,
+ tr( "Delete %1" ).arg( t ),
+ tr( "<qt>Are you sure you wish to delete %1 \"%2\"?</qt>" )
+ .arg( t ).arg(filename),
+ tr( "&Yes" ), tr( "&No" ), QString::null, 1 ) == 0 )
+ d->url.remove( QFileDialogPrivate::encodeFileName( filename ) );
+
+}
+
+void QFileDialogP::fileSelected( int )
+{
+ // unused
+}
+
+void QFileDialogP::fileHighlighted( int )
+{
+ // unused
+}
+
+void QFileDialogP::dirSelected( int )
+{
+ // unused
+}
+
+void QFileDialogP::pathSelected( int )
+{
+ // unused
+}
+
+
+void QFileDialogP::cdUpClicked()
+{
+ QString oldName = nameEdit->text();
+ setUrl( QUrlOperator( d->url, ".." ) );
+ if ( !oldName.isEmpty() )
+ nameEdit->setText( oldName );
+}
+
+void QFileDialogP::newFolderClicked()
+{
+ QString foldername( tr( "New Folder 1" ) );
+ int i = 0;
+ QStringList lst;
+ QListViewItemIterator it( files );
+ for ( ; it.current(); ++it )
+ if ( it.current()->text( 0 ).contains( tr( "New Folder" ) ) )
+ lst.append( it.current()->text( 0 ) );
+
+ if ( !lst.count() == 0 )
+ while ( lst.contains( foldername ) )
+ foldername = tr( "New Folder %1" ).arg( ++i );
+
+ d->url.mkdir( foldername );
+}
+
+void QFileDialogP::createdDirectory( const QUrlInfo &info, QNetworkOperation * )
+{
+ resortDir();
+ if ( d->moreFiles->isVisible() ) {
+ for ( uint i = 0; i < d->moreFiles->count(); ++i ) {
+ if ( d->moreFiles->text( i ) == info.name() ) {
+ d->moreFiles->setCurrentItem( i );
+ d->moreFiles->startRename( FALSE );
+ break;
+ }
+ }
+ } else {
+ QListViewItem *item = files->firstChild();
+ while ( item ) {
+ if ( item->text( 0 ) == info.name() ) {
+ files->setSelected( item, TRUE );
+ files->setCurrentItem( item );
+ files->startRename( FALSE );
+ break;
+ }
+ item = item->nextSibling();
+ }
+ }
+}
+
+
+/*!
+ This is a convenience static function that will return an existing directory
+ selected by the user.
+
+ \code
+ QString s = QFileDialogP::getExistingDirectory(
+ "/home",
+ this,
+ "get existing directory"
+ "Choose a directory",
+ TRUE );
+ \endcode
+
+ This function creates a modal file dialog called \a name, with
+ parent, \a parent. If parent is not 0, the dialog will be shown
+ centered over the parent.
+
+ The dialog's working directory is set to \a dir, and the caption is
+ set to \a caption. Either of these may be QString::null in which case
+ the current directory and a default caption will be used respectively.
+
+ If \a dirOnly is TRUE, then only directories will be shown in
+ the file dialog; otherwise both directories and files will be shown.
+
+ Under Unix/X11, the normal behavior of the file dialog is to resolve
+ and follow symlinks. For example, if /usr/tmp is a symlink to /var/tmp,
+ the file dialog will change to /var/tmp after entering /usr/tmp.
+ If \a resolveSymlinks is FALSE, the file dialog will treat
+ symlinks as regular directories.
+
+ \sa getOpenFileName(), getOpenFileNames(), getSaveFileName()
+*/
+
+QString QFileDialogP::getExistingDirectory( const QString & dir,
+ QWidget *parent,
+ const char* name,
+ const QString& caption,
+ bool dirOnly,
+ bool resolveSymlinks)
+{
+ bool save_qt_resolve_symlinks = qt_resolve_symlinks;
+ qt_resolve_symlinks = resolveSymlinks;
+
+ makeVariables();
+ QString wd;
+ if ( workingDirectory )
+ wd = *workingDirectory;
+
+#if defined(Q_WS_WIN)
+ QString initialDir;
+ if ( !dir.isEmpty() ) {
+ QUrlOperator u( dir );
+ if ( QFileInfo( u.path() ).isDir() )
+ initialDir = dir;
+ } else
+ initialDir = QString::null;
+ if ( qApp->style().styleHint( QStyle::SH_GUIStyle ) == WindowsStyle && dirOnly )
+ return winGetExistingDirectory( initialDir, parent, name, caption );
+#endif
+#if defined(Q_WS_MAC)
+ if( ( qApp->style().inherits(QMAC_DEFAULT_STYLE) ) )
+ return macGetOpenFileNames("", 0,
+ parent, name, caption, FALSE, TRUE).first();
+#endif
+
+ QFileDialogP *dialog = new QFileDialogP( parent, name ? name : "qt_filedlg_ged", TRUE );
+#ifndef QT_NO_WIDGET_TOPEXTRA
+ if ( !caption.isNull() )
+ dialog->setCaption( caption );
+ else
+ dialog->setCaption( QFileDialogP::tr("Find Directory") );
+#endif
+
+ dialog->setMode( dirOnly ? DirectoryOnly : Directory );
+
+ dialog->d->types->clear();
+ dialog->d->types->insertItem( QFileDialogP::tr("Directories") );
+ dialog->d->types->setEnabled( FALSE );
+
+ QString dir_( dir );
+ dir_ = dir_.simplifyWhiteSpace();
+ if ( dir_.isEmpty() && !wd.isEmpty() )
+ dir_ = wd;
+ QUrlOperator u( dir_ );
+ if ( u.isLocalFile() ) {
+ if ( !dir_.isEmpty() ) {
+ QFileInfo f( u.path() );
+ if ( f.exists() )
+ if ( f.isDir() ) {
+ dialog->setDir( dir_ );
+ wd = dir_;
+ }
+ } else if ( !wd.isEmpty() ) {
+ QUrl tempUrl( wd );
+ QFileInfo f( tempUrl.path() );
+ if ( f.isDir() ) {
+ dialog->setDir( wd );
+ }
+ } else {
+ QString theDir = dir_;
+ if ( theDir.isEmpty() ) {
+ theDir = QDir::currentDirPath();
+ } if ( !theDir.isEmpty() ) {
+ QUrl tempUrl( theDir );
+ QFileInfo f( tempUrl.path() );
+ if ( f.isDir() ) {
+ wd = theDir;
+ dialog->setDir( theDir );
+ }
+ }
+ }
+ } else {
+ dialog->setUrl( dir_ );
+ }
+
+ QString result;
+ dialog->setSelection( dialog->d->url.toString() );
+
+ if ( dialog->exec() == QDialog::Accepted ) {
+ result = dialog->selectedFile();
+ wd = result;
+ }
+ delete dialog;
+
+ if ( !result.isEmpty() && result.right( 1 ) != "/" )
+ result += "/";
+
+ qt_resolve_symlinks = save_qt_resolve_symlinks;
+
+ return result;
+}
+
+
+/*!
+ \property QFileDialogP::mode
+ \brief the file dialog's mode
+
+ The default mode is \c ExistingFile.
+*/
+
+void QFileDialogP::setMode( Mode newMode )
+{
+ if ( d->mode != newMode ) {
+ d->mode = newMode;
+ QString sel = d->currentFileName;
+ if ( isDirectoryMode( newMode ) ) {
+ files->setMultiSelection( FALSE );
+ d->moreFiles->setMultiSelection( FALSE );
+ if ( sel.isNull() )
+ sel = QString::fromLatin1(".");
+ d->types->setEnabled( FALSE );
+ } else if ( newMode == ExistingFiles ) {
+ files->setSelectionMode( QListView::Extended );
+ d->moreFiles->setSelectionMode( QListBox::Extended );
+ d->types->setEnabled( TRUE );
+ } else {
+ files->setMultiSelection( FALSE );
+ d->moreFiles->setMultiSelection( FALSE );
+ d->types->setEnabled( TRUE );
+ }
+ rereadDir();
+ QUrlInfo f( d->url, "." );
+ trySetSelection( f.isDir(), d->url, FALSE );
+ }
+
+ QString okt;
+ bool changeFilters = FALSE;
+ if ( mode() == AnyFile ) {
+ okt = tr("Save");
+ d->fileL->setText( tr("File &name:") );
+ if ( d->types->count() == 1 ) {
+ d->types->setCurrentItem( 0 );
+ if ( d->types->currentText() == "Directories" ) {
+ changeFilters = TRUE;
+ }
+ }
+ }
+ else if ( mode() == Directory || mode() == DirectoryOnly ) {
+ okt = tr("OK");
+ d->fileL->setText( tr("Directory:") );
+ d->types->clear();
+ d->types->insertItem( tr("Directories") );
+ }
+ else {
+ okt = tr("Open");
+ d->fileL->setText( tr("File &name:") );
+ if ( d->types->count() == 1 ) {
+ d->types->setCurrentItem( 0 );
+ if ( d->types->currentText() == "Directories" ) {
+ changeFilters = TRUE;
+ }
+ }
+ }
+
+ if ( changeFilters ) {
+ d->types->clear();
+ d->types->insertItem( tr("All Files (*)") );
+ }
+
+ okB->setText( okt );
+}
+
+QFileDialogP::Mode QFileDialogP::mode() const
+{
+ return d->mode;
+}
+
+/*! \reimp
+*/
+
+void QFileDialogP::done( int i )
+{
+ if ( i == QDialog::Accepted && (d->mode == ExistingFile || d->mode == ExistingFiles) ) {
+ QStringList selection = selectedFiles();
+ for ( uint f = 0; f < selection.count(); f++ ) {
+ QString file = selection[f];
+ if ( file.isNull() )
+ continue;
+ if ( d->url.isLocalFile() && !QFile::exists( file ) ) {
+ QMessageBox::information( this, tr("Error"), tr("%1\nFile not found.\nCheck path and filename.").arg( file ) );
+ return;
+ }
+ }
+ }
+ QDialog::done( i );
+}
+
+/*!
+ \property QFileDialogP::viewMode
+
+ \brief the file dialog's view mode
+
+ If you set the view mode to be \e Detail (the default), then you
+ will see the file's details, such as the size of the file and the
+ date the file was last modified in addition to the file's name.
+
+ If you set the view mode to be \e List, then you will just
+ see a list of the files and folders.
+
+ See \l QFileDialogP::ViewMode
+*/
+
+
+QFileDialogP::ViewMode QFileDialogP::viewMode() const
+{
+ if ( detailViewMode )
+ return Detail;
+ else
+ return List;
+}
+
+void QFileDialogP::setViewMode( ViewMode m )
+{
+ if ( m == Detail ) {
+ detailViewMode = TRUE;
+ d->stack->raiseWidget( files );
+ d->detailView->setOn( TRUE );
+ d->mcView->setOn( FALSE );
+ } else if ( m == List ) {
+ detailViewMode = FALSE;
+ d->stack->raiseWidget( d->moreFiles );
+ d->detailView->setOn( FALSE );
+ d->mcView->setOn( TRUE );
+ }
+}
+
+
+/*!
+ \property QFileDialogP::previewMode
+
+ \brief the preview mode for the file dialog
+
+ If you set the mode to be a mode other than \e NoPreview, you must
+ use setInfoPreview() or setContentsPreview() to set the dialog's
+ preview widget to your preview widget and enable the preview
+ widget(s) with setInfoPreviewEnabled() or
+ setContentsPreviewEnabled().
+
+ \sa infoPreview, contentsPreview, viewMode
+*/
+
+void QFileDialogP::setPreviewMode( PreviewMode m )
+{
+ if ( m == NoPreview ) {
+ d->previewInfo->setOn( FALSE );
+ d->previewContents->setOn( FALSE );
+ } else if ( m == Info && d->infoPreview ) {
+ d->previewInfo->setOn( TRUE );
+ d->previewContents->setOn( FALSE );
+ changeMode( d->modeButtons->id( d->previewInfo ) );
+ } else if ( m == Contents && d->contentsPreview ) {
+ d->previewInfo->setOn( FALSE );
+ d->previewContents->setOn( TRUE );
+ changeMode( d->modeButtons->id( d->previewContents ) );
+ }
+}
+QFileDialogP::PreviewMode QFileDialogP::previewMode() const
+{
+ if ( d->infoPreview && d->previewInfo->isVisible() )
+ return Info;
+ else if ( d->contentsPreview && d->previewContents->isVisible() )
+ return Contents;
+
+ return NoPreview;
+}
+
+
+/*!
+ Adds the specified widgets to the bottom of the file dialog. The
+ label \a l is placed underneath the "file name" and the "file types"
+ labels. The widget \a w is placed underneath the file types combobox.
+ The button \a b is placed underneath the Cancel pushbutton.
+
+ \code
+ MyFileDialog::MyFileDialog( QWidget* parent, const char* name ) :
+ QFileDialogP( parent, name )
+ {
+ QLabel* label = new QLabel( "Added widgets", this );
+ QLineEdit* lineedit = new QLineEdit( this );
+ QToolButton* toolbutton = new QToolButton( this );
+
+ addWidgets( label, lineedit, toolbutton );
+ }
+ \endcode
+
+ If you don't want to have one of the widgets added, pass 0 in that
+ widget's position.
+
+ Every time you call this function, a new row of widgets will be added
+ to the bottom of the file dialog.
+
+ \sa addToolButton(), addLeftWidget(), addRightWidget()
+*/
+
+void QFileDialogP::addWidgets( QLabel * l, QWidget * w, QPushButton * b )
+{
+ if ( !l && !w && !b )
+ return;
+
+ d->geometryDirty = TRUE;
+
+ QHBoxLayout *lay = new QHBoxLayout();
+ d->extraWidgetsLayouts.append( lay );
+ d->topLevelLayout->addLayout( lay );
+
+ if ( !l )
+ l = new QLabel( this, "qt_intern_lbl" );
+ d->extraLabels.append( l );
+ lay->addWidget( l );
+
+ if ( !w )
+ w = new QWidget( this, "qt_intern_widget" );
+ d->extraWidgets.append( w );
+ lay->addWidget( w );
+ lay->addSpacing( 15 );
+
+ if ( b ) {
+ d->extraButtons.append( b );
+ lay->addWidget( b );
+ } else {
+ QWidget *wid = new QWidget( this, "qt_extrabuttons_widget" );
+ d->extraButtons.append( wid );
+ lay->addWidget( wid );
+ }
+
+ updateGeometries();
+}
+
+/*!
+ Adds the tool button \a b to the row of tool buttons at the top of the
+ file dialog. The button is appended to the right of
+ this row. If \a separator is TRUE, a small space is inserted between the
+ last button of the row and the new button \a b.
+
+ \sa addWidgets(), addLeftWidget(), addRightWidget()
+*/
+
+void QFileDialogP::addToolButton( QButton *b, bool separator )
+{
+ if ( !b || !d->buttonLayout )
+ return;
+
+ d->geometryDirty = TRUE;
+
+ d->toolButtons.append( b );
+ if ( separator )
+ d->buttonLayout->addSpacing( 8 );
+ d->buttonLayout->addWidget( b );
+
+ updateGeometries();
+}
+
+/*!
+ Adds the widget \a w to the left-hand side of the file dialog.
+
+ \sa addRightWidget(), addWidgets(), addToolButton()
+*/
+
+void QFileDialogP::addLeftWidget( QWidget *w )
+{
+ if ( !w )
+ return;
+ d->geometryDirty = TRUE;
+
+ d->leftLayout->addWidget( w );
+ d->leftLayout->addSpacing( 5 );
+
+ updateGeometries();
+}
+
+/*!
+ Adds the widget \a w to the right-hand side of the file dialog.
+
+ \sa addLeftWidget(), addWidgets(), addToolButton()
+*/
+
+void QFileDialogP::addRightWidget( QWidget *w )
+{
+ if ( !w )
+ return;
+ d->geometryDirty = TRUE;
+
+ d->rightLayout->addSpacing( 5 );
+ d->rightLayout->addWidget( w );
+
+ updateGeometries();
+}
+
+/*! \reimp */
+
+void QFileDialogP::keyPressEvent( QKeyEvent * ke )
+{
+ if ( !d->ignoreNextKeyPress &&
+ ke && ( ke->key() == Key_Enter ||
+ ke->key() == Key_Return ) ) {
+ ke->ignore();
+ if ( d->paths->hasFocus() ) {
+ ke->accept();
+ if ( d->url == QUrl(d->paths->currentText()) )
+ nameEdit->setFocus();
+ } else if ( d->types->hasFocus() ) {
+ ke->accept();
+ // ### is there a suitable condition for this? only valid
+ // wildcards?
+ nameEdit->setFocus();
+ } else if ( nameEdit->hasFocus() ) {
+ if ( d->currentFileName.isNull() ) {
+ // maybe change directory
+ QUrlInfo i( d->url, nameEdit->text() );
+ if ( i.isDir() ) {
+ nameEdit->setText( QString::fromLatin1("") );
+ setDir( QUrlOperator( d->url, QFileDialogPrivate::encodeFileName(i.name()) ) );
+ }
+ ke->accept();
+ } else if ( mode() == ExistingFiles ) {
+ QUrlInfo i( d->url, nameEdit->text() );
+ if ( i.isFile() ) {
+ QListViewItem * i = files->firstChild();
+ while ( i && nameEdit->text() != i->text( 0 ) )
+ i = i->nextSibling();
+ if ( i )
+ files->setSelected( i, TRUE );
+ else
+ ke->accept(); // strangely, means to ignore that event
+ }
+ }
+ } else if ( files->hasFocus() || d->moreFiles->hasFocus() ) {
+ ke->accept();
+ }
+ } else if ( ke->key() == Key_Escape ) {
+ ke->ignore();
+ }
+
+ d->ignoreNextKeyPress = FALSE;
+
+ if ( !ke->isAccepted() ) {
+ QDialog::keyPressEvent( ke );
+ }
+}
+
+
+/*! \class QFileIconProviderP qfiledialog.h
+
+ \brief The QFileIconProviderP class provides icons for QFileDialogP to
+ use.
+
+ \ingroup misc
+
+ By default QFileIconProviderP is not used, but any application or
+ library can subclass it, reimplement pixmap() to return a suitable
+ icon, and make all QFileDialogP objects use it by calling the static
+ function QFileDialogP::setIconProvider().
+
+ It is advisable to make all the icons that QFileIconProviderP returns be
+ the same size or at least the same width. This makes the list view
+ look much better.
+
+ \sa QFileDialogP
+*/
+
+
+/*! Constructs an empty file icon provider called \a name, with the
+ parent \a parent.
+*/
+
+QFileIconProviderP::QFileIconProviderP( QObject * parent, const char* name )
+ : QObject( parent, name )
+{
+ // nothing necessary
+}
+
+
+/*!
+ Returns a pointer to a pixmap that should be used to
+ signify the file with the information \a info.
+
+ If pixmap() returns 0, QFileDialogP draws the default pixmap.
+
+ The default implementation returns particular icons for files, directories,
+ link-files and link-directories. It returns a blank "icon" for other types.
+
+ If you return a pixmap here, it should measure 16x16 pixels.
+*/
+
+const QPixmap * QFileIconProviderP::pixmap( const QFileInfo & info )
+{
+ if ( info.isSymLink() ) {
+ if ( info.isFile() )
+ return symLinkFileIcon;
+ else
+ return symLinkDirIcon;
+ } else if ( info.isDir() ) {
+ return closedFolderIcon;
+ } else if ( info.isFile() ) {
+ return fileIcon;
+ } else {
+ return fifteenTransparentPixels;
+ }
+}
+
+/*!
+ Sets the QFileIconProviderP used by the file dialog to \a provider.
+
+ The default is that there is no QFileIconProviderP and QFileDialogP
+ just draws a folder icon next to each directory and nothing next
+ to files.
+
+ \sa QFileIconProviderP, iconProvider()
+*/
+
+void QFileDialogP::setIconProvider( QFileIconProviderP * provider )
+{
+ fileIconProvider = provider;
+}
+
+
+/*!
+ Returns a pointer to the icon provider currently set on the file dialog.
+ By default there is no icon provider, and this function returns 0.
+
+ \sa setIconProvider(), QFileIconProviderP
+*/
+
+QFileIconProviderP * QFileDialogP::iconProvider()
+{
+ return fileIconProvider;
+}
+
+
+#if defined(Q_WS_WIN)
+
+static QString getWindowsRegString( HKEY key, const char *subKey )
+{
+ QString s;
+ char buf[512];
+ DWORD bsz = sizeof(buf);
+#ifdef Q_OS_TEMP
+ int r = RegQueryValueEx( key, (LPCTSTR)qt_winTchar(subKey, TRUE), 0, 0, (LPBYTE)buf, &bsz );
+#else
+ int r = RegQueryValueExA( key, subKey, 0, 0, (LPBYTE)buf, &bsz );
+#endif
+ if ( r == ERROR_SUCCESS ) {
+ s = buf;
+ } else if ( r == ERROR_MORE_DATA ) {
+ char *ptr = new char[bsz+1];
+#ifdef Q_OS_TEMP
+ r = RegQueryValueEx( key, (LPCTSTR)qt_winTchar(subKey, TRUE), 0, 0, (LPBYTE)ptr, &bsz );
+#else
+ r = RegQueryValueExA( key, subKey, 0, 0, (LPBYTE)ptr, &bsz );
+#endif
+ if ( r == ERROR_SUCCESS )
+ s = ptr;
+ delete [] ptr;
+ }
+ return s;
+}
+
+static void initPixmap( QPixmap &pm )
+{
+ pm.fill( Qt::white );
+}
+
+QWindowsIconProvider::QWindowsIconProvider( QObject *parent, const char *name )
+ : QFileIconProviderP( parent, name )
+{
+ pixw = GetSystemMetrics( SM_CXSMICON );
+ pixh = GetSystemMetrics( SM_CYSMICON );
+
+ HKEY k;
+ HICON si;
+ int r;
+ QString s;
+ UINT res;
+
+#ifdef Q_OS_TEMP
+ // ---------- get default folder pixmap
+ r = RegOpenKeyEx( HKEY_CLASSES_ROOT,
+ L"folder\\DefaultIcon",
+ 0, KEY_READ, &k );
+#else
+ // ---------- get default folder pixmap
+ r = RegOpenKeyExA( HKEY_CLASSES_ROOT,
+ "folder\\DefaultIcon",
+ 0, KEY_READ, &k );
+#endif
+ if ( r == ERROR_SUCCESS ) {
+ s = getWindowsRegString( k, 0 );
+ RegCloseKey( k );
+
+ QStringList lst = QStringList::split( ",", s );
+
+#ifdef Q_OS_TEMP
+ res = (UINT)ExtractIconEx( (LPCTSTR)qt_winTchar( lst[ 0 ].simplifyWhiteSpace(), TRUE ),
+ lst[ 1 ].simplifyWhiteSpace().toInt(),
+ 0, &si, 1 );
+#else
+ res = ExtractIconExA( lst[ 0 ].simplifyWhiteSpace().latin1(),
+ lst[ 1 ].simplifyWhiteSpace().toInt(),
+ 0, &si, 1 );
+#endif
+
+ if ( res ) {
+ defaultFolder.resize( pixw, pixh );
+ initPixmap( defaultFolder );
+ QPainter p( &defaultFolder );
+ DrawIconEx( p.handle(), 0, 0, si, pixw, pixh, 0, NULL, DI_NORMAL );
+ p.end();
+ defaultFolder.setMask( defaultFolder.createHeuristicMask() );
+ *closedFolderIcon = defaultFolder;
+ DestroyIcon( si );
+ } else {
+ defaultFolder = *closedFolderIcon;
+ }
+ } else {
+ RegCloseKey( k );
+ }
+
+#ifdef Q_OS_TEMP
+ //------------------------------- get default file pixmap
+ res = (UINT)ExtractIconEx( L"shell32.dll",
+ 0, 0, &si, 1 );
+#else
+ //------------------------------- get default file pixmap
+ res = ExtractIconExA( "shell32.dll",
+ 0, 0, &si, 1 );
+#endif
+
+ if ( res ) {
+ defaultFile.resize( pixw, pixh );
+ initPixmap( defaultFile );
+ QPainter p( &defaultFile );
+ DrawIconEx( p.handle(), 0, 0, si, pixw, pixh, 0, NULL, DI_NORMAL );
+ p.end();
+ defaultFile.setMask( defaultFile.createHeuristicMask() );
+ *fileIcon = defaultFile;
+ DestroyIcon( si );
+ } else {
+ defaultFile = *fileIcon;
+ }
+
+#ifdef Q_OS_TEMP
+ //------------------------------- get default exe pixmap
+ res = (UINT)ExtractIconEx( L"shell32.dll",
+ 2, 0, &si, 1 );
+#else
+ //------------------------------- get default exe pixmap
+ res = ExtractIconExA( "shell32.dll",
+ 2, 0, &si, 1 );
+#endif
+
+ if ( res ) {
+ defaultExe.resize( pixw, pixh );
+ initPixmap( defaultExe );
+ QPainter p( &defaultExe );
+ DrawIconEx( p.handle(), 0, 0, si, pixw, pixh, 0, NULL, DI_NORMAL );
+ p.end();
+ defaultExe.setMask( defaultExe.createHeuristicMask() );
+ DestroyIcon( si );
+ } else {
+ defaultExe = *fileIcon;
+ }
+}
+
+QWindowsIconProvider::~QWindowsIconProvider()
+{
+ if ( this == fileIconProvider )
+ fileIconProvider = 0;
+}
+
+const QPixmap * QWindowsIconProvider::pixmap( const QFileInfo &fi )
+{
+ QString ext = fi.extension().upper();
+ QString key = ext;
+ ext.prepend( "." );
+ QMap< QString, QPixmap >::Iterator it;
+
+ if ( fi.isDir() ) {
+ return &defaultFolder;
+ } else if ( ext.lower() != ".exe" ) {
+ it = cache.find( key );
+ if ( it != cache.end() )
+ return &( *it );
+
+ HKEY k, k2;
+#ifdef Q_OS_TEMP
+ int r = RegOpenKeyEx( HKEY_CLASSES_ROOT,
+ (LPCTSTR)qt_winTchar(ext, TRUE),
+ 0, KEY_READ, &k );
+#else
+ int r = RegOpenKeyExA( HKEY_CLASSES_ROOT,
+ ext.latin1(),
+ 0, KEY_READ, &k );
+#endif
+ QString s;
+ if ( r == ERROR_SUCCESS ) {
+ s = getWindowsRegString( k, 0 );
+ } else {
+ cache[ key ] = defaultFile;
+ RegCloseKey( k );
+ return &defaultFile;
+ }
+ RegCloseKey( k );
+
+#ifdef Q_OS_TEMP
+ r = RegOpenKeyEx( HKEY_CLASSES_ROOT,
+ (LPCTSTR)qt_winTchar( s + "\\DefaultIcon", TRUE ),
+ 0, KEY_READ, &k2 );
+#else
+ r = RegOpenKeyExA( HKEY_CLASSES_ROOT,
+ QString( s + "\\DefaultIcon" ).latin1() ,
+ 0, KEY_READ, &k2 );
+#endif
+ if ( r == ERROR_SUCCESS ) {
+ s = getWindowsRegString( k2, 0 );
+ } else {
+ cache[ key ] = defaultFile;
+ RegCloseKey( k2 );
+ return &defaultFile;
+ }
+ RegCloseKey( k2 );
+
+ QStringList lst = QStringList::split( ",", s );
+
+ HICON si;
+ UINT res;
+ QString filepath = lst[ 0 ].stripWhiteSpace();
+ if ( filepath.find("%1") != -1 ) {
+ filepath = filepath.arg( fi.filePath() );
+ if ( ext.lower() == ".dll" ) {
+ pix = defaultFile;
+ return &pix;
+ }
+ }
+
+#ifdef Q_OS_TEMP
+ res = (UINT)ExtractIconEx( (LPCTSTR)qt_winTchar(filepath, TRUE),
+ lst[ 1 ].stripWhiteSpace().toInt(),
+ NULL, &si, 1 );
+#else
+ res = ExtractIconExA( filepath.latin1(),
+ lst[ 1 ].stripWhiteSpace().toInt(),
+ NULL, &si, 1 );
+#endif
+
+ if ( res ) {
+ pix.resize( pixw, pixh );
+ initPixmap( pix );
+ QPainter p( &pix );
+ DrawIconEx( p.handle(), 0, 0, si, pixw, pixh, 0, NULL, DI_NORMAL );
+ p.end();
+ pix.setMask( pix.createHeuristicMask() );
+ DestroyIcon( si );
+ } else {
+ pix = defaultFile;
+ }
+
+ cache[ key ] = pix;
+ return &pix;
+ } else {
+ HICON si;
+ UINT res;
+#ifdef Q_OS_TEMP
+ res = (UINT)ExtractIconEx( (LPCTSTR)qt_winTchar(fi.absFilePath(), TRUE),
+ -1,
+ 0, 0, 1 );
+#else
+ res = ExtractIconExA( fi.absFilePath().latin1(),
+ -1,
+ 0, 0, 1 );
+#endif
+
+ if ( res == 0 ) {
+ return &defaultExe;
+ } else {
+#ifdef Q_OS_TEMP
+ res = (UINT)ExtractIconEx( (LPCTSTR)qt_winTchar(fi.absFilePath(), TRUE),
+ res - 1,
+ 0, &si, 1 );
+#else
+ res = ExtractIconExA( fi.absFilePath().latin1(),
+ res - 1,
+ 0, &si, 1 );
+#endif
+ }
+
+ if ( res ) {
+ pix.resize( pixw, pixh );
+ initPixmap( pix );
+ QPainter p( &pix );
+ DrawIconEx( p.handle(), 0, 0, si, pixw, pixh, 0, NULL, DI_NORMAL );
+ p.end();
+ pix.setMask( pix.createHeuristicMask() );
+ DestroyIcon( si );
+ } else {
+ pix = defaultExe;
+ }
+
+ return &pix;
+ }
+
+ // can't happen!
+ return 0;
+}
+#endif
+
+
+
+/*!
+ \reimp
+*/
+bool QFileDialogP::eventFilter( QObject * o, QEvent * e )
+{
+ if ( e->type() == QEvent::KeyPress && ( (QKeyEvent*)e )->key() == Key_F5 ) {
+ rereadDir();
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress && ( (QKeyEvent*)e )->key() == Key_F2 &&
+ ( o == files || o == files->viewport() ) ) {
+ if ( files->isVisible() && files->currentItem() ) {
+ if ( mode() != QFileDialogP::ExistingFiles &&
+ QUrlInfo( d->url, "." ).isWritable() && files->currentItem()->text( 0 ) != ".." ) {
+ files->renameItem = files->currentItem();
+ files->startRename( TRUE );
+ }
+ }
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress && ( (QKeyEvent*)e )->key() == Key_F2 &&
+ ( o == d->moreFiles || o == d->moreFiles->viewport() ) ) {
+ if ( d->moreFiles->isVisible() && d->moreFiles->currentItem() != -1 ) {
+ if ( mode() != QFileDialogP::ExistingFiles &&
+ QUrlInfo( d->url, "." ).isWritable() &&
+ d->moreFiles->item( d->moreFiles->currentItem() )->text() != ".." ) {
+ d->moreFiles->renameItem = d->moreFiles->item( d->moreFiles->currentItem() );
+ d->moreFiles->startRename( TRUE );
+ }
+ }
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress && d->moreFiles->renaming ) {
+ d->moreFiles->lined->setFocus();
+ QApplication::sendEvent( d->moreFiles->lined, e );
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress && files->renaming ) {
+ files->lined->setFocus();
+ QApplication::sendEvent( files->lined, e );
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress &&
+ ((QKeyEvent *)e)->key() == Key_Backspace &&
+ ( o == files ||
+ o == d->moreFiles ||
+ o == files->viewport() ||
+ o == d->moreFiles->viewport() ) ) {
+ cdUpClicked();
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress &&
+ ((QKeyEvent *)e)->key() == Key_Delete &&
+ ( o == files ||
+ o == files->viewport() ) ) {
+ if ( files->currentItem() )
+ deleteFile( files->currentItem()->text( 0 ) );
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( e->type() == QEvent::KeyPress &&
+ ((QKeyEvent *)e)->key() == Key_Delete &&
+ ( o == d->moreFiles ||
+ o == d->moreFiles->viewport() ) ) {
+ int c = d->moreFiles->currentItem();
+ if ( c >= 0 )
+ deleteFile( d->moreFiles->item( c )->text() );
+ ((QKeyEvent *)e)->accept();
+ return TRUE;
+ } else if ( o == files && e->type() == QEvent::FocusOut &&
+ files->currentItem() && mode() != ExistingFiles ) {
+ } else if ( o == files && e->type() == QEvent::KeyPress ) {
+ QTimer::singleShot( 0, this, SLOT(fixupNameEdit()) );
+ } else if ( o == nameEdit && e->type() == QEvent::KeyPress ) {
+ if ( ( nameEdit->cursorPosition() == (int)nameEdit->text().length() || nameEdit->hasSelectedText() ) &&
+ isprint(((QKeyEvent *)e)->ascii()) ) {
+#if defined(_WS_WIN_)
+ QString nt( nameEdit->text().lower() );
+#else
+ QString nt( nameEdit->text() );
+#endif
+ nt.truncate( nameEdit->cursorPosition() );
+ nt += (char)(((QKeyEvent *)e)->ascii());
+ QListViewItem * i = files->firstChild();
+#if defined(_WS_WIN_)
+ while( i && i->text( 0 ).left(nt.length()).lower() != nt )
+#else
+ while( i && i->text( 0 ).left(nt.length()) != nt )
+#endif
+ i = i->nextSibling();
+ if ( i ) {
+ nt = i->text( 0 );
+ int cp = nameEdit->cursorPosition()+1;
+ nameEdit->validateAndSet( nt, cp, cp, nt.length() );
+ return TRUE;
+ }
+ }
+ } else if ( o == nameEdit && e->type() == QEvent::FocusIn ) {
+ fileNameEditDone();
+ } else if ( d->moreFiles->renaming && o != d->moreFiles->lined && e->type() == QEvent::FocusIn ) {
+ d->moreFiles->lined->setFocus();
+ return TRUE;
+ } else if ( files->renaming && o != files->lined && e->type() == QEvent::FocusIn ) {
+ files->lined->setFocus();
+ return TRUE;
+ } else if ( ( o == d->moreFiles || o == d->moreFiles->viewport() ) &&
+ e->type() == QEvent::FocusIn ) {
+ if ( o == d->moreFiles->viewport() && !d->moreFiles->viewport()->hasFocus() ||
+ o == d->moreFiles && !d->moreFiles->hasFocus() )
+ ((QWidget*)o)->setFocus();
+ return FALSE;
+ }
+
+ return QDialog::eventFilter( o, e );
+}
+
+/*!
+ Sets the filters used in the file dialog to \a filters. Each group
+ of filters must be separated by \c{;;} (\e two semi-colons).
+
+ \code
+ QString types("*.png;;*.xpm;;*.jpg");
+ QFileDialogP fd = new QFileDialogP( this );
+ fd->setFilters( types );
+ fd->show();
+ \endcode
+
+*/
+
+void QFileDialogP::setFilters( const QString &filters )
+{
+ QStringList lst = makeFiltersList( filters );
+ setFilters( lst );
+}
+
+/*!
+ \overload
+
+ \a types must be a null-terminated list of strings.
+
+*/
+
+void QFileDialogP::setFilters( const char ** types )
+{
+ if ( !types || !*types )
+ return;
+
+ d->types->clear();
+ while( types && *types ) {
+ d->types->insertItem( QString::fromLatin1(*types) );
+ types++;
+ }
+ d->types->setCurrentItem( 0 );
+ setFilter( d->types->text( 0 ) );
+}
+
+
+/*! \overload void QFileDialogP::setFilters( const QStringList & )
+*/
+
+void QFileDialogP::setFilters( const QStringList & types )
+{
+ if ( types.count() < 1 )
+ return;
+
+ d->types->clear();
+ for ( QStringList::ConstIterator it = types.begin(); it != types.end(); ++it )
+ d->types->insertItem( *it );
+ d->types->setCurrentItem( 0 );
+ setFilter( d->types->text( 0 ) );
+}
+
+/*!
+ Adds the filter \a filter to the list of filters and makes it the
+ current filter.
+
+ \code
+ QFileDialogP* fd = new QFileDialogP( this );
+ fd->addFilter( "Images (*.png *.jpg *.xpm)" );
+ fd->show();
+ \endcode
+
+ In the above example, a file dialog is created, and the file filter "Images
+ (*.png *.jpg *.xpm)" is added and is set as the current filter. The original
+ filter, "All Files (*)", is still available.
+
+ \sa setFilter(), setFilters()
+*/
+
+void QFileDialogP::addFilter( const QString &filter )
+{
+ if ( filter.isEmpty() )
+ return;
+ QString f = filter;
+ QRegExp r( QString::fromLatin1(qt_file_dialog_filter_reg_exp) );
+ int index = r.search( f );
+ if ( index >= 0 )
+ f = r.cap( 2 );
+ for ( int i = 0; i < d->types->count(); ++i ) {
+ QString f2( d->types->text( i ) );
+ int index = r.search( f2 );
+ if ( index >= 0 )
+ f2 = r.cap( 1 );
+ if ( f2 == f ) {
+ d->types->setCurrentItem( i );
+ setFilter( f2 );
+ return;
+ }
+ }
+
+ d->types->insertItem( filter );
+ d->types->setCurrentItem( d->types->count() - 1 );
+ setFilter( d->types->text( d->types->count() - 1 ) );
+}
+
+/*!
+ Since modeButtons is a top-level widget, it may be destroyed by the
+ kernel at application exit. Notice if this happens to
+ avoid double deletion.
+*/
+
+void QFileDialogP::modeButtonsDestroyed()
+{
+ if ( d )
+ d->modeButtons = 0;
+}
+
+
+/*!
+ This is a convenience static function that will return one or more
+ existing files selected by the user.
+
+ \code
+ QStringList files = QFileDialogP::getOpenFileNames(
+ "Images (*.png *.xpm *.jpg)",
+ "/home",
+ this,
+ "open files dialog"
+ "Select one or more files to open" );
+ \endcode
+
+ This function creates a modal file dialog called \a name, with
+ parent \a parent. If \a parent is not 0, the dialog will be shown
+ centered over the parent.
+
+ The file dialog's working directory will be set to \a dir. If \a
+ dir includes a file name, the file will be selected. The filter
+ is set to \a filter so that only those files which match the filter
+ are shown. The filter selected is set to \a selectedFilter. The parameters
+ \a dir, \a selectedFilter and \a filter may be QString::null.
+
+ The dialog's caption is set to \a caption. If \a caption is not
+ specified then a default caption will be used.
+
+ Under Windows and Mac OS X, this static function will use the native
+ file dialog and not a QFileDialogP, unless the style of the application
+ is set to something other than the native style.
+
+ Under Unix/X11, the normal behavior of the file dialog is to resolve
+ and follow symlinks. For example, if /usr/tmp is a symlink to /var/tmp,
+ the file dialog will change to /var/tmp after entering /usr/tmp.
+ If \a resolveSymlinks is FALSE, the file dialog will treat
+ symlinks as regular directories.
+
+ Note that if you want to iterate over the list of files, you should
+ iterate over a copy, e.g.
+ \code
+ QStringList list = files;
+ QStringList::Iterator it = list.begin();
+ while( it != list.end() ) {
+ myProcessing( *it );
+ ++it;
+ }
+ \endcode
+
+ \sa getOpenFileName(), getSaveFileName(), getExistingDirectory()
+*/
+
+QStringList QFileDialogP::getOpenFileNames( const QString & filter,
+ const QString& dir,
+ QWidget *parent,
+ const char* name,
+ const QString& caption,
+ QString *selectedFilter,
+ bool resolveSymlinks )
+{
+ bool save_qt_resolve_symlinks = qt_resolve_symlinks;
+ qt_resolve_symlinks = resolveSymlinks;
+
+ QStringList filters;
+ if ( !filter.isEmpty() )
+ filters = makeFiltersList( filter );
+
+ makeVariables();
+
+ if ( workingDirectory->isNull() )
+ *workingDirectory = QDir::currentDirPath();
+
+ if ( !dir.isEmpty() ) {
+ // #### works only correct for local files
+ QUrlOperator u( dir );
+ if ( u.isLocalFile() && QFileInfo( u ).isDir() ) {
+ *workingDirectory = dir;
+ } else {
+ *workingDirectory = u.toString();
+ }
+ }
+
+#if defined(Q_WS_WIN)
+ if ( qApp->style().styleHint( QStyle::SH_GUIStyle ) == WindowsStyle )
+ return winGetOpenFileNames( filter, workingDirectory, parent, name, caption, selectedFilter );
+#elif defined(Q_WS_MAC)
+ if( ( qApp->style().inherits(QMAC_DEFAULT_STYLE) ) )
+ return macGetOpenFileNames(filter, workingDirectory, parent, name, caption );
+#endif
+
+ QFileDialogP *dlg = new QFileDialogP( *workingDirectory, QString::null, parent, name ? name : "qt_filedlg_gofns", TRUE );
+
+ Q_CHECK_PTR( dlg );
+#ifndef QT_NO_WIDGET_TOPEXTRA
+ if ( parent && parent->icon() && !parent->icon()->isNull() )
+ dlg->setIcon( *parent->icon() );
+ else if ( qApp->mainWidget() && qApp->mainWidget()->icon() && !qApp->mainWidget()->icon()->isNull() )
+ dlg->setIcon( *qApp->mainWidget()->icon() );
+#endif
+
+ dlg->setFilters( filters );
+ if ( selectedFilter )
+ dlg->setFilter( *selectedFilter );
+#ifndef QT_NO_WIDGET_TOPEXTRA
+ if ( !caption.isNull() )
+ dlg->setCaption( caption );
+ else
+ dlg->setCaption( QFileDialogP::tr("Open") );
+#endif
+ dlg->setMode( QFileDialogP::ExistingFiles );
+ QString result;
+ QStringList lst;
+ if ( dlg->exec() == QDialog::Accepted ) {
+ lst = dlg->selectedFiles();
+ *workingDirectory = dlg->d->url;
+ if ( selectedFilter )
+ *selectedFilter = dlg->selectedFilter();
+ }
+ delete dlg;
+
+ qt_resolve_symlinks = save_qt_resolve_symlinks;
+
+ return lst;
+}
+
+/*! Updates the line edit to match the speed-key usage in QListView. */
+
+void QFileDialogP::fixupNameEdit()
+{
+ if ( files->currentItem() && d->mode != ExistingFiles ) {
+ if ( ( (QFileDialogPrivate::File*)files->currentItem() )->info.isFile() )
+ nameEdit->setText( files->currentItem()->text( 0 ) );
+ }
+}
+
+/*!
+ Returns the URL of the current working directory in the file dialog.
+
+ \sa setUrl()
+*/
+
+QUrl QFileDialogP::url() const
+{
+ return d->url;
+}
+
+static bool isRoot( const QUrl &u )
+{
+#if defined(Q_OS_MAC9)
+ QString p = QDir::convertSeparators(u.path());
+ if(p.contains(':') == 1)
+ return TRUE;
+#elif defined(Q_OS_UNIX)
+ if ( u.path() == "/" )
+ return TRUE;
+#elif defined(Q_OS_WIN32)
+ QString p = u.path();
+ if ( p.length() == 3 &&
+ p.right( 2 ) == ":/" )
+ return TRUE;
+ if ( p[ 0 ] == '/' && p[ 1 ] == '/' ) {
+ int slashes = p.contains( '/' );
+ if ( slashes <= 3 )
+ return TRUE;
+ if ( slashes == 4 && p[ (int)p.length() - 1 ] == '/' )
+ return TRUE;
+ }
+#else
+#if defined(Q_CC_GNU)
+#warning "case not covered.."
+#endif
+#endif
+
+ if ( !u.isLocalFile() && u.path() == "/" )
+ return TRUE;
+
+ return FALSE;
+}
+
+void QFileDialogP::urlStart( QNetworkOperation *op )
+{
+ if ( !op )
+ return;
+
+ if ( op->operation() == QNetworkProtocol::OpListChildren ) {
+ if ( isRoot( d->url ) )
+ d->cdToParent->setEnabled( FALSE );
+ else
+ d->cdToParent->setEnabled( TRUE );
+ d->mimeTypeTimer->stop();
+ d->sortedList.clear();
+ d->pendingItems.clear();
+ d->moreFiles->clearSelection();
+ files->clearSelection();
+ d->moreFiles->clear();
+ files->clear();
+ files->setSorting( -1 );
+
+ QString s = d->url.toString( FALSE, FALSE );
+ bool found = FALSE;
+ for ( int i = 0; i < d->paths->count(); ++i ) {
+#if defined(Q_WS_WIN)
+ if ( d->paths->text( i ).lower() == s.lower() ) {
+#else
+ if ( d->paths->text( i ) == s ) {
+#endif
+ found = TRUE;
+ d->paths->setCurrentItem( i );
+ break;
+ }
+ }
+ if ( !found ) {
+ d->paths->insertItem( *openFolderIcon, s, -1 );
+ d->paths->setCurrentItem( d->paths->count() - 1 );
+ }
+ d->last = 0;
+ d->hadDotDot = FALSE;
+
+ if ( d->goBack && d->history.last() != d->url.toString() ) {
+ d->history.append( d->url.toString() );
+ if ( d->history.count() > 1 )
+ d->goBack->setEnabled( TRUE );
+ }
+ }
+}
+
+void QFileDialogP::urlFinished( QNetworkOperation *op )
+{
+ if ( !op )
+ return;
+
+ if ( op->operation() == QNetworkProtocol::OpListChildren ) {
+ if ( QApplication::overrideCursor() )
+ QApplication::restoreOverrideCursor();
+ }
+ if ( op->state() == QNetworkProtocol::StFailed ) {
+ if ( d->paths->hasFocus() )
+ d->ignoreNextKeyPress = TRUE;
+
+ if ( d->progressDia ) {
+ d->ignoreStop = TRUE;
+ d->progressDia->close();
+ delete d->progressDia;
+ d->progressDia = 0;
+ }
+
+ QMessageBox::critical( this, tr( "Error" ), op->protocolDetail() );
+
+ int ecode = op->errorCode();
+ if ( ecode == QNetworkProtocol::ErrListChildren || ecode == QNetworkProtocol::ErrParse ||
+ ecode == QNetworkProtocol::ErrUnknownProtocol || ecode == QNetworkProtocol::ErrLoginIncorrect ||
+ ecode == QNetworkProtocol::ErrValid || ecode == QNetworkProtocol::ErrHostNotFound ||
+ ecode == QNetworkProtocol::ErrFileNotExisting ) {
+ if (d->url != d->oldUrl) {
+ QString nf = d->url.nameFilter();
+ d->url = d->oldUrl;
+ d->url.setNameFilter( nf );
+ rereadDir();
+ }
+ } else {
+ // another error happened, no need to go back to last dir
+ }
+ } else if ( op->operation() == QNetworkProtocol::OpListChildren &&
+ op == d->currListChildren ) {
+ if ( !d->hadDotDot && !isRoot( d->url ) ) {
+ bool ok = TRUE;
+#if defined(Q_WS_WIN)
+ if ( d->url.path().left( 2 ) == "//" )
+ ok = FALSE;
+#endif
+ if ( ok ) {
+ QUrlInfo ui( d->url, ".." );
+ ui.setName( ".." );
+ ui.setDir( TRUE );
+ ui.setFile( FALSE );
+ ui.setSymLink( FALSE );
+ ui.setSize( 0 );
+ QValueList<QUrlInfo> lst;
+ lst << ui;
+ insertEntry( lst, 0 );
+ }
+ }
+ resortDir();
+ } else if ( op->operation() == QNetworkProtocol::OpGet ) {
+ } else if ( op->operation() == QNetworkProtocol::OpPut ) {
+ rereadDir();
+ if ( d->progressDia ) {
+ d->ignoreStop = TRUE;
+ d->progressDia->close();
+ }
+ delete d->progressDia;
+ d->progressDia = 0;
+ }
+}
+
+void QFileDialogP::dataTransferProgress( int bytesDone, int bytesTotal, QNetworkOperation *op )
+{
+ if ( !op )
+ return;
+
+ QString label;
+ QUrl u( op->arg( 0 ) );
+ if ( u.isLocalFile() ) {
+ label = u.path();
+ } else {
+ label = QString( "%1 (on %2)" );
+ label = label.arg( u.path() ).arg( u.host() );
+ }
+
+ if ( !d->progressDia ) {
+ if ( bytesDone < bytesTotal) {
+ d->ignoreStop = FALSE;
+ d->progressDia = new QFDProgressDialog( this, label, bytesTotal );
+ connect( d->progressDia, SIGNAL( cancelled() ),
+ this, SLOT( stopCopy() ) );
+ d->progressDia->show();
+ } else
+ return;
+ }
+
+ if ( d->progressDia ) {
+ if ( op->operation() == QNetworkProtocol::OpGet ) {
+ if ( d->progressDia ) {
+ d->progressDia->setReadProgress( bytesDone );
+ }
+ } else if ( op->operation() == QNetworkProtocol::OpPut ) {
+ if ( d->progressDia ) {
+ d->progressDia->setWriteLabel( label );
+ d->progressDia->setWriteProgress( bytesDone );
+ }
+ } else {
+ return;
+ }
+ }
+}
+
+void QFileDialogP::insertEntry( const QValueList<QUrlInfo> &lst, QNetworkOperation *op )
+{
+ if ( op && op->operation() == QNetworkProtocol::OpListChildren &&
+ op != d->currListChildren )
+ return;
+ QValueList<QUrlInfo>::ConstIterator it = lst.begin();
+ for ( ; it != lst.end(); ++it ) {
+ const QUrlInfo &inf = *it;
+ if ( d->mode == DirectoryOnly && !inf.isDir() )
+ continue;
+ if ( inf.name() == ".." ) {
+ d->hadDotDot = TRUE;
+ if ( isRoot( d->url ) )
+ continue;
+#if defined(Q_WS_WIN)
+ if ( d->url.path().left( 2 ) == "//" )
+ continue;
+#endif
+ } else if ( inf.name() == "." )
+ continue;
+
+#if defined(Q_WS_WIN)
+ if ( !bShowHiddenFiles ) {
+ if ( d->url.isLocalFile() ) {
+ QString file = d->url.path() + inf.name();
+#if defined(UNICODE)
+ if ( qWinVersion() & Qt::WV_NT_based ) {
+ if ( GetFileAttributesW( (TCHAR*)qt_winTchar( file, TRUE ) ) & FILE_ATTRIBUTE_HIDDEN )
+ continue;
+ }
+ else
+#endif
+ {
+ if ( GetFileAttributesA( file.local8Bit() ) & FILE_ATTRIBUTE_HIDDEN )
+ continue;
+ }
+ } else {
+ if ( inf.name() != ".." && inf.name()[0] == QChar('.') )
+ continue;
+ }
+ }
+#else
+ if ( !bShowHiddenFiles && inf.name() != ".." ) {
+ if ( inf.name()[ 0 ] == QChar( '.' ) )
+ continue;
+ }
+
+#endif
+ if ( !d->url.isLocalFile() ) {
+ QFileDialogPrivate::File * i = 0;
+ QFileDialogPrivate::MCItem *i2 = 0;
+ i = new QFileDialogPrivate::File( d, &inf, files );
+ i2 = new QFileDialogPrivate::MCItem( d->moreFiles, i );
+
+ if ( d->mode == ExistingFiles && inf.isDir() ||
+ ( isDirectoryMode( d->mode ) && inf.isFile() ) ) {
+ i->setSelectable( FALSE );
+ i2->setSelectable( FALSE );
+ }
+
+ i->i = i2;
+ }
+
+ d->sortedList.append( new QUrlInfo( inf ) );
+ }
+}
+
+void QFileDialogP::removeEntry( QNetworkOperation *op )
+{
+ if ( !op )
+ return;
+
+ QUrlInfo *i = 0;
+ QListViewItemIterator it( files );
+ bool ok1 = FALSE, ok2 = FALSE;
+ for ( i = d->sortedList.first(); it.current(); ++it, i = d->sortedList.next() ) {
+ if ( ( (QFileDialogPrivate::File*)it.current() )->info.name() == op->arg( 0 ) ) {
+ d->pendingItems.removeRef( (QFileDialogPrivate::File*)it.current() );
+ delete ( (QFileDialogPrivate::File*)it.current() )->i;
+ delete it.current();
+ ok1 = TRUE;
+ }
+ if ( i && i->name() == op->arg( 0 ) ) {
+ d->sortedList.removeRef( i );
+ i = d->sortedList.prev();
+ ok2 = TRUE;
+ }
+ if ( ok1 && ok2 )
+ break;
+ }
+}
+
+void QFileDialogP::itemChanged( QNetworkOperation *op )
+{
+ if ( !op )
+ return;
+
+ QUrlInfo *i = 0;
+ QListViewItemIterator it1( files );
+ bool ok1 = FALSE, ok2 = FALSE;
+ // first check whether the new file replaces an existing file.
+ for ( i = d->sortedList.first(); it1.current(); ++it1, i = d->sortedList.next() ) {
+ if ( ( (QFileDialogPrivate::File*)it1.current() )->info.name() == op->arg( 1 ) ) {
+ delete ( (QFileDialogPrivate::File*)it1.current() )->i;
+ delete it1.current();
+ ok1 = TRUE;
+ }
+ if ( i && i->name() == op->arg( 1 ) ) {
+ d->sortedList.removeRef( i );
+ i = d->sortedList.prev();
+ ok2 = TRUE;
+ }
+ if ( ok1 && ok2 )
+ break;
+ }
+
+ i = 0;
+ QListViewItemIterator it( files );
+ ok1 = FALSE;
+ ok2 = FALSE;
+ for ( i = d->sortedList.first(); it.current(); ++it, i = d->sortedList.next() ) {
+ if ( ( (QFileDialogPrivate::File*)it.current() )->info.name() == op->arg( 0 ) ) {
+ ( (QFileDialogPrivate::File*)it.current() )->info.setName( op->arg( 1 ) );
+ ok1 = TRUE;
+ }
+ if ( i && i->name() == op->arg( 0 ) ) {
+ i->setName( op->arg( 1 ) );
+ ok2 = TRUE;
+ }
+ if ( ok1 && ok2 )
+ break;
+ }
+
+ resortDir();
+}
+
+/*!
+ \property QFileDialogP::infoPreview
+
+ \brief whether the file dialog can provide preview information about
+ the currently selected file
+
+ The default is FALSE.
+*/
+bool QFileDialogP::isInfoPreviewEnabled() const
+{
+ return d->infoPreview;
+}
+
+void QFileDialogP::setInfoPreviewEnabled( bool info )
+{
+ if ( info == d->infoPreview )
+ return;
+ d->geometryDirty = TRUE;
+ d->infoPreview = info;
+ updateGeometries();
+}
+
+
+/*!
+ \property QFileDialogP::contentsPreview
+
+ \brief whether the file dialog can provide a contents preview of the
+ currently selected file
+
+ The default is FALSE.
+
+ \sa setContentsPreview() setInfoPreviewEnabled()
+*/
+// ### improve the above documentation: how is the preview done, how can I add
+// support for customized preview, etc.
+
+bool QFileDialogP::isContentsPreviewEnabled() const
+{
+ return d->contentsPreview;
+}
+
+void QFileDialogP::setContentsPreviewEnabled( bool contents )
+{
+ if ( contents == d->contentsPreview )
+ return;
+ d->geometryDirty = TRUE;
+ d->contentsPreview = contents;
+ updateGeometries();
+}
+
+
+/*!
+ Sets the widget to be used for displaying information about the file
+ to the widget \a w and a preview of that information to the
+ QFilePreviewP \a preview.
+
+ Normally you would create a preview widget that derives from both QWidget and
+ QFilePreviewP, so you should pass the same widget twice.
+
+ \code
+ class Preview : public QLabel, public QFilePreviewP
+ {
+ public:
+ Preview( QWidget *parent=0 ) : QLabel( parent ) {}
+
+ void previewUrl( const QUrl &u )
+ {
+ QString path = u.path();
+ QPixmap pix( path );
+ if ( pix.isNull() )
+ setText( "This is not a pixmap" );
+ else
+ setText( "This is a pixmap" );
+ }
+ };
+
+ //...
+
+ int main( int argc, char** argv )
+ {
+ Preview* p = new Preview;
+
+ QFileDialogP* fd = new QFileDialogP( this );
+ fd->setInfoPreviewEnabled( TRUE );
+ fd->setInfoPreview( p, p );
+ fd->setPreviewMode( QFileDialogP::Info );
+ fd->show();
+ }
+
+ \endcode
+
+ \sa setContentsPreview(), setInfoPreviewEnabled(), setPreviewMode()
+
+*/
+
+void QFileDialogP::setInfoPreview( QWidget *w, QFilePreviewP *preview )
+{
+ if ( !w || !preview )
+ return;
+
+ if ( d->infoPreviewWidget ) {
+ d->preview->removeWidget( d->infoPreviewWidget );
+ delete d->infoPreviewWidget;
+ }
+ if ( d->infoPreviewer )
+ delete d->infoPreviewer;
+ d->infoPreviewWidget = w;
+ d->infoPreviewer = preview;
+ w->reparent( d->preview, 0, QPoint( 0, 0 ) );
+}
+
+/*!
+ Sets the widget to be used for displaying the contents of the file
+ to the widget \a w and a preview of those contents to the
+ QFilePreviewP \a preview.
+
+ Normally you would create a preview widget that derives from both QWidget and
+ QFilePreviewP, so you should pass the same widget twice.
+
+ \code
+ class Preview : public QLabel, public QFilePreviewP
+ {
+ public:
+ Preview( QWidget *parent=0 ) : QLabel( parent ) {}
+
+ void previewUrl( const QUrl &u )
+ {
+ QString path = u.path();
+ QPixmap pix( path );
+ if ( pix.isNull() )
+ setText( "This is not a pixmap" );
+ else
+ setPixmap( pix );
+ }
+ };
+
+ //...
+
+ int main( int argc, char** argv )
+ {
+ Preview* p = new Preview;
+
+ QFileDialogP* fd = new QFileDialogP( this );
+ fd->setContentsPreviewEnabled( TRUE );
+ fd->setContentsPreview( p, p );
+ fd->setPreviewMode( QFileDialogP::Contents );
+ fd->show();
+ }
+ \endcode
+
+ \sa setContentsPreviewEnabled(), setInfoPreview(), setPreviewMode()
+*/
+
+void QFileDialogP::setContentsPreview( QWidget *w, QFilePreviewP *preview )
+{
+ if ( !w || !preview )
+ return;
+
+ if ( d->contentsPreviewWidget ) {
+ d->preview->removeWidget( d->contentsPreviewWidget );
+ delete d->contentsPreviewWidget;
+ }
+ if ( d->contentsPreviewer )
+ delete d->contentsPreviewer;
+ d->contentsPreviewWidget = w;
+ d->contentsPreviewer = preview;
+ w->reparent( d->preview, 0, QPoint( 0, 0 ) );
+}
+
+/*!
+ Re-sorts the displayed directory.
+
+ \sa rereadDir()
+*/
+
+void QFileDialogP::resortDir()
+{
+ d->mimeTypeTimer->stop();
+ d->pendingItems.clear();
+
+ QFileDialogPrivate::File *item = 0;
+ QFileDialogPrivate::MCItem *item2 = 0;
+
+ d->sortedList.sort();
+
+ if ( files->childCount() > 0 || d->moreFiles->count() > 0 ) {
+ d->moreFiles->clear();
+ files->clear();
+ d->last = 0;
+ files->setSorting( -1 );
+ }
+
+ QUrlInfo *i = sortAscending ? d->sortedList.first() : d->sortedList.last();
+ for ( ; i; i = sortAscending ? d->sortedList.next() : d->sortedList.prev() ) {
+ item = new QFileDialogPrivate::File( d, i, files );
+ item2 = new QFileDialogPrivate::MCItem( d->moreFiles, item, item2 );
+ item->i = item2;
+ d->pendingItems.append( item );
+ if ( d->mode == ExistingFiles && item->info.isDir() ||
+ ( isDirectoryMode( d->mode ) && item->info.isFile() ) ) {
+ item->setSelectable( FALSE );
+ item2->setSelectable( FALSE );
+ }
+ }
+
+ // ##### As the QFileIconProviderP only support QFileInfo and no
+ // QUrlInfo it can be only used for local files at the moment. In
+ // 3.0 we have to change the API of QFileIconProviderP to work on
+ // QUrlInfo so that also remote filesystems can be show mime-type
+ // specific icons.
+ if ( d->url.isLocalFile() )
+ d->mimeTypeTimer->start( 0 );
+}
+
+/*!
+ Stops the current copy operation.
+*/
+
+void QFileDialogP::stopCopy()
+{
+ if ( d->ignoreStop )
+ return;
+
+ d->url.blockSignals( TRUE );
+ d->url.stop();
+ if ( d->progressDia ) {
+ d->ignoreStop = TRUE;
+ QTimer::singleShot( 100, this, SLOT( removeProgressDia() ) );
+ }
+ d->url.blockSignals( FALSE );
+}
+
+/*!
+ \internal
+*/
+
+void QFileDialogP::removeProgressDia()
+{
+ if ( d->progressDia )
+ delete d->progressDia;
+ d->progressDia = 0;
+}
+
+/*!
+ \internal
+*/
+
+void QFileDialogP::doMimeTypeLookup()
+{
+ if ( !iconProvider() ) {
+ d->pendingItems.clear();
+ d->mimeTypeTimer->stop();
+ return;
+ }
+
+ d->mimeTypeTimer->stop();
+ if ( d->pendingItems.count() == 0 ) {
+ return;
+ }
+
+ QRect r;
+ QFileDialogPrivate::File *item = d->pendingItems.first();
+ if ( item ) {
+ QFileInfo fi;
+ if ( d->url.isLocalFile() ) {
+ fi.setFile( QUrl( d->url.path(), QFileDialogPrivate::encodeFileName( item->info.name() ) ).path( FALSE ) );
+ } else
+ fi.setFile( item->info.name() ); // #####
+ const QPixmap *p = iconProvider()->pixmap( fi );
+ if ( p && p != item->pixmap( 0 ) &&
+ ( !item->pixmap( 0 ) || p->serialNumber() != item->pixmap( 0 )->serialNumber() ) &&
+ p != fifteenTransparentPixels ) {
+ item->hasMimePixmap = TRUE;
+
+ // evil hack to avoid much too much repaints!
+ qApp->processEvents();
+ files->setUpdatesEnabled( FALSE );
+ files->viewport()->setUpdatesEnabled( FALSE );
+ if ( item != d->pendingItems.first() )
+ return;
+ item->setPixmap( 0, *p );
+ qApp->processEvents();
+ files->setUpdatesEnabled( TRUE );
+ files->viewport()->setUpdatesEnabled( TRUE );
+
+ if ( files->isVisible() ) {
+ QRect ir( files->itemRect( item ) );
+ if ( ir != QRect( 0, 0, -1, -1 ) ) {
+ r = r.unite( ir );
+ }
+ } else {
+ QRect ir( d->moreFiles->itemRect( item->i ) );
+ if ( ir != QRect( 0, 0, -1, -1 ) ) {
+ r = r.unite( ir );
+ }
+ }
+ }
+ if ( d->pendingItems.count() )
+ d->pendingItems.removeFirst();
+ }
+
+ if ( d->moreFiles->isVisible() ) {
+ d->moreFiles->viewport()->repaint( r, FALSE );
+ } else {
+ files->viewport()->repaint( r, FALSE );
+ }
+
+ if ( d->pendingItems.count() )
+ d->mimeTypeTimer->start( 0 );
+ else if ( d->moreFiles->isVisible() )
+ d->moreFiles->triggerUpdate( TRUE );
+}
+
+/*!
+ If \a b is TRUE then all the files in the current directory are selected;
+ otherwise, they are deselected.
+*/
+
+void QFileDialogP::selectAll( bool b )
+{
+ if ( d->mode != ExistingFiles )
+ return;
+ d->moreFiles->selectAll( b );
+ files->selectAll( b );
+}
+
+void QFileDialogP::goBack()
+{
+ if ( !d->goBack || !d->goBack->isEnabled() )
+ return;
+ d->history.remove( d->history.last() );
+ if ( d->history.count() < 2 )
+ d->goBack->setEnabled( FALSE );
+ setUrl( d->history.last() );
+}
+
+// a class with wonderfully inflexible flexibility. why doesn't it
+// just subclass QWidget in the first place? 'you have to derive your
+// preview widget from QWidget and from this class' indeed.
+
+/*!
+ \class QFilePreviewP qfiledialog.h
+ \ingroup misc
+ \brief The QFilePreviewP class provides file previewing in QFileDialogP.
+
+ This class is an abstract base class which is used to implement
+ widgets that can display a preview of a file in a QFileDialogP.
+
+ You must derive the preview widget from both QWidget and from this
+ class. Then you must reimplement this class's previewUrl() function,
+ which is called by the file dialog if the preview of a file
+ (specified as a URL) should be shown.
+
+ See also QFileDialog::setPreviewMode(), QFileDialogP::setContentsPreview(),
+ QFileDialogP::setInfoPreview(), QFileDialogP::setInfoPreviewEnabled(),
+ QFileDialogP::setContentsPreviewEnabled().
+
+ For an example of a preview widget see qt/examples/qdir/qdir.cpp.
+*/
+
+/*!
+ Constructs the QFilePreviewP.
+*/
+
+QFilePreviewP::QFilePreviewP()
+{
+}
+
+/*!
+ \fn void QFilePreviewP::previewUrl( const QUrl &url )
+
+ This function is called by QFileDialogP if a preview
+ for the \a url should be shown. Reimplement this
+ function to provide file previewing.
+*/
+
+#endif
--- /dev/null
+/////////////////////////////////////////////////////////////////////////////
+// Module : PatchQt
+// File : qfiledialogP.h
+// Description : the patch for Qt's QFileDialog class (qfiledialog.h)
+/////////////////////////////////////////////////////////////////////////////
+
+/****************************************************************************
+** $Id$
+**
+** Definition of QFileDialog class
+**
+** Created : 950428
+**
+** Copyright (C) 1992-2000 Trolltech AS. All rights reserved.
+**
+** This file is part of the dialogs module of the Qt GUI Toolkit.
+**
+** This file may be distributed under the terms of the Q Public License
+** as defined by Trolltech AS of Norway and appearing in the file
+** LICENSE.QPL included in the packaging of this file.
+**
+** This file may be distributed and/or modified under the terms of the
+** GNU General Public License version 2 as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL included in the
+** packaging of this file.
+**
+** Licensees holding valid Qt Enterprise Edition or Qt Professional Edition
+** licenses may use this file in accordance with the Qt Commercial License
+** Agreement provided with the Software.
+**
+** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
+** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+**
+** See http://www.trolltech.com/pricing.html or email sales@trolltech.com for
+** information about Qt Commercial License Agreements.
+** See http://www.trolltech.com/qpl/ for QPL licensing information.
+** See http://www.trolltech.com/gpl/ for GPL licensing information.
+**
+** Contact info@trolltech.com if any conditions of this licensing are
+** not clear to you.
+**
+**********************************************************************/
+
+#ifndef QFILEDIALOGP_H
+#define QFILEDIALOGP_H
+
+class QPushButton;
+class QButton;
+class QLabel;
+class QWidget;
+class QFileDialog;
+class QTimer;
+class QNetworkOperation;
+class QLineEdit;
+class QListViewItem;
+class QListBoxItem;
+class QProgressBar;
+class QFileDialogPrivate;
+class QFileDialogQFileListView;
+
+#ifndef QT_H
+#include "qdir.h"
+#include "qdialog.h"
+#include "qurloperator.h"
+#include "qurlinfo.h"
+#include "qlistbox.h"
+#include "qlistview.h"
+#include "qlineedit.h"
+#endif // QT_H
+
+#ifndef QT_NO_FILEDIALOG
+
+class Q_EXPORT QFileIconProviderP : public QObject
+{
+ Q_OBJECT
+public:
+ QFileIconProviderP( QObject * parent = 0, const char* name = 0 );
+ virtual const QPixmap * pixmap( const QFileInfo & );
+
+private: // Disabled copy constructor and operator=
+#if defined(Q_DISABLE_COPY)
+ QFileIconProviderP( const QFileIconProviderP & );
+ QFileIconProviderP& operator=( const QFileIconProviderP & );
+#endif
+};
+
+class Q_EXPORT QFilePreviewP
+{
+public:
+ QFilePreviewP();
+ virtual void previewUrl( const QUrl &url ) = 0;
+
+};
+
+class Q_EXPORT QFileDialogP : public QDialog
+{
+ Q_OBJECT
+ Q_ENUMS( Mode ViewMode PreviewMode )
+ // ##### Why are this read-only properties ?
+ Q_PROPERTY( QString selectedFile READ selectedFile )
+ Q_PROPERTY( QString selectedFilter READ selectedFilter )
+ Q_PROPERTY( QStringList selectedFiles READ selectedFiles )
+ // #### Should not we be able to set the path ?
+ Q_PROPERTY( QString dirPath READ dirPath )
+ Q_PROPERTY( bool showHiddenFiles READ showHiddenFiles WRITE setShowHiddenFiles )
+ Q_PROPERTY( Mode mode READ mode WRITE setMode )
+ Q_PROPERTY( ViewMode viewMode READ viewMode WRITE setViewMode )
+ Q_PROPERTY( PreviewMode previewMode READ previewMode WRITE setPreviewMode )
+ Q_PROPERTY( bool infoPreview READ isInfoPreviewEnabled WRITE setInfoPreviewEnabled )
+ Q_PROPERTY( bool contentsPreview READ isContentsPreviewEnabled WRITE setContentsPreviewEnabled )
+
+public:
+ QFileDialogP( const QString& dirName, const QString& filter = QString::null,
+ QWidget* parent=0, const char* name=0, bool modal = FALSE );
+ QFileDialogP( QWidget* parent=0, const char* name=0, bool modal = FALSE );
+ ~QFileDialogP();
+
+ // recommended static functions
+
+ static QString getOpenFileName( const QString &initially = QString::null,
+ const QString &filter = QString::null,
+ QWidget *parent = 0, const char* name = 0,
+ const QString &caption = QString::null,
+ QString *selectedFilter = 0,
+ bool resolveSymlinks = TRUE);
+ static QString getSaveFileName( const QString &initially = QString::null,
+ const QString &filter = QString::null,
+ QWidget *parent = 0, const char* name = 0,
+ const QString &caption = QString::null,
+ QString *selectedFilter = 0,
+ bool resolveSymlinks = TRUE);
+ static QString getExistingDirectory( const QString &dir = QString::null,
+ QWidget *parent = 0,
+ const char* name = 0,
+ const QString &caption = QString::null,
+ bool dirOnly = TRUE,
+ bool resolveSymlinks = TRUE);
+ static QStringList getOpenFileNames( const QString &filter= QString::null,
+ const QString &dir = QString::null,
+ QWidget *parent = 0,
+ const char* name = 0,
+ const QString &caption = QString::null,
+ QString *selectedFilter = 0,
+ bool resolveSymlinks = TRUE);
+
+ // other static functions
+
+ static void setIconProvider( QFileIconProviderP * );
+ static QFileIconProviderP* iconProvider();
+
+ // non-static function for special needs
+
+ QString selectedFile() const;
+ QString selectedFilter() const;
+ virtual void setSelectedFilter( const QString& );
+ virtual void setSelectedFilter( int );
+
+ void setSelection( const QString &);
+
+ void selectAll( bool b );
+
+ QStringList selectedFiles() const;
+
+ QString dirPath() const;
+
+ void setDir( const QDir & );
+ const QDir *dir() const;
+
+ void setShowHiddenFiles( bool s );
+ bool showHiddenFiles() const;
+
+ void rereadDir();
+ void resortDir();
+
+ enum Mode { AnyFile, ExistingFile, Directory, ExistingFiles, DirectoryOnly };
+ void setMode( Mode );
+ Mode mode() const;
+
+ enum ViewMode { Detail, List };
+ enum PreviewMode { NoPreview, Contents, Info };
+ void setViewMode( ViewMode m );
+ ViewMode viewMode() const;
+ void setPreviewMode( PreviewMode m );
+ PreviewMode previewMode() const;
+
+ bool eventFilter( QObject *, QEvent * );
+
+ bool isInfoPreviewEnabled() const;
+ bool isContentsPreviewEnabled() const;
+ void setInfoPreviewEnabled( bool );
+ void setContentsPreviewEnabled( bool );
+
+ void setInfoPreview( QWidget *w, QFilePreviewP *preview );
+ void setContentsPreview( QWidget *w, QFilePreviewP *preview );
+
+ QUrl url() const;
+
+ void addFilter( const QString &filter );
+
+public slots:
+ void done( int );
+ void setDir( const QString& );
+ void setUrl( const QUrlOperator &url );
+ void setFilter( const QString& );
+ void setFilters( const QString& );
+ void setFilters( const char ** );
+ void setFilters( const QStringList& );
+
+protected:
+ void resizeEvent( QResizeEvent * );
+ void keyPressEvent( QKeyEvent * );
+
+ void addWidgets( QLabel *, QWidget *, QPushButton * );
+ void addToolButton( QButton *b, bool separator = FALSE );
+ void addLeftWidget( QWidget *w );
+ void addRightWidget( QWidget *w );
+
+signals:
+ void fileHighlighted( const QString& );
+ void fileSelected( const QString& );
+ void filesSelected( const QStringList& );
+ void dirEntered( const QString& );
+ void filterSelected( const QString& );
+
+private slots:
+ void detailViewSelectionChanged();
+ void listBoxSelectionChanged();
+ void changeMode( int );
+ void fileNameEditReturnPressed();
+ void stopCopy();
+ void removeProgressDia();
+
+ void fileSelected( int );
+ void fileHighlighted( int );
+ void dirSelected( int );
+ void pathSelected( int );
+
+ void updateFileNameEdit( QListViewItem *);
+ void selectDirectoryOrFile( QListViewItem * );
+ void popupContextMenu( QListViewItem *, const QPoint &, int );
+ void popupContextMenu( QListBoxItem *, const QPoint & );
+ void updateFileNameEdit( QListBoxItem *);
+ void selectDirectoryOrFile( QListBoxItem * );
+ void fileNameEditDone();
+
+ void okClicked();
+ void filterClicked(); // not used
+ void cancelClicked();
+
+ void cdUpClicked();
+ void newFolderClicked();
+
+ void fixupNameEdit();
+
+ void doMimeTypeLookup();
+
+ void updateGeometries();
+ void modeButtonsDestroyed();
+ void urlStart( QNetworkOperation *op );
+ void urlFinished( QNetworkOperation *op );
+ void dataTransferProgress( int bytesDone, int bytesTotal, QNetworkOperation * );
+ void insertEntry( const QValueList<QUrlInfo> &fi, QNetworkOperation *op );
+ void removeEntry( QNetworkOperation * );
+ void createdDirectory( const QUrlInfo &info, QNetworkOperation * );
+ void itemChanged( QNetworkOperation * );
+ void goBack();
+
+private:
+ enum PopupAction {
+ PA_Open = 0,
+ PA_Delete,
+ PA_Rename,
+ PA_SortName,
+ PA_SortSize,
+ PA_SortType,
+ PA_SortDate,
+ PA_SortUnsorted,
+ PA_Cancel,
+ PA_Reload,
+ PA_Hidden
+ };
+
+ void init();
+ bool trySetSelection( bool isDir, const QUrlOperator &, bool );
+ void deleteFile( const QString &filename );
+ void popupContextMenu( const QString &filename, bool withSort,
+ PopupAction &action, const QPoint &p );
+
+ QDir reserved; // was cwd
+ QString fileName;
+
+ friend class QFileDialogQFileListView;
+ friend class QFileListBox;
+
+ QFileDialogPrivate *d;
+ QFileDialogQFileListView *files;
+
+ QLineEdit *nameEdit; // also filter
+ QPushButton *okB;
+ QPushButton *cancelB;
+
+#if defined(Q_WS_WIN)
+ static QString winGetOpenFileName( const QString &initialSelection,
+ const QString &filter,
+ QString* workingDirectory,
+ QWidget *parent = 0,
+ const char* name = 0,
+ const QString& caption = QString::null,
+ QString* selectedFilter = 0 );
+ static QString winGetSaveFileName( const QString &initialSelection,
+ const QString &filter,
+ QString* workingDirectory,
+ QWidget *parent = 0,
+ const char* name = 0,
+ const QString& caption = QString::null,
+ QString* selectedFilter = 0 );
+ static QStringList winGetOpenFileNames( const QString &filter,
+ QString* workingDirectory,
+ QWidget *parent = 0,
+ const char* name = 0,
+ const QString& caption = QString::null,
+ QString* selectedFilter = 0 );
+ static QString winGetExistingDirectory( const QString &initialDirectory,
+ QWidget* parent = 0,
+ const char* name = 0,
+ const QString& caption = QString::null);
+ static QString resolveLinkFile( const QString& linkfile );
+#endif
+#if defined(Q_WS_MACX) || defined(Q_WS_MAC9)
+ static QString macGetSaveFileName( const QString &, const QString &,
+ QString *, QWidget *, const char*,
+ const QString& );
+ static QStringList macGetOpenFileNames( const QString &, QString*,
+ QWidget *, const char *,
+ const QString&, bool = TRUE,
+ bool = FALSE );
+#endif
+
+
+private: // Disabled copy constructor and operator=
+#if defined(Q_DISABLE_COPY)
+ QFileDialogP( const QFileDialogP & );
+ QFileDialogP &operator=( const QFileDialogP & );
+#endif
+};
+
+/******************************************************************
+ *
+ * Definitions of view classes
+ *
+ ******************************************************************/
+
+class QRenameEdit : public QLineEdit
+{
+ Q_OBJECT
+
+public:
+ QRenameEdit( QWidget *parent )
+ : QLineEdit( parent, "qt_rename_edit" )
+ {}
+
+protected:
+ void keyPressEvent( QKeyEvent *e );
+ void focusOutEvent( QFocusEvent *e );
+
+signals:
+ void escapePressed();
+
+};
+
+class QFileListBox : public QListBox
+{
+ friend class QFileDialogP;
+
+ Q_OBJECT
+
+private:
+ QFileListBox( QWidget *parent, QFileDialogP *d );
+
+ void clear();
+ void show();
+ void startRename( bool check = TRUE );
+ void viewportMousePressEvent( QMouseEvent *e );
+ void viewportMouseReleaseEvent( QMouseEvent *e );
+ void viewportMouseDoubleClickEvent( QMouseEvent *e );
+ void viewportMouseMoveEvent( QMouseEvent *e );
+#ifndef QT_NO_DRAGANDDROP
+ void viewportDragEnterEvent( QDragEnterEvent *e );
+ void viewportDragMoveEvent( QDragMoveEvent *e );
+ void viewportDragLeaveEvent( QDragLeaveEvent *e );
+ void viewportDropEvent( QDropEvent *e );
+ bool acceptDrop( const QPoint &pnt, QWidget *source );
+ void setCurrentDropItem( const QPoint &pnt );
+#endif
+ void keyPressEvent( QKeyEvent *e );
+
+private slots:
+ void rename();
+ void cancelRename();
+ void doubleClickTimeout();
+ void changeDirDuringDrag();
+ void dragObjDestroyed();
+ void contentsMoved( int, int );
+
+private:
+ QRenameEdit *lined;
+ QFileDialogP *filedialog;
+ bool renaming;
+ QTimer* renameTimer;
+ QListBoxItem *renameItem, *dragItem;
+ QPoint pressPos, oldDragPos;
+ bool mousePressed;
+ int urls;
+ QString startDragDir;
+ QListBoxItem *currDropItem;
+ QTimer *changeDirTimer;
+ bool firstMousePressEvent;
+ QUrlOperator startDragUrl;
+
+};
+
+
+class QFileDialogQFileListView : public QListView
+{
+ Q_OBJECT
+
+public:
+ QFileDialogQFileListView( QWidget *parent, QFileDialogP *d );
+
+ void clear();
+ void startRename( bool check = TRUE );
+ void setSorting( int column, bool increasing = TRUE );
+
+ QRenameEdit *lined;
+ bool renaming;
+ QListViewItem *renameItem;
+
+private:
+ void viewportMousePressEvent( QMouseEvent *e );
+ void viewportMouseDoubleClickEvent( QMouseEvent *e );
+ void keyPressEvent( QKeyEvent *e );
+ void viewportMouseReleaseEvent( QMouseEvent *e );
+ void viewportMouseMoveEvent( QMouseEvent *e );
+#ifndef QT_NO_DRAGANDDROP
+ void viewportDragEnterEvent( QDragEnterEvent *e );
+ void viewportDragMoveEvent( QDragMoveEvent *e );
+ void viewportDragLeaveEvent( QDragLeaveEvent *e );
+ void viewportDropEvent( QDropEvent *e );
+ bool acceptDrop( const QPoint &pnt, QWidget *source );
+ void setCurrentDropItem( const QPoint &pnt );
+#endif
+
+private slots:
+ void rename();
+ void cancelRename();
+ void changeSortColumn2( int column );
+ void doubleClickTimeout();
+ void changeDirDuringDrag();
+ void dragObjDestroyed();
+ void contentsMoved( int, int );
+
+private:
+ QFileDialogP *filedialog;
+ QTimer* renameTimer;
+ QPoint pressPos, oldDragPos;
+ bool mousePressed;
+ int urls;
+ QString startDragDir;
+ QListViewItem *currDropItem, *dragItem;
+ QTimer *changeDirTimer;
+ bool firstMousePressEvent;
+ bool ascending;
+ int sortcolumn;
+ QUrlOperator startDragUrl;
+
+};
+
+/****************************************************************************
+ *
+ * Classes for copy progress dialog
+ *
+ ****************************************************************************/
+
+class QFDProgressAnimation : public QWidget
+{
+ Q_OBJECT
+
+public:
+ QFDProgressAnimation( QWidget *parent );
+ void start();
+
+private slots:
+ void next();
+
+protected:
+ void paintEvent( QPaintEvent *e );
+
+private:
+ int step;
+ QTimer *timer;
+
+};
+
+class QFDProgressDialog : public QDialog
+{
+ Q_OBJECT
+
+public:
+ QFDProgressDialog( QWidget *parent, const QString &fn, int steps );
+
+ void setReadProgress( int p );
+ void setWriteProgress( int p );
+ void setWriteLabel( const QString &s );
+
+signals:
+ void cancelled();
+
+private:
+ QProgressBar *readBar;
+ QProgressBar *writeBar;
+ QLabel *writeLabel;
+ QFDProgressAnimation *animation;
+
+};
+
+#endif
+
+#endif // QFILEDIALOG_H
--- /dev/null
+// SALOME OCCViewer : build OCC Viewer into Salome desktop
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : Plot2d_Prs.cxx
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#include "Plot2d_Prs.h"
+
+//==========================================================
+/*!
+ * Plot2d_Prs::Plot2d_Prs
+ * Default constructor
+ */
+//==========================================================
+Plot2d_Prs::Plot2d_Prs()
+{
+}
+
+//==========================================================
+/*!
+ * Plot2d_Prs::Plot2d_Prs
+ * Standard constructor
+ */
+//==========================================================
+Plot2d_Prs::Plot2d_Prs( const Plot2d_Curve* obj )
+{
+ AddObject( obj );
+}
+
+//==========================================================
+/*!
+ * Plot2d_Prs::~Plot2d_Prs
+ * Destructor
+ */
+//==========================================================
+Plot2d_Prs::~Plot2d_Prs()
+{
+ myObjects.clear();
+}
+
+//==========================================================
+/*!
+ * Plot2d_Prs::GetObjects
+ * Get curves list
+ */
+//==========================================================
+Plot2d_CurveContainer Plot2d_Prs::GetObjects() const
+{
+ return myObjects;
+}
+
+//==========================================================
+/*!
+ * Plot2d_Prs::AddObject
+ * Add curbe
+ */
+//==========================================================
+void Plot2d_Prs::AddObject( const Plot2d_Curve* obj )
+{
+ myObjects.addCurve( (Plot2d_Curve*)obj );
+}
+
+//==========================================================
+/*!
+ * Plot2d_Prs::IsNull
+ * Return 0 if list of the curves is empty
+ * [ Reimplemented from SALOME_Prs ]
+ */
+//==========================================================
+bool Plot2d_Prs::IsNull() const
+{
+ return myObjects.isEmpty();
+}
--- /dev/null
+// SALOME OCCViewer : build OCC Viewer into Salome desktop
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : Plot2d_Prs.h
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#ifndef PLOT2D_PRS_H
+#define PLOT2D_PRS_H
+
+#include "SALOME_Prs.h"
+#include <Plot2d_CurveContainer.h>
+
+class Plot2d_Curve;
+
+class Plot2d_Prs : public SALOME_Prs2d
+{
+public:
+ Plot2d_Prs();
+ // Default constructor
+ Plot2d_Prs( const Plot2d_Curve* obj );
+ // Standard constructor
+ ~Plot2d_Prs();
+ // Destructor
+
+ Plot2d_CurveContainer GetObjects() const;
+ // Get curves list
+ void AddObject( const Plot2d_Curve* obj );
+ // Add curve
+
+ bool IsNull() const;
+ // Reimplemented from SALOME_Prs
+
+private:
+ Plot2d_CurveContainer myObjects; // list of curves
+};
+
+#endif
--- /dev/null
+# source path
+top_srcdir=@top_srcdir@
+top_builddir=../..
+srcdir=@srcdir@
+VPATH=.:@srcdir@:@top_srcdir@/idl
+
+
+@COMMENCE@
+
+EXPORT_HEADERS = SALOME_Prs.h
+
+# Libraries targets
+
+LIB = libSalomePrs.la
+LIB_SRC = SALOME_Prs.cxx
+
+LIB_CLIENT_IDL =
+
+# Executables targets
+BIN =
+BIN_SRC =
+
+CPPFLAGS+=
+LDFLAGS+=
+
+
+@CONCLUDE@
--- /dev/null
+// File: SALOME_Prs.cxx
+// Created: Wed Apr 28 15:03:43 2004
+// Author: Sergey ANIKIN
+// <san@startrex.nnov.opencascade.com>
+
+
+#include "SALOME_Prs.h"
+
+#include "utilities.h"
+
+using namespace std;
+
+//===========================================================
+/*!
+ * Function: SALOME_OCCPrs::DisplayIn
+ * Purpose: Dispatches display operation to proper Display()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_OCCPrs::DisplayIn( SALOME_View* v ) const
+{
+ if ( v ) v->Display( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_OCCPrs::EraseIn
+ * Purpose: Dispatches display operation to proper Erase()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_OCCPrs::EraseIn( SALOME_View* v, const bool forced ) const
+{
+ if ( v ) v->Erase( this, forced );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_OCCPrs::LocalSelectionIn
+ * Purpose: Dispatches operation to proper LocalSelectionIn()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_OCCPrs::LocalSelectionIn( SALOME_View* v, const int mode ) const
+{
+ if ( v ) v->LocalSelection( this, mode );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_OCCPrs::Update
+ * Purpose: Dispatches update operation to proper Update()
+ * method of SALOME_Displayer
+ */
+//===========================================================
+void SALOME_OCCPrs::Update( SALOME_Displayer* d )
+{
+ if ( d ) d->Update( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_VTKPrs::DisplayIn
+ * Purpose: Dispatches display operation to proper Display()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_VTKPrs::DisplayIn( SALOME_View* v ) const
+{
+ if ( v ) v->Display( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_VTKPrs::EraseIn
+ * Purpose: Dispatches display operation to proper Erase()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_VTKPrs::EraseIn( SALOME_View* v, const bool forced ) const
+{
+ if ( v ) v->Erase( this, forced );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_VTKPrs::LocalSelectionIn
+ * Purpose: Dispatches operation to proper LocalSelectionIn()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_VTKPrs::LocalSelectionIn( SALOME_View* v, const int mode ) const
+{
+ if ( v ) v->LocalSelection( this, mode );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_VTKPrs::Update
+ * Purpose: Dispatches update operation to proper Update()
+ * method of SALOME_Displayer
+ */
+//===========================================================
+void SALOME_VTKPrs::Update( SALOME_Displayer* d )
+{
+ if ( d ) d->Update( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Prs2d::DisplayIn
+ * Purpose: Dispatches display operation to proper Display()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_Prs2d::DisplayIn( SALOME_View* v ) const
+{
+ if ( v ) v->Display( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Prs2d::EraseIn
+ * Purpose: Dispatches display operation to proper Erase()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_Prs2d::EraseIn( SALOME_View* v, const bool forced ) const
+{
+ if ( v ) v->Erase( this, forced );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Prs2d::LocalSelectionIn
+ * Purpose: Dispatches operation to proper LocalSelectionIn()
+ * method of SALOME_View
+ */
+//===========================================================
+void SALOME_Prs2d::LocalSelectionIn( SALOME_View* v, const int mode ) const
+{
+ if ( v ) v->LocalSelection( this, mode );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Prs2d::Update
+ * Purpose: Dispatches update operation to proper Update()
+ * method of SALOME_Displayer
+ */
+//===========================================================
+void SALOME_Prs2d::Update( SALOME_Displayer* d )
+{
+ if ( d ) d->Update( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Display
+ * Purpose: Gives control to SALOME_Prs object, so that
+ * it could perform double dispatch
+ */
+//===========================================================
+void SALOME_View::Display( const SALOME_Prs* prs )
+{
+ prs->DisplayIn( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Erase
+ * Purpose: Gives control to SALOME_Prs object, so that
+ * it could perform double dispatch
+ */
+//===========================================================
+void SALOME_View::Erase( const SALOME_Prs* prs, const bool forced )
+{
+ prs->EraseIn( this, forced );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::LocalSelection
+ * Purpose: Gives control to SALOME_Prs object, so that
+ * it could perform double dispatch
+ */
+//===========================================================
+void SALOME_View::LocalSelection( const SALOME_Prs* prs, const int mode )
+{
+ prs->LocalSelectionIn( this, mode );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Display
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::Display( const SALOME_OCCPrs* )
+{
+ MESSAGE( "SALOME_View::Display( const SALOME_OCCPrs& ) called! Probably, presentation is being displayed in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Display
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::Display( const SALOME_VTKPrs* )
+{
+ MESSAGE( "SALOME_View::Display( const SALOME_VTKPrs& ) called! Probably, presentation is being displayed in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Display
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::Display( const SALOME_Prs2d* )
+{
+ MESSAGE( "SALOME_View::Display( const SALOME_Prs2d& ) called! Probably, presentation is being displayed in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Erase
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::Erase( const SALOME_OCCPrs*, const bool )
+{
+ MESSAGE( "SALOME_View::Erase( const SALOME_OCCPrs& ) called! Probably, presentation is being erased in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Erase
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::Erase( const SALOME_VTKPrs*, const bool )
+{
+ MESSAGE( "SALOME_View::Erase( const SALOME_VTKPrs& ) called! Probably, presentation is being erased in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::Erase
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::Erase( const SALOME_Prs2d*, const bool )
+{
+ MESSAGE( "SALOME_View::Erase( const SALOME_Prs2d& ) called! Probably, presentation is being erased in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::LocalSelection
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::LocalSelection( const SALOME_OCCPrs*, const int )
+{
+ MESSAGE( "SALOME_View::LocalSelection( const SALOME_OCCPrs* ) called! \
+ Probably, selection is being activated in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::LocalSelection
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::LocalSelection( const SALOME_VTKPrs*, const int )
+{
+ MESSAGE( "SALOME_View::LocalSelection( const SALOME_VTKPrs* ) called! \
+ Probably, selection is being activated in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::LocalSelection
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::LocalSelection( const SALOME_Prs2d*, const int )
+{
+ MESSAGE( "SALOME_View::LocalSelection( const SALOME_Prs2d* ) called! \
+ Probably, selection is being activated in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_View::GlobalSelection
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_View::GlobalSelection( const bool ) const
+{
+ MESSAGE( "SALOME_View::GlobalSelection() called! \
+ Probably, selection is being activated in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Displayer::UpdatePrs
+ * Purpose: Gives control to SALOME_Prs object, so that
+ * it could perform double dispatch
+ */
+//===========================================================
+void SALOME_Displayer::UpdatePrs( SALOME_Prs* prs )
+{
+ prs->Update( this );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Displayer::Update
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_Displayer::Update( SALOME_OCCPrs* )
+{
+ MESSAGE( "SALOME_Displayer::Update( SALOME_OCCPrs* ) called! Probably, presentation is being updated in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Displayer::Update
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_Displayer::Update( SALOME_VTKPrs* )
+{
+ MESSAGE( "SALOME_Displayer::Update( SALOME_VTKPrs* ) called! Probably, presentation is being updated in uncompatible viewframe." );
+}
+
+//===========================================================
+/*!
+ * Function: SALOME_Displayer::Update
+ * Purpose: Virtual method, should be reimplemented in successors,
+ * by default issues a warning and does nothing.
+ */
+//===========================================================
+void SALOME_Displayer::Update( SALOME_Prs2d* )
+{
+ MESSAGE( "SALOME_Displayer::Update( SALOME_Prs2d* ) called! Probably, presentation is being updated in uncompatible viewframe." );
+}
+
--- /dev/null
+// SALOME OBJECT : implementation of interactive object visualization for OCC and VTK viewers
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : SALOME_Prs.h
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#ifndef SALOME_PRS_H
+#define SALOME_PRS_H
+
+class SALOME_View;
+class SALOME_Displayer;
+
+//===========================================================
+/*!
+ * Class: SALOME_Prs
+ * Description: Base class for SALOME graphic object wrappers - presentations.
+ * Presentations are temporary objects, so they can be created on the stack.
+ */
+//===========================================================
+
+class SALOME_Prs
+{
+public:
+ virtual ~SALOME_Prs() {}
+ // Destructor
+
+ virtual void DisplayIn( SALOME_View* ) const = 0;
+ // Key method for double dispatch of display operation
+
+ virtual void EraseIn( SALOME_View*, const bool = false ) const = 0;
+ // Key method for double dispatch of erase operation
+
+ virtual void Update( SALOME_Displayer* ) = 0;
+ // Key method for double dispatch of update operation
+
+ virtual bool IsNull() const = 0;
+ // Should return true, if this presentation contains a graphic object
+
+ virtual void LocalSelectionIn( SALOME_View*, const int ) const = 0;
+ // Key method for double dispatch of activation of subshapes selection
+};
+
+//===========================================================
+/*!
+ * Class: SALOME_OCCPrs
+ * Description: Base class for OpenCASCADE graphic object (AIS_InteractiveObject) wrappers.
+ * This intermediate class is necessary to avoid dependencies from OCC libs.
+ */
+//===========================================================
+
+class SALOME_OCCPrs : public SALOME_Prs
+{
+public:
+ virtual void DisplayIn( SALOME_View* ) const;
+ // It uses double dispatch in order to
+ // invoke Display() method corresponding to the actual type of presentation.
+
+ virtual void EraseIn( SALOME_View*, const bool = false ) const;
+ // It uses double dispatch in order to
+ // invoke Erase() method corresponding to the actual type of presentation.
+
+ virtual void Update( SALOME_Displayer* );
+ // It uses double dispatch in order to
+ // invoke Update() method corresponding to the actual type of presentation.
+
+ virtual void LocalSelectionIn( SALOME_View*, const int ) const;
+ // Key method for double dispatch of activation of subshapes selection
+};
+
+//===========================================================
+/*!
+ * Class: SALOME_VTKPrs
+ * Description: Base class for VTK graphic object (vtkActor) wrappers
+ * This intermediate class is necessary to avoid dependencies from VTK libs.
+ */
+//===========================================================
+
+class SALOME_VTKPrs : public SALOME_Prs
+{
+public:
+ virtual void DisplayIn( SALOME_View* ) const;
+ // It uses double dispatch in order to
+ // invoke Display() method corresponding to the actual type of presentation.
+
+ virtual void EraseIn( SALOME_View*, const bool = false ) const;
+ // It uses double dispatch in order to
+ // invoke Erase() method corresponding to the actual type of presentation.
+
+ virtual void Update( SALOME_Displayer* );
+ // It uses double dispatch in order to
+ // invoke Update() method corresponding to the actual type of presentation.
+
+ virtual void LocalSelectionIn( SALOME_View*, const int ) const;
+ // Key method for double dispatch of activation of subshapes selection
+};
+
+//===========================================================
+/*!
+ * Class: SALOME_Prs2d
+ * Description: Base class for Plot2d graphic object (Plot2d_Curve) wrappers.
+ */
+//===========================================================
+
+class SALOME_Prs2d : public SALOME_Prs
+{
+public:
+ virtual void DisplayIn( SALOME_View* ) const;
+ // It uses double dispatch in order to
+ // invoke Display() method corresponding to the actual type of presentation.
+
+ virtual void EraseIn( SALOME_View*, const bool = false ) const;
+ // It uses double dispatch in order to
+ // invoke Erase() method corresponding to the actual type of presentation.
+
+ virtual void Update( SALOME_Displayer* );
+ // It uses double dispatch in order to
+ // invoke Update() method corresponding to the actual type of presentation.
+
+ virtual void LocalSelectionIn( SALOME_View*, const int ) const;
+ // Key method for double dispatch of activation of subshapes selection
+};
+
+/////////////////////////////////////////////////////////////////////////
+// Base classes for object wrappers for any other visualization libraries
+// should be added here!
+/////////////////////////////////////////////////////////////////////////
+
+//===========================================================
+/*!
+ * Class: SALOME_View
+ * Description: Base class for SALOME views (or view frames)
+ */
+//===========================================================
+
+class SALOME_View
+{
+public:
+ virtual ~SALOME_View() {}
+ // Destructor
+
+ void Display( const SALOME_Prs* );
+ // This Display() method should be called to display given presentation
+ // created anywhere by anybody. It simply passes control to SALOME_Prs object
+ // so that it could perform double dispatch.
+ void Erase( const SALOME_Prs*, const bool = false );
+ // This Erase() method should be called to erase given presentation
+ // created anywhere by anybody. It simply passes control to SALOME_Prs object
+ // so that it could perform double dispatch.
+
+ void LocalSelection( const SALOME_Prs*, const int );
+ // This LocalSelection() method should be called to activate sub-shapes selection
+ // created anywhere by anybody. It simply passes control to SALOME_Prs object
+ // so that it could perform double dispatch.
+
+ // Interface for derived views
+
+ // Display() methods for ALL kinds of presentation should appear here
+ virtual void Display( const SALOME_OCCPrs* );
+ virtual void Display( const SALOME_VTKPrs* );
+ virtual void Display( const SALOME_Prs2d* );
+ // Add new Display() methods here...
+
+ // Erase() methods for ALL kinds of presentation should appear here
+ virtual void Erase( const SALOME_OCCPrs*, const bool = false );
+ virtual void Erase( const SALOME_VTKPrs*, const bool = false );
+ virtual void Erase( const SALOME_Prs2d*, const bool = false );
+ // Add new Erase() methods here...
+
+ // LocalSelection() methods for ALL kinds of presentation should appear here
+ virtual void LocalSelection( const SALOME_OCCPrs*, const int );
+ virtual void LocalSelection( const SALOME_VTKPrs*, const int );
+ virtual void LocalSelection( const SALOME_Prs2d* , const int );
+
+ virtual void GlobalSelection( const bool = false ) const;
+ // Deactivates selection of sub-shapes (must be redefined with OCC viewer)
+
+ // Creates empty presenation of corresponding type
+ virtual SALOME_Prs* CreatePrs( const char* entry = 0 ) { return 0; }
+
+ // Axiluary methods called before and after displaying of objects
+ virtual void BeforeDisplay( SALOME_Displayer* d ) {}
+ virtual void AfterDisplay ( SALOME_Displayer* d ) {}
+};
+
+//===========================================================
+/*!
+ * Classes: SALOME_Displayer
+ * Description: These classes are used to specify type of view
+ * VTK, OCC or Plot2d
+ */
+//===========================================================
+
+class SALOME_OCCViewType {};
+class SALOME_VTKViewType {};
+class SALOME_Plot2dViewType {};
+
+//===========================================================
+/*!
+ * Class: SALOME_Displayer
+ * Description: Base class for SALOME displayers
+ */
+//===========================================================
+
+class SALOME_Displayer
+{
+public:
+ virtual ~SALOME_Displayer() {}
+ // Destructor
+
+ void UpdatePrs( SALOME_Prs* );
+ // This Update() method should be called to update given presentation
+ // created anywhere by anybody. It simply passes control to SALOME_Prs object
+ // so that it could perform double dispatch.
+
+ // Interface for derived displayers
+
+ // Update() methods for ALL kinds of presentation should appear here
+ virtual void Update( SALOME_OCCPrs* );
+ virtual void Update( SALOME_VTKPrs* );
+ virtual void Update( SALOME_Prs2d* );
+ // Add new Update() methods here...
+
+ // Axiluary methods called before and after displaying of objects
+ virtual void BeforeDisplay( SALOME_View*, const SALOME_OCCViewType& ) {};
+ virtual void AfterDisplay ( SALOME_View*, const SALOME_OCCViewType& ) {};
+ virtual void BeforeDisplay( SALOME_View*, const SALOME_VTKViewType& ) {};
+ virtual void AfterDisplay ( SALOME_View*, const SALOME_VTKViewType& ) {};
+ virtual void BeforeDisplay( SALOME_View*, const SALOME_Plot2dViewType& ) {};
+ virtual void AfterDisplay ( SALOME_View*, const SALOME_Plot2dViewType& ) {};
+};
+
+#endif
+
--- /dev/null
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+
+
+#include <stdexcept>
+#include <qapplication.h>
+
+#include "CASCatch_SignalsHandler.h" // CAREFUL ! position of this file is critic : see Lucien PIGNOLONI / OCC
+
+
+extern "C" int HandleSignals(QApplication *theQApplication)
+{
+ CASCatch_SignalsHandler aSignalsHandler;
+ int aRet = -1;
+ try {
+ aRet = theQApplication->exec();
+ }catch(Standard_Failure){
+ Handle(Standard_Failure) aFail = Standard_Failure::Caught();
+ throw std::runtime_error(aFail->GetMessageString());
+ }
+ return aRet;
+}
--- /dev/null
+// KERNEL Utils : common utils for KERNEL
+// Copyright (C) 2003 CEA
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+
+
+#include <stdexcept>
+#include <stdio.h>
+#include <signal.h>
+
+#include "Utils_SignalsHandler.h"
+
+
+//============================================================================
+//function : Handler
+//purpose : univisal handler for signals
+//============================================================================
+static void Handler(int theSigId)
+{
+ char aMessage[256] = "";
+ sprintf(aMessage,"Signal with ID = %d was cautch!",theSigId);
+ throw std::runtime_error(aMessage);
+}
+
+
+//=======================================================================
+//function : SetSigHandler
+//purpose : Redefine signal handlers. If the handler of the signal is
+// set as SIG_IGN. That's why the shells often ignore some
+// signal when starting child processes. We keep it.
+//=======================================================================
+static void SetSignalHandler(Utils_SignalsHandler::TSigHandlerCont& theSigHandlerCont,
+ int theSigId)
+{
+ TSigHandler anOldHandler = signal(theSigId,&Handler);
+ if(anOldHandler == SIG_IGN)
+ signal(theSigId,SIG_IGN);
+ theSigHandlerCont[theSigId] = anOldHandler;
+}
+
+static TSigHandler StoreSignalHandler(Utils_SignalsHandler::TSigHandlerCont& theSigHandlerCont,
+ int theSigId)
+{
+ TSigHandler anOldHandler = signal(theSigId,&Handler);
+ signal(theSigId,anOldHandler);
+ if(anOldHandler == SIG_IGN)
+ signal(theSigId,SIG_IGN);
+ theSigHandlerCont[theSigId] = anOldHandler;
+ return anOldHandler;
+}
+
+static void RestoreSigHandler(TSigHandler theSigHandler,
+ int theSigId)
+{
+ signal(theSigId,theSigHandler);
+}
+
+
+//=======================================================================
+//function : Utils_SignalsHandler
+//purpose : Constructor
+//=======================================================================
+Utils_SignalsHandler::Utils_SignalsHandler()
+{
+ StoreSignalHandler(mySigHandlerCont,SIGHUP); // floating point exception
+ StoreSignalHandler(mySigHandlerCont,SIGFPE); // floating point exception
+
+ StoreSignalHandler(mySigHandlerCont,SIGINT); // interrupt
+ StoreSignalHandler(mySigHandlerCont,SIGQUIT); // quit
+ StoreSignalHandler(mySigHandlerCont,SIGBUS); // bus error
+ StoreSignalHandler(mySigHandlerCont,SIGILL); // illegal instruction
+ StoreSignalHandler(mySigHandlerCont,SIGTERM); // termination
+ StoreSignalHandler(mySigHandlerCont,SIGSEGV); // segmentation
+ //StoreSignalHandler(mySigHandlerCont,SIGABRT); // abort (ANSI).
+ StoreSignalHandler(mySigHandlerCont,SIGSTKFLT); // stack fault.
+}
+
+
+//=======================================================================
+//function : Utils_SignalsHandler
+//purpose : destructor
+//=======================================================================
+Utils_SignalsHandler::~Utils_SignalsHandler()
+{
+ TSigHandlerCont::iterator anIter = mySigHandlerCont.begin();
+ TSigHandlerCont::iterator anIterEnd = mySigHandlerCont.end();
+ for(; anIter != anIterEnd; anIter++)
+ RestoreSigHandler(anIter->second,anIter->first);
+}
+
+
+//=======================================================================
+//function : SetSigHandler
+//purpose : sets new handler for pointed signal
+//=======================================================================
+TSigHandler Utils_SignalsHandler::SetSigHandler(int theSigId,
+ TSigHandler theSigHandler)
+{
+ TSigHandler anOldHandler = signal(theSigId,theSigHandler);
+ if(anOldHandler == SIG_IGN)
+ signal(theSigId,SIG_IGN);
+ mySigHandlerCont[theSigId] = anOldHandler;
+ return anOldHandler;
+}
--- /dev/null
+// KERNEL Utils : common utils for KERNEL
+// Copyright (C) 2003 CEA
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+
+#ifndef _UTILS_SIGNALSHANDLER_H_
+#define _UTILS_SIGNALSHANDLER_H_
+
+
+#include <map>
+typedef void (*TSigHandler)(int);
+
+
+class Utils_SignalsHandler{
+ public:
+ Utils_SignalsHandler();
+ ~Utils_SignalsHandler();
+
+ TSigHandler GetSigHandler(int theSigId);
+ TSigHandler SetSigHandler(int theSigId, TSigHandler theSigHandler);
+ typedef std::map<int,TSigHandler> TSigHandlerCont;
+
+ private:
+ TSigHandlerCont mySigHandlerCont;
+};
+
+
+class Utils_CASSignalsHandler: private Utils_SignalsHandler{
+ public:
+ Utils_CASSignalsHandler();
+};
+
+
+#endif
--- /dev/null
+// SALOME OBJECT : kernel of SALOME component
+//
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : SALOME_GeometryFilter.cxx
+// Author : Michael ZORIN
+// Module : SALOME
+// $Header$
+
+#include "SALOME_ShrinkFilter.h"
+
+#include <vtkCell.h>
+#include <vtkCellData.h>
+#include <vtkIdList.h>
+#include <vtkObjectFactory.h>
+#include <vtkPointData.h>
+#include <vtkUnstructuredGrid.h>
+
+#ifdef _DEBUG_
+static int MYDEBUG = 0;
+static int MYDEBUGWITHFILES = 0;
+#else
+static int MYDEBUG = 0;
+static int MYDEBUGWITHFILES = 0;
+#endif
+
+vtkCxxRevisionMacro(SALOME_ShrinkFilter, "$Revision$");
+vtkStandardNewMacro(SALOME_ShrinkFilter);
+
+
+SALOME_ShrinkFilter::SALOME_ShrinkFilter():
+ myStoreMapping(0)
+{}
+
+
+SALOME_ShrinkFilter::~SALOME_ShrinkFilter()
+{}
+
+
+void SALOME_ShrinkFilter::Execute()
+{
+ vtkPoints *newPts;
+ int i, j, numIds, abort=0;
+ vtkIdType cellId, numCells, numPts;
+ vtkIdType oldId, newId;
+ float center[3], *p, pt[3];
+ vtkPointData *pd, *outPD;;
+ vtkIdList *ptIds, *newPtIds;
+ vtkDataSet *input= this->GetInput();
+ vtkUnstructuredGrid *output = this->GetOutput();
+ vtkIdType tenth;
+ float decimal;
+
+ vtkDebugMacro(<<"Shrinking cells");
+
+ numCells=input->GetNumberOfCells();
+ numPts = input->GetNumberOfPoints();
+ if (numCells < 1 || numPts < 1)
+ {
+ vtkErrorMacro(<<"No data to shrink!");
+ return;
+ }
+
+ ptIds = vtkIdList::New();
+ ptIds->Allocate(VTK_CELL_SIZE);
+ newPtIds = vtkIdList::New();
+ newPtIds->Allocate(VTK_CELL_SIZE);
+
+ output->Allocate(numCells);
+ newPts = vtkPoints::New();
+ newPts->Allocate(numPts*8,numPts);
+ pd = input->GetPointData();
+ outPD = output->GetPointData();
+ outPD->CopyAllocate(pd,numPts*8,numPts);
+
+ // Traverse all cells, obtaining node coordinates. Compute "center" of cell,
+ // then create new vertices shrunk towards center.
+ //
+ tenth = numCells/10 + 1;
+ decimal = 0.0;
+ if(myStoreMapping){
+ myVTK2ObjIds.clear();
+ myVTK2ObjIds.reserve(numCells);
+ }
+
+ for (cellId=0; cellId < numCells && !abort; cellId++)
+ {
+ input->GetCellPoints(cellId, ptIds);
+ numIds = ptIds->GetNumberOfIds();
+
+ //abort/progress methods
+ if (cellId % tenth == 0)
+ {
+ decimal += 0.1;
+ this->UpdateProgress (decimal);
+ abort = this->GetAbortExecute();
+ }
+
+ // get the center of the cell
+ center[0] = center[1] = center[2] = 0.0;
+ for (i=0; i < numIds; i++)
+ {
+ p = input->GetPoint(ptIds->GetId(i));
+ for (j=0; j < 3; j++)
+ {
+ center[j] += p[j];
+ }
+ }
+ for (j=0; j<3; j++)
+ {
+ center[j] /= numIds;
+ }
+
+ // Create new points and cells
+ newPtIds->Reset();
+ for (i=0; i < numIds; i++)
+ {
+ p = input->GetPoint(ptIds->GetId(i));
+ for (j=0; j < 3; j++)
+ {
+ pt[j] = center[j] + this->ShrinkFactor*(p[j] - center[j]);
+ }
+
+ oldId = ptIds->GetId(i);
+ newId = newPts->InsertNextPoint(pt);
+ if(myStoreMapping)
+ myVTK2ObjIds.push_back(oldId);
+ newPtIds->InsertId(i,newId);
+
+ outPD->CopyData(pd, oldId, newId);
+ }
+ output->InsertNextCell(input->GetCellType(cellId), newPtIds);
+ }//for all cells
+
+ // Update ourselves and release memory
+ //
+ output->GetCellData()->PassData(input->GetCellData());
+
+ output->SetPoints(newPts);
+ output->Squeeze();
+
+ ptIds->Delete();
+ newPtIds->Delete();
+ newPts->Delete();
+}
+
+
+void SALOME_ShrinkFilter::SetStoreMapping(int theStoreMapping){
+ myStoreMapping = theStoreMapping;
+ this->Modified();
+}
+
+
+vtkIdType SALOME_ShrinkFilter::GetNodeObjId(int theVtkID){
+ if(myVTK2ObjIds.empty() || theVtkID > myVTK2ObjIds.size()) return -1;
+ return myVTK2ObjIds[theVtkID];
+}
--- /dev/null
+// SALOME OBJECT : kernel of SALOME component
+//
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : SALOME_GeometryFilter.h
+// Author : Michael ZORIN
+// Module : SALOME
+// $Header$
+
+
+#ifndef __SALOME_ShrinkFilter_h
+#define __SALOME_ShrinkFilter_h
+
+#include <vtkShrinkFilter.h>
+#include <vector>
+
+class SALOME_ShrinkFilter : public vtkShrinkFilter
+{
+public:
+ static SALOME_ShrinkFilter *New();
+ vtkTypeRevisionMacro(SALOME_ShrinkFilter, vtkShrinkFilter);
+
+ void SetStoreMapping(int theStoreMapping);
+ int GetStoreMapping(){ return myStoreMapping;}
+
+ virtual vtkIdType GetNodeObjId(int theVtkID);
+ virtual vtkIdType GetElemObjId(int theVtkID) { return theVtkID;}
+
+protected:
+ SALOME_ShrinkFilter();
+ ~SALOME_ShrinkFilter();
+
+ void Execute();
+ void UnstructuredGridExecute();
+
+private:
+ int myStoreMapping;
+ typedef std::vector<vtkIdType> TVectorId;
+ TVectorId myVTK2ObjIds;
+};
+
+#endif
--- /dev/null
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+
+#include "VTKViewer_Actor.h"
+
+#include "SALOME_PassThroughFilter.h"
+
+// VTK Includes
+#include <vtkObjectFactory.h>
+#include <vtkUnstructuredGrid.h>
+#include <vtkDataSetMapper.h>
+#include <vtkRenderer.h>
+
+#include <vtkCell.h>
+#include <vtkPolyData.h>
+#include <vtkShrinkFilter.h>
+
+#include "utilities.h"
+
+using namespace std;
+
+#ifdef _DEBUG_
+static int MYDEBUG = 0;
+#else
+static int MYDEBUG = 0;
+#endif
+
+
+static void CopyPoints(vtkUnstructuredGrid* theGrid, vtkDataSet *theSourceDataSet){
+ vtkPoints *aPoints = vtkPoints::New();
+ vtkIdType iEnd = theSourceDataSet->GetNumberOfPoints();
+ aPoints->SetNumberOfPoints(iEnd);
+ for(vtkIdType i = 0; i < iEnd; i++){
+ aPoints->SetPoint(i,theSourceDataSet->GetPoint(i));
+ }
+ theGrid->SetPoints(aPoints);
+ aPoints->Delete();
+}
+
+
+//=======================================================================
+
+vtkStandardNewMacro(VTKViewer_Actor);
+
+VTKViewer_Actor::VTKViewer_Actor()
+{
+ myRenderer = NULL;
+ myIsInfinite = true;
+
+ Visibility = Pickable = false;
+
+ myUnstructuredGrid = vtkUnstructuredGrid::New();
+ myUnstructuredGrid->Allocate();
+
+ myIsShrunk = false;
+ myIsShrinkable = true;
+ myShrinkFilter = vtkShrinkFilter::New();
+
+ myMapper = vtkDataSetMapper::New();
+
+ myMapper->SetInput(myUnstructuredGrid);
+ Superclass::InitPipeLine(myMapper);
+
+ SetResolveCoincidentTopology(false);
+}
+
+
+void VTKViewer_Actor::SetShrinkFactor(float theValue){
+ myShrinkFilter->SetShrinkFactor(theValue);
+ Modified();
+}
+
+
+void VTKViewer_Actor::SetShrink()
+{
+ if ( !myIsShrinkable ) return;
+ if ( vtkDataSet* aDataSet = myPassFilter[0]->GetOutput() )
+ {
+ myShrinkFilter->SetInput( aDataSet );
+ myPassFilter[1]->SetInput( myShrinkFilter->GetOutput() );
+ myIsShrunk = true;
+ }
+}
+
+void VTKViewer_Actor::UnShrink()
+{
+ if ( !myIsShrunk ) return;
+ if ( vtkDataSet* aDataSet = myPassFilter[0]->GetOutput() )
+ {
+ myPassFilter[1]->SetInput( aDataSet );
+ myPassFilter[1]->Modified();
+ myIsShrunk = false;
+ Modified();
+ }
+}
+
+
+//----------------------------------------------------------------------------
+VTKViewer_Actor::~VTKViewer_Actor()
+{
+ if(MYDEBUG) INFOS("VTKViewer_Actor::~VTKViewer_Actor()");
+
+ myMapper->RemoveAllInputs();
+ myMapper->Delete();
+
+ myShrinkFilter->UnRegisterAllOutputs();
+ myShrinkFilter->Delete();
+
+ myUnstructuredGrid->Delete();
+}
+
+
+//----------------------------------------------------------------------------
+void VTKViewer_Actor::MapCells(SALOME_Actor* theMapActor,
+ const TColStd_IndexedMapOfInteger& theMapIndex)
+{
+ myUnstructuredGrid->Reset();
+
+ vtkDataSet *aSourceDataSet = theMapActor->GetInput();
+ CopyPoints(myUnstructuredGrid,aSourceDataSet);
+
+ int aNbOfParts = theMapIndex.Extent();
+ for(int ind = 1; ind <= aNbOfParts; ind++){
+ int aPartId = theMapIndex( ind );
+ vtkCell* aCell = theMapActor->GetElemCell(aPartId);
+ myUnstructuredGrid->InsertNextCell(aCell->GetCellType(),aCell->GetPointIds());
+ //for (int i = 0, iEnd = aCell->GetNumberOfEdges(); i < iEnd; i++){
+ // vtkCell* anEdgeCell = aCell->GetEdge(i);
+ // myUnstructuredGrid->InsertNextCell(VTK_LINE,anEdgeCell->GetPointIds());
+ //}
+ }
+
+ UnShrink();
+ if(theMapActor->IsShrunk()){
+ SetShrinkFactor(theMapActor->GetShrinkFactor());
+ SetShrink();
+ }
+}
+
+
+//----------------------------------------------------------------------------
+void VTKViewer_Actor::MapPoints(SALOME_Actor* theMapActor,
+ const TColStd_IndexedMapOfInteger& theMapIndex)
+{
+ myUnstructuredGrid->Reset();
+ if(int aNbOfParts = theMapIndex.Extent()){
+ vtkPoints *aPoints = vtkPoints::New();
+ aPoints->SetNumberOfPoints(aNbOfParts);
+ for(int i = 0; i < aNbOfParts; i++){
+ int aPartId = theMapIndex( i+1 );
+ float* aCoord = theMapActor->GetNodeCoord(aPartId);
+ aPoints->SetPoint(i,aCoord);
+ myUnstructuredGrid->InsertNextCell(VTK_VERTEX,1,&i);
+ }
+ myUnstructuredGrid->SetPoints(aPoints);
+ aPoints->Delete();
+ }
+
+ UnShrink();
+}
+
+
+//----------------------------------------------------------------------------
+void VTKViewer_Actor::MapEdge(SALOME_Actor* theMapActor,
+ const TColStd_IndexedMapOfInteger& theMapIndex)
+{
+ myUnstructuredGrid->Reset();
+
+ vtkDataSet *aSourceDataSet = theMapActor->GetInput();
+ CopyPoints(myUnstructuredGrid,aSourceDataSet);
+
+ int iEnd = theMapIndex.Extent();
+ int aCellId = -1, aCellCounter = 0;
+ for(int i = 1; i <= iEnd; i++){
+ int anId = theMapIndex( i );
+ if(anId > 0) {
+ aCellCounter++;
+ aCellId = anId;
+ }
+ }
+
+ if(aCellCounter == 1){
+ vtkCell* aCell = theMapActor->GetElemCell(aCellId);
+ if(aCell->GetCellType() <= VTK_LINE){
+ myUnstructuredGrid->InsertNextCell(aCell->GetCellType(),aCell->GetPointIds());
+ }else{
+ int aNbOfParts = aCell->GetNumberOfEdges();
+ for(int i = 1; i <= iEnd; i++){
+ int aPartId = theMapIndex(i);
+ if( aPartId < 0){
+ aPartId = -aPartId-1;
+ if(0 > aPartId || aPartId >= aNbOfParts) break;
+ vtkCell* anEdgeCell = aCell->GetEdge(aPartId);
+ myUnstructuredGrid->InsertNextCell(VTK_LINE,anEdgeCell->GetPointIds());
+ }
+ }
+ }
+ }else{
+ int aNbOfParts = aSourceDataSet->GetNumberOfCells();
+ for(int i = 1; i <= iEnd; i++){
+ int aPartId = theMapIndex( i );
+ if(aPartId > 0){
+ if(aPartId >= aNbOfParts) break;
+ vtkCell* aCell = aSourceDataSet->GetCell(aPartId);
+ myUnstructuredGrid->InsertNextCell(aCell->GetCellType(),aCell->GetPointIds());
+ }
+ }
+ }
+
+ UnShrink();
+ if(theMapActor->IsShrunk()){
+ SetShrinkFactor(theMapActor->GetShrinkFactor());
+ SetShrink();
+ }
+}
+
+//----------------------------------------------------------------------------
--- /dev/null
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+
+#ifndef VTKVIEWER_ACTOR_H
+#define VTKVIEWER_ACTOR_H
+
+#include <TColStd_IndexedMapOfInteger.hxx>
+
+class vtkRenderer;
+class vtkShrinkFilter;
+class vtkDataSetMapper;
+class vtkUnstructuredGrid;
+
+#include "SALOME_Actor.h"
+
+class VTKViewer_Actor : public SALOME_Actor {
+ public:
+ vtkTypeMacro(VTKViewer_Actor,SALOME_Actor);
+ static VTKViewer_Actor* New();
+ virtual ~VTKViewer_Actor();
+
+ void SetShrinkFactor(float value);
+ virtual void SetShrink();
+ virtual void UnShrink();
+
+ void MapCells(SALOME_Actor* theMapActor,
+ const TColStd_IndexedMapOfInteger& theMapIndex);
+
+ void MapPoints(SALOME_Actor* theMapActor,
+ const TColStd_IndexedMapOfInteger& theMapIndex);
+
+ void MapEdge(SALOME_Actor* theMapActor,
+ const TColStd_IndexedMapOfInteger& theMapIndex);
+
+ protected:
+ vtkUnstructuredGrid* myUnstructuredGrid;
+ vtkDataSetMapper* myMapper;
+
+ vtkRenderer* myRenderer;
+
+ vtkShrinkFilter* myShrinkFilter;
+ bool myIsShrinkable;
+ bool myIsShrunk;
+
+ VTKViewer_Actor();
+};
+
+#endif
--- /dev/null
+// SALOME VTKViewer : build VTK viewer into Salome desktop
+//
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : VTKViewer_ViewFrame.h
+// Author : Nicolas REJNERI
+// Module : SALOME
+// $Header$
+
+#ifndef VTKViewer_Algorithm_H
+#define VTKViewer_Algorithm_H
+
+class vtkActor;
+class vtkActorCollection;
+
+namespace SALOME{
+ namespace VTK{
+
+ template<typename TActor, typename TFunction>
+ TFunction ForEach(vtkActorCollection *theCollection, TFunction theFun)
+ {
+ if(theCollection){
+ theCollection->InitTraversal();
+ while(vtkActor *anAct = theCollection->GetNextActor())
+ if(TActor *anActor = dynamic_cast<TActor*>(anAct))
+ theFun(anActor);
+ }
+ return theFun;
+ }
+
+
+ template<typename TActor, typename TPredicate, typename TFunction>
+ TFunction ForEachIf(vtkActorCollection *theCollection,
+ TPredicate thePredicate,
+ TFunction theFun)
+ {
+ if(theCollection){
+ theCollection->InitTraversal();
+ while(vtkActor *anAct = theCollection->GetNextActor())
+ if(TActor *anActor = dynamic_cast<TActor*>(anAct))
+ if(thePredicate(anActor))
+ theFun(anActor);
+ }
+ return theFun;
+ }
+
+
+ template<typename TActor, typename TPredicate>
+ TActor* Find(vtkActorCollection *theCollection, TPredicate thePredicate)
+ {
+ if(theCollection){
+ theCollection->InitTraversal();
+ while(vtkActor *anAct = theCollection->GetNextActor())
+ if(TActor *anActor = dynamic_cast<TActor*>(anAct))
+ if(thePredicate(anActor))
+ return anActor;
+ }
+ return NULL;
+ }
+
+ }
+}
+
+#endif
--- /dev/null
+// SALOME VTKViewer : build VTK viewer into Salome desktop
+//
+// Copyright (C) 2003 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.opencascade.org/SALOME/ or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : VTKViewer_ViewFrame.h
+// Author : Nicolas REJNERI
+// Module : SALOME
+// $Header$
+
+#ifndef VTKViewer_Functor_H
+#define VTKViewer_Functor_H
+
+#include <functional>
+
+#include <string>
+#include "SALOME_InteractiveObject.hxx"
+
+namespace SALOME{
+ namespace VTK{
+
+
+ template<class TActor> struct TIsSameEntry
+ {
+ std::string myEntry;
+ TIsSameEntry(const char* theEntry): myEntry(theEntry){}
+ bool operator()(TActor* theActor){
+ if(theActor->hasIO()){
+ Handle(SALOME_InteractiveObject) anIO = theActor->getIO();
+ if(anIO->hasEntry())
+ return myEntry == anIO->getEntry();
+ }
+ return false;
+ }
+ };
+
+
+ template<class TActor> struct TIsSameIObject
+ {
+ Handle(SALOME_InteractiveObject) myIObject;
+ TIsSameIObject(const Handle(SALOME_InteractiveObject)& theIObject):
+ myIObject(theIObject)
+ {}
+ bool operator()(TActor* theActor){
+ if(theActor->hasIO()){
+ Handle(SALOME_InteractiveObject) anIO = theActor->getIO();
+ return myIObject->isSame(anIO);
+ }
+ return false;
+ }
+ };
+
+
+ template<class TActor, class TArg, class TStoreArg = TArg> struct TSetFunction
+ {
+ typedef void (TActor::* TAction)(TArg);
+ TAction myAction;
+ TStoreArg myArg;
+ TSetFunction(TAction theAction, TArg theArg):
+ myAction(theAction), myArg(theArg)
+ {}
+ void operator()(TActor* theActor){
+ (theActor->*myAction)(myArg);
+ }
+ };
+
+
+ template<class TActor, class TArg = int> struct TSetVisibility: TSetFunction<TActor,TArg>
+ {
+ TSetVisibility(TArg theArg):
+ TSetFunction<TActor,TArg>(&TActor::SetVisibility,theArg)
+ {}
+ };
+
+
+ }
+}
+
+
+#endif
--- /dev/null
+// SALOME VTKViewer : build VTK viewer into Salome desktop
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : VTKViewer_Prs.cxx
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#include "VTKViewer_Prs.h"
+
+//==========================================================
+/*!
+ * VTKViewer_Prs::VTKViewer_Prs
+ * Default constructor
+ */
+//==========================================================
+VTKViewer_Prs::VTKViewer_Prs() : myObjects( 0 )
+{
+}
+
+//==========================================================
+/*!
+ * VTKViewer_Prs::VTKViewer_Prs
+ * tandard constructora
+ */
+//==========================================================
+VTKViewer_Prs::VTKViewer_Prs( const vtkActor* obj )
+{
+ AddObject( obj );
+}
+
+//==========================================================
+/*!
+ * VTKViewer_Prs::~VTKViewer_Prs
+ * Destructor
+ */
+//==========================================================
+VTKViewer_Prs:: ~VTKViewer_Prs()
+{
+ if ( myObjects ) myObjects->Delete();
+}
+
+//==========================================================
+/*!
+ * VTKViewer_Prs::GetObjects
+ * Get actors list
+ */
+//==========================================================
+vtkActorCollection* VTKViewer_Prs::GetObjects() const
+{
+ return myObjects;
+}
+
+//==========================================================
+/*!
+ * VTKViewer_Prs::AddObject
+ * Add actor
+ */
+//==========================================================
+void VTKViewer_Prs::AddObject( const vtkActor* obj )
+{
+ if ( !myObjects)
+ myObjects = vtkActorCollection::New();
+ myObjects->AddItem( (vtkActor*)obj );
+}
+
+//==========================================================
+/*!
+ * VTKViewer_Prs::IsNull
+ * Return 0 if list of the actors is empty
+ * [ Reimplemented from SALOME_Prs ]
+ */
+//==========================================================
+bool VTKViewer_Prs::IsNull() const
+{
+ return !myObjects || myObjects->GetNumberOfItems() <= 0;
+}
--- /dev/null
+// SALOME VTKViewer : build VTK viewer into Salome desktop
+//
+// Copyright (C) 2004 OPEN CASCADE, EADS/CCR, LIP6, CEA/DEN,
+// CEDRAT, EDF R&D, LEG, PRINCIPIA R&D, BUREAU VERITAS
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+//
+// See http://www.salome-platform.org or email : webmaster.salome@opencascade.org
+//
+//
+//
+// File : VTKViewer_Prs.h
+// Author : Sergey ANIKIN
+// Module : SALOME
+// $Header$
+
+#ifndef VTKVIEWER_PRS_H
+#define VTKVIEWER_PRS_H
+
+#include "SALOME_Prs.h"
+
+#include <vtkActorCollection.h>
+
+class VTKViewer_Prs : public SALOME_VTKPrs
+{
+public:
+ VTKViewer_Prs();
+ // Default constructor
+ VTKViewer_Prs( const vtkActor* obj );
+ // Standard constructor
+ ~VTKViewer_Prs();
+ // Destructor
+
+ vtkActorCollection* GetObjects() const;
+ // Get actors list
+ void AddObject( const vtkActor* obj );
+ // Add actor
+
+ bool IsNull() const;
+ // Reimplemented from SALOME_Prs
+
+private:
+ vtkActorCollection* myObjects; // list of actors
+};
+
+#endif