Salome HOME
Merge from BR_V5_DEV 17Feb09
[samples/sierpinsky.git] / src / Sierpinsky / SIERPINSKY_Gen_i.cxx
1 //  Copyright (C) 2005-2008  OPEN CASCADE
2 //
3 //  This library is free software; you can redistribute it and/or
4 //  modify it under the terms of the GNU Lesser General Public
5 //  License as published by the Free Software Foundation; either
6 //  version 2.1 of the License.
7 //
8 //  This library is distributed in the hope that it will be useful,
9 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
10 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
11 //  Lesser General Public License for more details.
12 //
13 //  You should have received a copy of the GNU Lesser General Public
14 //  License along with this library; if not, write to the Free Software
15 //  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 //
17 //  See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com
18 //
19 ///////////////////////////////////////////////////////////
20 // File    : SIERPINSKY_Gen_i.cxx
21 // Author  : Vadim SANDLER (OCN)
22 // Created : 13/07/05
23 ///////////////////////////////////////////////////////////
24 //
25 #include "SIERPINSKY_Gen_i.hxx"
26 #include <MED_Factory.hxx>
27 #include <gd.h>
28
29 using namespace MED;
30
31 /*!
32  * Engine factory
33  */
34 extern "C"
35 {
36   PortableServer::ObjectId * SIERPINSKYEngine_factory( CORBA::ORB_ptr            orb,
37                                                        PortableServer::POA_ptr   poa, 
38                                                        PortableServer::ObjectId* contId,
39                                                        const char*               instanceName,
40                                                        const char*               interfaceName )
41 {
42   SIERPINSKY_Gen_i* anEngine = new SIERPINSKY_Gen_i( orb, poa, contId, instanceName, interfaceName );
43   return anEngine->getId() ;
44 }
45 }
46
47 /*!
48  * Default constructor
49  */
50 SIERPINSKY_Gen_i::SIERPINSKY_Gen_i()
51 {
52 }
53
54 /*!
55  * Constructor
56  */
57 SIERPINSKY_Gen_i::SIERPINSKY_Gen_i( CORBA::ORB_ptr            orb,
58                                     PortableServer::POA_ptr   poa,
59                                     PortableServer::ObjectId* contId, 
60                                     const char*               instanceName, 
61                                     const char*               interfaceName ) 
62 : Engines_Component_i( orb, poa, contId, instanceName, interfaceName ) 
63 {
64   // activate servant
65   _thisObj = this;
66   _id = poa->activate_object(_thisObj);
67   // set default values
68   Reset();
69 }
70
71 /*!
72  * Destructor
73  */
74 SIERPINSKY_Gen_i::~SIERPINSKY_Gen_i()
75 {
76   myPoints.clear();
77 }
78   
79 /*!
80  * Initializes engine with three reference points
81  */
82 void SIERPINSKY_Gen_i::Init( CORBA::Double theX1, CORBA::Double theY1, 
83                              CORBA::Double theX2, CORBA::Double theY2, 
84                              CORBA::Double theX3, CORBA::Double theY3 )
85 {
86   myRefPoints[0] = MyPoint( theX1, theY1 );
87   myRefPoints[1] = MyPoint( theX2, theY2 );
88   myRefPoints[2] = MyPoint( theX3, theY3 );
89   myPoints.clear();
90 }
91   
92 /*!
93  * Initializes engine with three default reference points: (0.5, 1), (0, 0), (1, 0)
94  */
95 void SIERPINSKY_Gen_i::Reset()
96 {
97   myRefPoints[0] = MyPoint( 0.5, 1.0 );
98   myRefPoints[1] = MyPoint( 0.0, 0.0 );
99   myRefPoints[2] = MyPoint( 1.0, 0.0 );
100   myPoints.clear();
101 }
102   
103 /*!
104  * Generates next iteration point
105  */
106 void SIERPINSKY_Gen_i::NextPoint( CORBA::Double  theX,     CORBA::Double  theY, 
107                                   CORBA::Long    theIter, 
108                                   CORBA::Double& theNextX, CORBA::Double& theNextY )
109 {
110   double x = theIter < 1 || theIter > 3 ? theX : ( theX + myRefPoints[ theIter-1 ].myX ) / 2;
111   double y = theIter < 1 || theIter > 3 ? theY : ( theY + myRefPoints[ theIter-1 ].myY ) / 2;
112   myPoints.push_back( MyPoint( x, y ) );
113   theNextX = x;
114   theNextY = y;
115 }
116   
117 /*!
118  * Exports data to the JPEG image
119  */
120 CORBA::Boolean SIERPINSKY_Gen_i::ExportToJPEG( const char* theFileName, CORBA::Long theSize )
121 {
122   if ( theSize <= 0 ) return false;
123
124   // open file
125   FILE* fileDescriptor = fopen( theFileName, "wb" );
126   if ( !fileDescriptor ) return false;
127
128   // create an image
129   gdImagePtr image = gdImageCreate( theSize, theSize );
130   int white = gdImageColorAllocate( image, 255, 255, 255 );
131   int black = gdImageColorAllocate( image,   0,   0,   0 );
132
133   gdImageRectangle( image, 0, 0, theSize-1, theSize-1, white );
134
135   // draw points
136   std::list<MyPoint>::const_iterator iter;
137   for ( iter = myPoints.begin(); iter != myPoints.end(); ++iter ) {
138     gdImageSetPixel( image, (int)( (*iter).myX * theSize ), theSize - (int)( (*iter).myY * theSize ), black );
139   }
140
141   // export jpeg image
142   gdImageJpeg( image, fileDescriptor, 95 );
143   fclose( fileDescriptor );
144   gdImageDestroy( image );
145   
146   return true;
147 }
148   
149 /*!
150  * Exports data to the MED file
151  */
152 CORBA::Boolean SIERPINSKY_Gen_i::ExportToMED( const char* theFileName, CORBA::Double theSize )
153 {
154   TErr anError;
155   
156   // if file already exists - remove it (MED cannot overwrite files correctly)
157   FILE* aFile = fopen( theFileName, "rb" );
158   if ( aFile ) {
159     fclose( aFile );
160     if ( remove( theFileName ) ) return false; // can't remove file
161   }
162   
163   // create MED 2.2 file
164   PWrapper aMed = CrWrapper( theFileName, MED::eV2_2 );
165
166   // create 2D mesh
167   PMeshInfo aMesh = aMed->CrMeshInfo( 2, "Sierpinsky" );
168   aMed->SetMeshInfo( aMesh, &anError );
169   if ( anError < 0 ) return false;
170
171   // create nodes
172   TFloatVector nodes;
173   TIntVector   connect;
174   std::list<MyPoint>::const_iterator iter;
175   int ind = 1;
176   for ( iter = myPoints.begin(); iter != myPoints.end(); ++iter ) {
177     nodes.push_back( (*iter).myX * theSize );
178     nodes.push_back( (*iter).myY * theSize );
179     connect.push_back( ind++ );
180   }
181   PNodeInfo aNodes = aMed->CrNodeInfo( aMesh, nodes, MED::eFULL_INTERLACE, MED::eCART, TStringVector(2), TStringVector(2), TIntVector( myPoints.size() ), TIntVector() );
182   aMed->SetNodeInfo( aNodes, &anError );
183   if ( anError < 0 ) return false;
184
185   PCellInfo aCells = aMed->CrCellInfo( aMesh, MED::eMAILLE, MED::ePOINT1, connect, eNOD, TIntVector( myPoints.size() ), TIntVector( myPoints.size() ) );
186   aMed->SetCellInfo( aCells, &anError );
187   if ( anError < 0 ) return false;
188
189   return true;
190 }