Advanced Strategic Command
exchangegraphics.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  cargodialog.cpp - description
3  -------------------
4  begin : Tue Oct 24 2000
5  copyright : (C) 2000 by Martin Bickel
6  email : bickel@asc-hq.org
7  ***************************************************************************/
8 
9 /***************************************************************************
10  * *
11  * This program is free software; you can redistribute it and/or modify *
12  * it under the terms of the GNU General Public License as published by *
13  * the Free Software Foundation; either version 2 of the License, or *
14  * (at your option) any later version. *
15  * *
16  ***************************************************************************/
17 
18 #include <boost/regex.hpp>
19 
20 #include "../paradialog.h"
21 #include "fileselector.h"
22 #include "../textfile_evaluation.h"
23 #include "../spfst.h"
24 #include "../spfst-legacy.h"
25 #include "../graphicset.h"
26 #include "../widgets/dropdownselector.h"
27 #include "exchangegraphics.h"
28 #include "../widgets/textrenderer.h"
29 #include "../fieldimageloader.h"
30 #include "../itemrepository.h"
31 
32 template<typename T, typename U>
33 void eraseElement( T& t, const U& u)
34 {
35  if ( t.find( u ) != t.end() )
36  t.erase( t.find(u) );
37 }
38 
39 
41 {
42  static const int dlg_width = 200;
43 
44  typedef map<int, Surface> OrgTerrainGFX;
45  static OrgTerrainGFX orgTerrainGFX;
46 
47  typedef map<const LoadableItemType*, Surface> OrgTerrainSurf;
48  static OrgTerrainSurf orgTerrainSurf;
49 
50  typedef map<int,ASCString> NewGFX;
51  static NewGFX newGFX;
52 
53  typedef map<ASCString,ASCString> NewSurfaces;
54  static NewSurfaces newSurfaces;
55 
56  PG_LineEdit* filename;
57  PG_LineEdit* imageNum;
58  PG_Label* terrain;
59  PG_Label* object;
60 
61  DropDownSelector* selectedType;
62 
63  bool fileSelect()
64  {
65  ASCString fn = selectFile("*.png;*.pcx", true );
66  if ( !fn.empty() )
67  filename->SetText( fn );
68  return true;
69  }
70 
71  ASCString getIdentifier( const TerrainType::Weather* w)
72  {
73  return "T: " + w->terraintype->filename;
74  }
75 
76  ASCString getIdentifier( const ObjectType* o)
77  {
78  return "O: " + o->filename;
79  }
80 
81  void setnewgfx ( int id, const ASCString& filename)
82  {
83  if ( orgTerrainGFX.find( id ) == orgTerrainGFX.end() )
84  orgTerrainGFX[id] = GraphicSetManager::Instance().getPic( id );
85 
86  GraphicSetManager::Instance().setPic( id, loadASCFieldImage ( filename ) );
87  newGFX[id] = filename;
88  }
89 
90  void setnewimage( TerrainType::Weather* trr, const ASCString& filename )
91  {
92  if ( orgTerrainSurf.find( trr ) == orgTerrainSurf.end() )
93  orgTerrainSurf[trr] = trr->image;
94 
95  trr->image = loadASCFieldImage ( filename );
96  newSurfaces[getIdentifier(trr)] = filename;
97  }
98 
99  void setnewimage( ObjectType* obj, const ASCString& filename )
100  {
101  obj->weatherPicture[0].images = loadASCFieldImageArray(filename, obj->weatherPicture[0].images.size() );
102  obj->displayMethod = 0;
103  /*
104  if ( orgTerrainSurf.find( obj ) == orgTerrainSurf.end() )
105  orgTerrainSurf[obj] = trr->image;
106 
107  trr->image = loadASCFieldImage ( filename );
108  newSurfaces[getIdentifier(trr)] = filename;
109  */
110  }
111 
112 
113  bool apply()
114  {
115  MapField* fld = actmap->getField( actmap->getCursor() );
116  if ( fld ) {
117  try {
118  if ( selectedType->GetSelectedItemIndex() == 0 ) {
119  if ( fld->typ->bi_pict >= 0 ) {
120  setnewgfx( fld->typ->bi_pict, filename->GetText() );
121  } else {
122  setnewimage( fld->typ, filename->GetText() );
123  }
124  }
125  if ( selectedType->GetSelectedItemIndex() == 1 ) {
126  if ( fld->objects.size() )
127  setnewimage( objectTypeRepository.getObject_byID( fld->objects[0].typ->id ), filename->GetText() );
128  }
129  }
130  catch ( ... ) {
131  warningMessage( "operation failed");
132  }
133  }
134  repaintMap();
135 
136  return true;
137  }
138 
139  bool close()
140  {
141  Hide();
142  return true;
143  }
144 
145  bool restore()
146  {
147  MapField* fld = actmap->getField( actmap->getCursor() );
148  if ( fld ) {
149  if ( selectedType->GetSelectedItemIndex() == 0 ) {
150  if ( fld->typ->bi_pict >= 0 ) {
151  if ( orgTerrainGFX.find(fld->typ->bi_pict) != orgTerrainGFX.end() ) {
152  GraphicSetManager::Instance().setPic( fld->typ->bi_pict, orgTerrainGFX[fld->typ->bi_pict] );
153  eraseElement( newGFX, fld->typ->bi_pict );
154  }
155  } else {
156  if ( orgTerrainSurf.find(fld->typ) != orgTerrainSurf.end() ) {
157  fld->typ->image = orgTerrainSurf[fld->typ];
158  eraseElement( newSurfaces, getIdentifier(fld->typ) );
159  }
160  }
161  }
162  }
163  repaintMap();
164  return true;
165  }
166 
167  bool readFile()
168  {
169  ASCString filename = selectFile("*.txt", true );
170  if ( filename.empty() )
171  return false;
172 
173  try {
174  tnfilestream stream ( filename, tnstream::reading );
175  bool finished = false;
176  while ( !finished ) {
177 
178  ASCString line;
179  finished = !stream.readTextString( line );
180 
181  boost::smatch what;
182 
183  static boost::regex gfx( "^GFX+(\\d+) -> (\\S+)");
184  if( boost::regex_match( line, what, gfx)) {
185  ASCString ids ( what[1] );
186  int id = atoi( ids.c_str() );
187 
188  ASCString name ( what[2] );
189  setnewgfx( id, name );
190  }
191 
192  static boost::regex trr( "^(T: \\S+) -> (\\S+)");
193  if( boost::regex_match( line, what, trr)) {
194  ASCString file ( what[1] );
195 
196  ASCString name ( what[2] );
197 
198  for ( int i = 0; i < terrainTypeRepository.getNum(); ++i ) {
199  TerrainType* t = terrainTypeRepository.getObject_byPos(i);
200  for ( int w = 0; w < cwettertypennum; ++w)
201  if ( t->weather[w] )
202  if ( getIdentifier(t->weather[w]) == file )
203  setnewimage( t->weather[w], name );
204  }
205  }
206  }
207  }
208  catch(...) {
209  errorMessage("an error occured");
210  }
211  repaintMap();
212  return true;
213  }
214 
215  bool snow()
216  {
217  MapField* fld = actmap->getField( actmap->getCursor() );
218  if ( fld ) {
219  if ( selectedType->GetSelectedItemIndex() == 0 ) {
220  if ( fld->typ->bi_pict < 0 )
221  snowify( fld->typ->image );
222  }
223  }
224  repaintMap();
225 
226  return true;
227  }
228 
229 
230  bool summary()
231  {
232  ASCString s;
233  for ( NewGFX::iterator i = newGFX.begin(); i != newGFX.end(); ++i )
234  s += "GFX" + ASCString::toString(i->first) + " -> " + i->second + "\n";
235 
236  for ( NewSurfaces::iterator i = newSurfaces.begin(); i != newSurfaces.end(); ++i )
237  s += i->first + " -> " + i->second + "\n";
238 
239 
240  ViewFormattedText vft("Graphics replacement summary", s, PG_Rect( -1, -1, 500, 400 ));
241  vft.Show();
242  vft.RunModal();
243  return true;
244  }
245 
246  void newCursorPos()
247  {
248  MapField* fld = actmap->getField( actmap->getCursor() );
249  if ( !fld )
250  return;
251 
252  if ( terrain ) {
253  ASCString s = "T: ID=" + ASCString::toString( fld->typ->terraintype->id );
254  if ( fld->typ->bi_pict >= 0 )
255  s += " GFX=" + ASCString::toString( fld->typ->bi_pict );
256 
257  if ( newGFX.find( fld->typ->bi_pict ) != newGFX.end() || newSurfaces.find( getIdentifier(fld->typ) ) != newSurfaces.end() )
258  s += " (R) ";
259 
260  terrain->SetText( s );
261  }
262 
263  if ( object ) {
264  if ( fld->objects.size() ) {
265  ASCString s = "O: ID=" + ASCString::toString( fld->objects.front().typ->id );
266  if ( fld->objects.front().typ->weatherPicture[0].bi3pic[0] >= 0 )
267  s += " GFX=" + ASCString::toString( fld->objects.front().typ->weatherPicture[0].bi3pic[0] );
268 
269  object->SetText( s );
270  } else
271  object->SetText("-");
272  }
273 
274  }
275 
276 
277  public:
278  ExchangeGraphics() : ASC_PG_Dialog( NULL, PG_Rect( PG_Application::GetScreenWidth() - dlg_width, -1, dlg_width, 450 ), "Exchange Graphics"), filename(NULL), imageNum(NULL),terrain(NULL), object(NULL), selectedType(NULL)
279  {
280 
281  selectedType = new DropDownSelector( this, PG_Rect( 10, 30, 180, 25 ));
282  selectedType->AddItem( "Terrain" );
283  selectedType->AddItem( "Object" );
284  selectedType->SelectItem( 0 );
285 
286  (new PG_Button( this, PG_Rect( 10, 100, 180, 30), "Select Filename"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::fileSelect )));
287 
288  terrain = new PG_Label( this, PG_Rect( 10, 140, 180, 25));
289  object = new PG_Label( this, PG_Rect( 10, 170, 180, 25));
290 
291 
292  (new PG_Button( this, PG_Rect( 10, 200, 180, 30), "Apply"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::apply )));
293  (new PG_Button( this, PG_Rect( 10, 240, 180, 30), "Restore Original"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::restore )));
294  (new PG_Button( this, PG_Rect( 10, 280, 180, 30), "Replacement Summary"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::summary )));
295  (new PG_Button( this, PG_Rect( 10, 320, 180, 30), "Load from file"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::readFile )));
296  (new PG_Button( this, PG_Rect( 10, 360, 180, 30), "Close"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::close )));
297  (new PG_Button( this, PG_Rect( 10, 400, 180, 30), "Snow"))->sigClick.connect( sigc::hide( sigc::mem_fun( *this, &ExchangeGraphics::snow )));
298 
299  cursorMoved.connect( sigc::mem_fun( *this, &ExchangeGraphics::newCursorPos ));
300  updateFieldInfo.connect( sigc::mem_fun( *this, &ExchangeGraphics::newCursorPos ));
301 
302  newCursorPos();
303 
304  filename = new PG_LineEdit( this, PG_Rect( 10, 65, 180, 30 ));
305 
306  }
307 };
308 
309 ExchangeGraphics::OrgTerrainGFX ExchangeGraphics::orgTerrainGFX;
310 ExchangeGraphics::OrgTerrainSurf ExchangeGraphics::orgTerrainSurf;
311 ExchangeGraphics::NewGFX ExchangeGraphics::newGFX;
312 ExchangeGraphics::NewSurfaces ExchangeGraphics::newSurfaces;
313 
314 
315 
317 {
318  static ExchangeGraphics* eg = NULL;
319  if ( !eg )
320  eg = new ExchangeGraphics();
321  eg->Show();
322 }
TerrainType::Weather * typ
the terraintype of the field
Definition: mapfield.h:38
The type of a field.
Definition: terraintype.h:75
int displayMethod
some objects require special displaying methods, for example shading the terrain they are build on ...
Definition: objecttype.h:175
ASCString filename
The name of the file from which the item was loaded.
Definition: typen.h:290
vector< Surface > loadASCFieldImageArray(const ASCString &file, int num)
ItemRepositoryLoader< ObjectType > objectTypeRepository("objecttype")
MapCoordinate & getCursor()
Definition: gamemap.cpp:933
void snowify(Surface &s, bool adaptive)
TerrainType * terraintype
pointer to the outer structure
Definition: terraintype.h:128
Weather * weather[cwettertypennum]
Definition: terraintype.h:140
Surface loadASCFieldImage(const ASCString &file, bool applyFieldMaskToImage)
void warningMessage(const ASCString &str)
sigc::signal< void > repaintMap
}@
Definition: spfst.cpp:45
a single field of the map
Definition: mapfield.h:26
The ASCString class provides an abstract way to manipulate strings.
Definition: ascstring.h:14
vector< Surface > images
Definition: objecttype.h:149
static ASCString toString(int i)
converts the parameter to a String
Definition: ascstring.cpp:193
ItemRepositoryLoader< TerrainType > terrainTypeRepository("terraintype")
Surface image
the image of the field
Definition: terraintype.h:103
An object that can be placed on fields. Roads, pipelines and ditches are examples of objects...
Definition: objecttype.h:30
Adapter class for using Paragui Dialogs in ASC. This class transfers the event control from ASC to Pa...
Definition: paradialog.h:127
sigc::signal< void > updateFieldInfo
Definition: spfst.cpp:47
void errorMessage(const ASCString &string)
void exchangeGraphics()
int bi_pict
the image index from the graphic set. -1 if graphics is not from graphic set.
Definition: terraintype.h:122
void eraseElement(T &t, const U &u)
ASCString selectFile(const ASCString &ext, bool load, bool overwriteMessage)
int atoi(const std::string &s)
Definition: misc.cpp:152
void AddItem(const std::string &text, void *userdata=NULL, Uint16 height=0)
sigc::signal< void > cursorMoved
Definition: spfst.cpp:48
GameMap * actmap
Definition: spfst.cpp:64
struct ObjectType::WeatherPicture weatherPicture[cwettertypennum]
virtual bool readTextString(ASCString &s, bool includeCR=false)
Reads a string.
Definition: basestrm.cpp:511
const int cwettertypennum
The number of different weather.
Definition: typen.h:61
void line(int x1, int y1, int x2, int y2, Uint8 actcol)
draws a simple line on the screen. Not very fast...
Definition: basegfx.cpp:181
ObjectContainer objects
Definition: mapfield.h:124
MapField * getField(int x, int y)
Definition: gamemap.h:465