Save.cpp 42 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284
  1. /*
  2. ** Command & Conquer Generals(tm)
  3. ** Copyright 2025 Electronic Arts Inc.
  4. **
  5. ** This program is free software: you can redistribute it and/or modify
  6. ** it under the terms of the GNU General Public License as published by
  7. ** the Free Software Foundation, either version 3 of the License, or
  8. ** (at your option) any later version.
  9. **
  10. ** This program is distributed in the hope that it will be useful,
  11. ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  12. ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  13. ** GNU General Public License for more details.
  14. **
  15. ** You should have received a copy of the GNU General Public License
  16. ** along with this program. If not, see <http://www.gnu.org/licenses/>.
  17. */
  18. ////////////////////////////////////////////////////////////////////////////////
  19. // //
  20. // (c) 2001-2003 Electronic Arts Inc. //
  21. // //
  22. ////////////////////////////////////////////////////////////////////////////////
  23. // FILE: Save.cpp /////////////////////////////////////////////////////////////
  24. //-----------------------------------------------------------------------------
  25. //
  26. // Westwood Studios Pacific.
  27. //
  28. // Confidential Information
  29. // Copyright (C) 2001 - All Rights Reserved
  30. //
  31. //-----------------------------------------------------------------------------
  32. //
  33. // Project: GUIEdit
  34. //
  35. // File name: Save.cpp
  36. //
  37. // Created: Colin Day, July 2001
  38. //
  39. // Desc: Save the window layout to a file
  40. //
  41. //-----------------------------------------------------------------------------
  42. ///////////////////////////////////////////////////////////////////////////////
  43. // SYSTEM INCLUDES ////////////////////////////////////////////////////////////
  44. #include <stdio.h>
  45. #include <assert.h>
  46. // USER INCLUDES //////////////////////////////////////////////////////////////
  47. #include "GUIEdit.h"
  48. #include "Common/Debug.h"
  49. #include "Common/NameKeyGenerator.h"
  50. #include "Common/FunctionLexicon.h"
  51. #include "GameClient/Display.h"
  52. #include "GameClient/GameWindow.h"
  53. #include "GameClient/GameWindowManager.h"
  54. #include "GameClient/GadgetRadioButton.h"
  55. ///////////////////////////////////////////////////////////////////////////////
  56. // DEFINES ////////////////////////////////////////////////////////////////////
  57. ///////////////////////////////////////////////////////////////////////////////
  58. #define BUFFER_SIZE (2048)
  59. #define INDENT_SIZE (2)
  60. // PRIVATE TYPES //////////////////////////////////////////////////////////////
  61. ///////////////////////////////////////////////////////////////////////////////
  62. // PRIVATE DATA ///////////////////////////////////////////////////////////////
  63. ///////////////////////////////////////////////////////////////////////////////
  64. static char buffer[ BUFFER_SIZE ]; ///< buffer for writing data to before file output
  65. static char offendingNames[ 65536 ];
  66. // PUBLIC DATA ////////////////////////////////////////////////////////////////
  67. // PRIVATE PROTOTYPES /////////////////////////////////////////////////////////
  68. ///////////////////////////////////////////////////////////////////////////////
  69. // PRIVATE FUNCTIONS //////////////////////////////////////////////////////////
  70. ///////////////////////////////////////////////////////////////////////////////
  71. // fileNewLine ================================================================
  72. /** Write a blank line to the file */
  73. //=============================================================================
  74. static void fileNewLine( FILE *fp )
  75. {
  76. fprintf( fp, "\n" );
  77. fflush( fp );
  78. } // end fileNewLine
  79. // writeBufferToFile ==========================================================
  80. /** Write the contents of the buffer to the file */
  81. //=============================================================================
  82. static void writeBufferToFile( FILE *fp, char *buffer )
  83. {
  84. // do the write
  85. fprintf( fp, buffer );
  86. //
  87. // flush the file stream so that if errors occur and we don't properly
  88. // recover it will be useful debugging information to see exactly how
  89. // far we got
  90. //
  91. fflush( fp );
  92. } // end writeBufferToFile
  93. // clearBufferToSpaces ========================================================
  94. /** Clear the buffer to all spaces */
  95. //=============================================================================
  96. static void clearBufferToSpaces( void )
  97. {
  98. Int i;
  99. for( i = 0; i < BUFFER_SIZE; i++ )
  100. buffer[ i ] = ' ';
  101. } // end clearBufferToSpaces
  102. // saveType ===================================================================
  103. /** Save type of window */
  104. //=============================================================================
  105. static Bool saveType( GameWindow *window, FILE *fp, Int dataIndent )
  106. {
  107. char *type;
  108. if( BitTest( window->winGetStyle(), GWS_PUSH_BUTTON ) )
  109. type = "PUSHBUTTON";
  110. else if( BitTest( window->winGetStyle(), GWS_RADIO_BUTTON ) )
  111. type = "RADIOBUTTON";
  112. else if( BitTest( window->winGetStyle(), GWS_TAB_CONTROL ) )
  113. type = "TABCONTROL";
  114. else if( BitTest( window->winGetStyle(), GWS_TAB_PANE ) )
  115. type = "TABPANE";
  116. else if( BitTest( window->winGetStyle(), GWS_CHECK_BOX ) )
  117. type = "CHECKBOX";
  118. else if( BitTest( window->winGetStyle(), GWS_VERT_SLIDER ) )
  119. type = "VERTSLIDER";
  120. else if( BitTest( window->winGetStyle(), GWS_HORZ_SLIDER ) )
  121. type = "HORZSLIDER";
  122. else if( BitTest( window->winGetStyle(), GWS_SCROLL_LISTBOX ) )
  123. type = "SCROLLLISTBOX";
  124. else if( BitTest( window->winGetStyle(), GWS_COMBO_BOX ) )
  125. type = "COMBOBOX";
  126. else if( BitTest( window->winGetStyle(), GWS_ENTRY_FIELD ) )
  127. type = "ENTRYFIELD";
  128. else if( BitTest( window->winGetStyle(), GWS_STATIC_TEXT ) )
  129. type = "STATICTEXT";
  130. else if( BitTest( window->winGetStyle(), GWS_PROGRESS_BAR ) )
  131. type = "PROGRESSBAR";
  132. else
  133. type = "USER";
  134. sprintf( &buffer[ dataIndent ], "WINDOWTYPE = %s;\n", type );
  135. writeBufferToFile( fp, buffer );
  136. return TRUE;
  137. } // end saveType
  138. // savePosition ===============================================================
  139. /** Save window position data */
  140. //=============================================================================
  141. static Bool savePosition( GameWindow *window, FILE *fp, Int dataIndent )
  142. {
  143. IRegion2D screenRect;
  144. ICoord2D size;
  145. // get the 4 screen position points of the window
  146. window->winGetScreenPosition( &screenRect.lo.x, &screenRect.lo.y );
  147. window->winGetSize( &size.x, &size.y );
  148. screenRect.hi.x = screenRect.lo.x + size.x;
  149. screenRect.hi.y = screenRect.lo.y + size.y;
  150. //
  151. // write those 4 screen points out with the ratio divisor that we
  152. // created them in (the edit window size) so we can scale them by
  153. // that ratio if need be
  154. //
  155. sprintf( &buffer[ dataIndent ], "SCREENRECT = UPPERLEFT: %d %d,\n",
  156. screenRect.lo.x, screenRect.lo.y );
  157. writeBufferToFile( fp, buffer );
  158. sprintf( &buffer[ dataIndent ], " BOTTOMRIGHT: %d %d,\n",
  159. screenRect.hi.x, screenRect.hi.y );
  160. writeBufferToFile( fp, buffer );
  161. sprintf( &buffer[ dataIndent ], " CREATIONRESOLUTION: %d %d;\n",
  162. TheDisplay->getWidth(), TheDisplay->getHeight() );
  163. writeBufferToFile( fp, buffer );
  164. return TRUE;
  165. } // end savePosition
  166. // saveName ===================================================================
  167. // Save name */
  168. //=============================================================================
  169. static Bool saveName( GameWindow *window, FILE *fp, Int dataIndent )
  170. {
  171. WinInstanceData *instData = window->winGetInstanceData();
  172. sprintf( &buffer[ dataIndent ], "NAME = \"%s:%s\";\n",
  173. TheEditor->getSaveFilename(), instData->m_decoratedNameString.str() );
  174. writeBufferToFile( fp, buffer );
  175. return TRUE;
  176. } // end saveName
  177. // saveStatus =================================================================
  178. /** Save status information */
  179. //=============================================================================
  180. static Bool saveStatus( GameWindow *window, FILE *fp, Int dataIndent )
  181. {
  182. Int i;
  183. Bool bitWritten;
  184. UnsignedInt bit;
  185. sprintf( &buffer[ dataIndent ], "STATUS = " );
  186. i = 0;
  187. bitWritten = FALSE;
  188. while( WindowStatusNames[ i ] )
  189. {
  190. bit = 1 << i;
  191. if( BitTest( window->winGetStatus(), bit ) )
  192. {
  193. // if this is an additional bit add a +
  194. if( bitWritten == TRUE )
  195. strcat( buffer, "+");
  196. // add status name
  197. strcat( buffer, WindowStatusNames[ i ] );
  198. bitWritten = TRUE;
  199. } // end
  200. i++;
  201. } // end while
  202. // if no bits written write NONE in the file
  203. if( bitWritten == FALSE )
  204. strcat( buffer, "NONE" );
  205. // complete line and write
  206. strcat( buffer, ";\n" );
  207. writeBufferToFile( fp, buffer );
  208. return TRUE;
  209. } // end saveStatus
  210. // saveStyle ==================================================================
  211. /** Save style information */
  212. //=============================================================================
  213. static Bool saveStyle( GameWindow *window, FILE *fp, Int dataIndent )
  214. {
  215. Int i;
  216. Bool bitWritten;
  217. UnsignedInt bit;
  218. sprintf( &buffer[ dataIndent ], "STYLE = " );
  219. i = 0;
  220. bitWritten = FALSE;
  221. while( WindowStyleNames[ i ] )
  222. {
  223. bit = 1 << i;
  224. if( BitTest( window->winGetStyle(), bit ) )
  225. {
  226. // if this is an additional bit add a +
  227. if( bitWritten == TRUE )
  228. strcat( buffer, "+");
  229. // add status name
  230. strcat( buffer, WindowStyleNames[ i ] );
  231. bitWritten = TRUE;
  232. } // end
  233. i++;
  234. } // end while
  235. // if no bits written write NONE in the file
  236. if( bitWritten == FALSE )
  237. strcat( buffer, "NONE" );
  238. // complete line and write
  239. strcat( buffer, ";\n" );
  240. writeBufferToFile( fp, buffer );
  241. return TRUE;
  242. } // end saveStyle
  243. // saveCallbacks ==============================================================
  244. /** Save string representations of the window function callbacks into
  245. * the save file */
  246. //=============================================================================
  247. static Bool saveCallbacks( GameWindow *window, FILE *fp, Int dataIndent )
  248. {
  249. GameWindowEditData *editData = window->winGetEditData();
  250. // if no edit data don't write anything for callbacks
  251. if( editData == NULL )
  252. return FALSE;
  253. // system
  254. AsciiString name;
  255. name = editData->systemCallbackString;
  256. if( name.isEmpty() )
  257. name = GUIEDIT_NONE_STRING;
  258. sprintf( &buffer[ dataIndent ], "SYSTEMCALLBACK = \"%s\";\n", name.str() );
  259. writeBufferToFile( fp, buffer );
  260. // input
  261. name = editData->inputCallbackString;
  262. if( name.isEmpty() )
  263. name = GUIEDIT_NONE_STRING;
  264. sprintf( &buffer[ dataIndent ], "INPUTCALLBACK = \"%s\";\n", name.str() );
  265. writeBufferToFile( fp, buffer );
  266. // tooltip
  267. name = editData->tooltipCallbackString;
  268. if( name.isEmpty() )
  269. name = GUIEDIT_NONE_STRING;
  270. sprintf( &buffer[ dataIndent ], "TOOLTIPCALLBACK = \"%s\";\n", name.str() );
  271. writeBufferToFile( fp, buffer );
  272. // draw
  273. name = editData->drawCallbackString;
  274. if( name.isEmpty() )
  275. name = GUIEDIT_NONE_STRING;
  276. sprintf( &buffer[ dataIndent ], "DRAWCALLBACK = \"%s\";\n", name.str() );
  277. writeBufferToFile( fp, buffer );
  278. return TRUE;
  279. } // end saveCallbacks
  280. // saveHeaderTemplate =========================================================
  281. /** Save HeaderTemplate for a window */
  282. //=============================================================================
  283. static Bool saveHeaderTemplate(GameWindow *window, FILE *fp, Int dataIndent )
  284. {
  285. AsciiString headerName = window->winGetInstanceData()->m_headerTemplateName;
  286. if(headerName.isEmpty())
  287. headerName = GUIEDIT_NONE_STRING;
  288. sprintf( &buffer[ dataIndent ], "HEADERTEMPLATE = \"%s\";\n", headerName.str() );
  289. writeBufferToFile( fp, buffer );
  290. return TRUE;
  291. }
  292. // saveFont ===================================================================
  293. /** Save font name for a window */
  294. //=============================================================================
  295. static Bool saveFont( GameWindow *window, FILE *fp, Int dataIndent )
  296. {
  297. GameFont *font = window->winGetFont();
  298. // if no font data don't write anything
  299. if( font == NULL )
  300. return TRUE;
  301. // write the font data
  302. sprintf( &buffer[ dataIndent ], "FONT = NAME: \"%s\", SIZE: %d, BOLD: %d;\n",
  303. font->nameString.str(), font->pointSize, font->bold );
  304. writeBufferToFile( fp, buffer );
  305. return TRUE;
  306. } // end saveFont
  307. // saveTooltipText ===================================================================
  308. /** Save the text for a window */
  309. //=============================================================================
  310. static Bool saveTooltipText( GameWindow *window, FILE *fp, Int dataIndent )
  311. {
  312. WinInstanceData *instData = window->winGetInstanceData();
  313. // save the text label
  314. if (instData->getTooltipTextLength())
  315. {
  316. sprintf( &buffer[ dataIndent ], "TOOLTIPTEXT = \"%s\";\n", instData->m_tooltipString.str() );
  317. writeBufferToFile( fp, buffer );
  318. } // end if
  319. return TRUE;
  320. } // end saveTooltipText
  321. // saveTooltipDelay ===================================================================
  322. /** Save the delay for a window */
  323. //=============================================================================
  324. static Bool saveTooltipDelay( GameWindow *window, FILE *fp, Int dataIndent )
  325. {
  326. WinInstanceData *instData = window->winGetInstanceData();
  327. // save the text label
  328. //if (instData->getTooltipTextLength())
  329. //{//
  330. sprintf( &buffer[ dataIndent ], "TOOLTIPDELAY = %d;\n", instData->m_tooltipDelay );
  331. writeBufferToFile( fp, buffer );
  332. //} // end if
  333. return TRUE;
  334. } // end saveTooltipText
  335. // saveText ===================================================================
  336. /** Save the text for a window */
  337. //=============================================================================
  338. static Bool saveText( GameWindow *window, FILE *fp, Int dataIndent )
  339. {
  340. WinInstanceData *instData = window->winGetInstanceData();
  341. // save the text label
  342. if (!instData->m_textLabelString.isEmpty())
  343. {
  344. sprintf( &buffer[ dataIndent ], "TEXT = \"%s\";\n", instData->m_textLabelString.str() );
  345. writeBufferToFile( fp, buffer );
  346. } // end if
  347. return TRUE;
  348. } // end saveText
  349. // saveTextColor ==============================================================
  350. /** Save the text colors for enabled, disable, and hilite with
  351. * drop border colors */
  352. //=============================================================================
  353. static Bool saveTextColor( GameWindow *window, FILE *fp, Int dataIndent )
  354. {
  355. Int i, max = 3; // 3 states, enabled, hilite and disabled
  356. UnsignedByte r, g, b, a, br, bg, bb, ba;
  357. Color color, border;
  358. for( i = 0; i < max; i++ )
  359. {
  360. switch( i )
  361. {
  362. case 0: color = window->winGetEnabledTextColor();
  363. border = window->winGetEnabledTextBorderColor();
  364. break;
  365. case 1: color = window->winGetDisabledTextColor();
  366. border = window->winGetDisabledTextBorderColor();
  367. break;
  368. case 2: color = window->winGetHiliteTextColor();
  369. border = window->winGetHiliteTextBorderColor();
  370. break;
  371. }
  372. // get color components
  373. GameGetColorComponents( color, &r, &g, &b, &a );
  374. GameGetColorComponents( border, &br, &bg, &bb, &ba );
  375. if( i == 0 )
  376. sprintf( &buffer[ dataIndent ], "TEXTCOLOR = ENABLED: %d %d %d %d, ENABLEDBORDER: %d %d %d %d,\n",
  377. r, g, b, a, br, bg, bb, ba );
  378. else if( i == max - 1 )
  379. sprintf( &buffer[ dataIndent ], " HILITE: %d %d %d %d, HILITEBORDER: %d %d %d %d;\n",
  380. r, g, b, a, br, bg, bb, ba );
  381. else
  382. sprintf( &buffer[ dataIndent ], " DISABLED: %d %d %d %d, DISABLEDBORDER: %d %d %d %d,\n",
  383. r, g, b, a, br, bg, bb, ba );
  384. writeBufferToFile( fp, buffer );
  385. } // end for i
  386. return TRUE;
  387. } // end saveTextColor
  388. // tokenIsEnabledData =========================================================
  389. /** Token refers to enabled draw data */
  390. //=============================================================================
  391. static Bool tokenIsEnabledData( char *token )
  392. {
  393. if( strcmp( token, "ENABLEDDRAWDATA" ) == 0 ||
  394. strcmp( token, "LISTBOXENABLEDUPBUTTONDRAWDATA" ) == 0 ||
  395. strcmp( token, "LISTBOXENABLEDDOWNBUTTONDRAWDATA" ) == 0 ||
  396. strcmp( token, "LISTBOXENABLEDSLIDERDRAWDATA" ) == 0 ||
  397. strcmp( token, "COMBOBOXDROPDOWNBUTTONENABLEDDRAWDATA" ) == 0 ||
  398. strcmp( token, "COMBOBOXEDITBOXENABLEDDRAWDATA" ) == 0 ||
  399. strcmp( token, "COMBOBOXLISTBOXENABLEDDRAWDATA" ) == 0 ||
  400. strcmp( token, "SLIDERTHUMBENABLEDDRAWDATA" ) == 0 )
  401. return TRUE;
  402. return FALSE;
  403. } // end tokenIsEnabledData
  404. // tokenIsDisabledData ========================================================
  405. /** Token refers to Disabled draw data */
  406. //=============================================================================
  407. static Bool tokenIsDisabledData( char *token )
  408. {
  409. if( strcmp( token, "DISABLEDDRAWDATA" ) == 0 ||
  410. strcmp( token, "LISTBOXDISABLEDUPBUTTONDRAWDATA" ) == 0 ||
  411. strcmp( token, "LISTBOXDISABLEDDOWNBUTTONDRAWDATA" ) == 0 ||
  412. strcmp( token, "LISTBOXDISABLEDSLIDERDRAWDATA" ) == 0 ||
  413. strcmp( token, "COMBOBOXDROPDOWNBUTTONDISABLEDDRAWDATA" ) == 0 ||
  414. strcmp( token, "COMBOBOXEDITBOXDISABLEDDRAWDATA" ) == 0 ||
  415. strcmp( token, "COMBOBOXLISTBOXDISABLEDDRAWDATA" ) == 0 ||
  416. strcmp( token, "SLIDERTHUMBDISABLEDDRAWDATA" ) == 0 )
  417. return TRUE;
  418. return FALSE;
  419. } // end tokenIsDisabledData
  420. // tokenIsHiliteData ==========================================================
  421. /** Token refers to Hilite draw data */
  422. //=============================================================================
  423. static Bool tokenIsHiliteData( char *token )
  424. {
  425. if( strcmp( token, "HILITEDRAWDATA" ) == 0 ||
  426. strcmp( token, "LISTBOXHILITEUPBUTTONDRAWDATA" ) == 0 ||
  427. strcmp( token, "LISTBOXHILITEDOWNBUTTONDRAWDATA" ) == 0 ||
  428. strcmp( token, "LISTBOXHILITESLIDERDRAWDATA" ) == 0 ||
  429. strcmp( token, "COMBOBOXLISTBOXHILITEDRAWDATA" ) == 0 ||
  430. strcmp( token, "COMBOBOXEDITBOXHILITEDRAWDATA" ) == 0 ||
  431. strcmp( token, "COMBOBOXDROPDOWNBUTTONHILITEDRAWDATA" ) == 0 ||
  432. strcmp( token, "SLIDERTHUMBHILITEDRAWDATA" ) == 0 )
  433. return TRUE;
  434. return FALSE;
  435. } // end tokenIsHiliteData
  436. // saveDrawData ===============================================================
  437. /** Save the draw data array */
  438. //=============================================================================
  439. static Bool saveDrawData( char *token, GameWindow *window,
  440. FILE *fp, Int dataIndent )
  441. {
  442. Int i;
  443. WinInstanceData *instData = window->winGetInstanceData();
  444. char spaces[ 128 ];
  445. // format spaces so it looks pretty and lines up in the text file
  446. Int len = strlen( token );
  447. assert( len < sizeof( spaces ) );
  448. for( i = 0; i < len; i++ )
  449. spaces[ i ] = ' ';
  450. spaces[ i ] = 0; // terminate
  451. for( i = 0; i < MAX_DRAW_DATA; i++ )
  452. {
  453. WinDrawData *drawData;
  454. UnsignedByte r, g, b, a, br, bg, bb, ba;
  455. const Image *image;
  456. // get the right draw data
  457. if( tokenIsEnabledData( token ) )
  458. drawData = &instData->m_enabledDrawData[ i ];
  459. else if( tokenIsDisabledData( token ) )
  460. drawData = &instData->m_disabledDrawData[ i ];
  461. else if( tokenIsHiliteData( token ) )
  462. drawData = &instData->m_hiliteDrawData[ i ];
  463. else
  464. {
  465. DEBUG_LOG(( "Save draw data, unknown token '%s'\n", token ));
  466. assert( 0 );
  467. return FALSE;
  468. } // end else
  469. image = drawData->image;
  470. GameGetColorComponents( drawData->color, &r, &g, &b, &a );
  471. GameGetColorComponents( drawData->borderColor, &br, &bg, &bb, &ba );
  472. if( i == 0 )
  473. sprintf( &buffer[ dataIndent ], "%s = IMAGE: %s, COLOR: %d %d %d %d, BORDERCOLOR: %d %d %d %d,\n",
  474. token, image ? image->getName().str() : "NoImage", r, g, b, a, br, bg, bb, ba );
  475. else if( i == MAX_DRAW_DATA - 1 )
  476. sprintf( &buffer[ dataIndent ], "%s IMAGE: %s, COLOR: %d %d %d %d, BORDERCOLOR: %d %d %d %d;\n",
  477. spaces, image ? image->getName().str() : "NoImage", r, g, b, a, br, bg, bb, ba );
  478. else
  479. sprintf( &buffer[ dataIndent ], "%s IMAGE: %s, COLOR: %d %d %d %d, BORDERCOLOR: %d %d %d %d,\n",
  480. spaces, image ? image->getName().str() : "NoImage", r, g, b, a, br, bg, bb, ba );
  481. writeBufferToFile( fp, buffer );
  482. } // end for i
  483. return TRUE;
  484. } // end saveDrawData
  485. // saveListboxData ============================================================
  486. /** Save listbox data to the file */
  487. //=============================================================================
  488. static Bool saveListboxData( GameWindow *window, FILE *fp, Int dataIndent )
  489. {
  490. ListboxData *listData = (ListboxData *)window->winGetUserData();
  491. // sanity
  492. if( listData == NULL )
  493. {
  494. DEBUG_LOG(( "No listbox data to save for window '%d'\n",
  495. window->winGetWindowId() ));
  496. assert( 0 );
  497. return FALSE;
  498. } // end if
  499. sprintf( &buffer[ dataIndent ], "LISTBOXDATA = LENGTH: %d,\n", listData->listLength );
  500. writeBufferToFile( fp, buffer );
  501. sprintf( &buffer[ dataIndent ], " AUTOSCROLL: %d,\n", listData->autoScroll );
  502. writeBufferToFile( fp, buffer );
  503. sprintf( &buffer[ dataIndent ], " SCROLLIFATEND: %d,\n", listData->scrollIfAtEnd );
  504. writeBufferToFile( fp, buffer );
  505. sprintf( &buffer[ dataIndent ], " AUTOPURGE: %d,\n", listData->autoPurge );
  506. writeBufferToFile( fp, buffer );
  507. sprintf( &buffer[ dataIndent ], " SCROLLBAR: %d,\n", listData->scrollBar );
  508. writeBufferToFile( fp, buffer );
  509. sprintf( &buffer[ dataIndent ], " MULTISELECT: %d,\n", listData->multiSelect );
  510. writeBufferToFile( fp, buffer );
  511. sprintf( &buffer[ dataIndent ], " COLUMNS: %d,\n", listData->columns );
  512. writeBufferToFile( fp, buffer );
  513. if(listData->columns > 1)
  514. {
  515. for(Int i = 0; i < listData->columns; i++ )
  516. {
  517. sprintf( &buffer[ dataIndent ], " COLUMNSWIDTH%%: %d,\n", listData->columnWidthPercentage[i] );
  518. writeBufferToFile( fp, buffer );
  519. }
  520. }
  521. sprintf( &buffer[ dataIndent ], " FORCESELECT: %d;\n", listData->forceSelect );
  522. writeBufferToFile( fp, buffer );
  523. // save the up button draw data for the listbox
  524. if( listData->upButton )
  525. {
  526. saveDrawData( "LISTBOXENABLEDUPBUTTONDRAWDATA", listData->upButton, fp, dataIndent );
  527. saveDrawData( "LISTBOXDISABLEDUPBUTTONDRAWDATA", listData->upButton, fp, dataIndent );
  528. saveDrawData( "LISTBOXHILITEUPBUTTONDRAWDATA", listData->upButton, fp, dataIndent );
  529. } // end if
  530. // save down button draw data for listbox
  531. if( listData->downButton )
  532. {
  533. saveDrawData( "LISTBOXENABLEDDOWNBUTTONDRAWDATA", listData->downButton, fp, dataIndent );
  534. saveDrawData( "LISTBOXDISABLEDDOWNBUTTONDRAWDATA", listData->downButton, fp, dataIndent );
  535. saveDrawData( "LISTBOXHILITEDOWNBUTTONDRAWDATA", listData->downButton, fp, dataIndent );
  536. } // end if
  537. // save the slider draw data on the listbox
  538. if( listData->slider )
  539. {
  540. GameWindow *thumb = listData->slider->winGetChild();
  541. saveDrawData( "LISTBOXENABLEDSLIDERDRAWDATA", listData->slider, fp, dataIndent );
  542. saveDrawData( "LISTBOXDISABLEDSLIDERDRAWDATA", listData->slider, fp, dataIndent );
  543. saveDrawData( "LISTBOXHILITESLIDERDRAWDATA", listData->slider, fp, dataIndent );
  544. if( thumb )
  545. {
  546. saveDrawData( "SLIDERTHUMBENABLEDDRAWDATA", thumb, fp, dataIndent );
  547. saveDrawData( "SLIDERTHUMBDISABLEDDRAWDATA", thumb, fp, dataIndent );
  548. saveDrawData( "SLIDERTHUMBHILITEDRAWDATA", thumb, fp, dataIndent );
  549. } // end if
  550. } // end if
  551. return TRUE;
  552. } // end saveListboxData
  553. // saveComboBoxData ============================================================
  554. /** Save Combo Box data to the file */
  555. //=============================================================================
  556. static Bool saveComboBoxData( GameWindow *window, FILE *fp, Int dataIndent )
  557. {
  558. ComboBoxData *comboData = (ComboBoxData *)window->winGetUserData();
  559. // sanity
  560. if( comboData == NULL )
  561. {
  562. DEBUG_LOG(( "No comboData data to save for window '%d'\n",
  563. window->winGetWindowId() ));
  564. assert( 0 );
  565. return FALSE;
  566. } // end if
  567. sprintf( &buffer[ dataIndent ], "COMBOBOXDATA = ISEDITABLE: %d,\n", comboData->isEditable );
  568. writeBufferToFile( fp, buffer );
  569. sprintf( &buffer[ dataIndent ], " MAXCHARS: %d,\n", comboData->maxChars );
  570. writeBufferToFile( fp, buffer );
  571. sprintf( &buffer[ dataIndent ], " MAXDISPLAY: %d,\n", comboData->maxDisplay );
  572. writeBufferToFile( fp, buffer );
  573. sprintf( &buffer[ dataIndent ], " ASCIIONLY: %d,\n", comboData->asciiOnly );
  574. writeBufferToFile( fp, buffer );
  575. sprintf( &buffer[ dataIndent ], " LETTERSANDNUMBERS: %d;\n", comboData->lettersAndNumbersOnly );
  576. writeBufferToFile( fp, buffer );
  577. //Save teh dropDownButton draw data for the combo box
  578. if( comboData->dropDownButton )
  579. {
  580. saveDrawData( "COMBOBOXDROPDOWNBUTTONENABLEDDRAWDATA", comboData->dropDownButton, fp, dataIndent );
  581. saveDrawData( "COMBOBOXDROPDOWNBUTTONDISABLEDDRAWDATA", comboData->dropDownButton, fp, dataIndent );
  582. saveDrawData( "COMBOBOXDROPDOWNBUTTONHILITEDRAWDATA", comboData->dropDownButton, fp, dataIndent );
  583. } // end if
  584. if( comboData->editBox )
  585. {
  586. saveDrawData( "COMBOBOXEDITBOXENABLEDDRAWDATA", comboData->editBox, fp, dataIndent );
  587. saveDrawData( "COMBOBOXEDITBOXDISABLEDDRAWDATA", comboData->editBox, fp, dataIndent );
  588. saveDrawData( "COMBOBOXEDITBOXHILITEDRAWDATA", comboData->editBox, fp, dataIndent );
  589. } // end if
  590. if(comboData->listBox)
  591. {
  592. ListboxData *listData = (ListboxData *)comboData->listBox->winGetUserData();
  593. saveDrawData( "COMBOBOXLISTBOXENABLEDDRAWDATA", comboData->listBox, fp, dataIndent );
  594. saveDrawData( "COMBOBOXLISTBOXDISABLEDDRAWDATA", comboData->listBox, fp, dataIndent );
  595. saveDrawData( "COMBOBOXLISTBOXHILITEDRAWDATA", comboData->listBox, fp, dataIndent );
  596. // save the up button draw data for the listbox
  597. if( listData->upButton )
  598. {
  599. saveDrawData( "LISTBOXENABLEDUPBUTTONDRAWDATA", listData->upButton, fp, dataIndent );
  600. saveDrawData( "LISTBOXDISABLEDUPBUTTONDRAWDATA", listData->upButton, fp, dataIndent );
  601. saveDrawData( "LISTBOXHILITEUPBUTTONDRAWDATA", listData->upButton, fp, dataIndent );
  602. } // end if
  603. // save down button draw data for listbox
  604. if( listData->downButton )
  605. {
  606. saveDrawData( "LISTBOXENABLEDDOWNBUTTONDRAWDATA", listData->downButton, fp, dataIndent );
  607. saveDrawData( "LISTBOXDISABLEDDOWNBUTTONDRAWDATA", listData->downButton, fp, dataIndent );
  608. saveDrawData( "LISTBOXHILITEDOWNBUTTONDRAWDATA", listData->downButton, fp, dataIndent );
  609. } // end if
  610. // save the slider draw data on the listbox
  611. if( listData->slider )
  612. {
  613. GameWindow *thumb = listData->slider->winGetChild();
  614. saveDrawData( "LISTBOXENABLEDSLIDERDRAWDATA", listData->slider, fp, dataIndent );
  615. saveDrawData( "LISTBOXDISABLEDSLIDERDRAWDATA", listData->slider, fp, dataIndent );
  616. saveDrawData( "LISTBOXHILITESLIDERDRAWDATA", listData->slider, fp, dataIndent );
  617. if( thumb )
  618. {
  619. saveDrawData( "SLIDERTHUMBENABLEDDRAWDATA", thumb, fp, dataIndent );
  620. saveDrawData( "SLIDERTHUMBDISABLEDDRAWDATA", thumb, fp, dataIndent );
  621. saveDrawData( "SLIDERTHUMBHILITEDRAWDATA", thumb, fp, dataIndent );
  622. } // end if
  623. } // end if
  624. }// end if
  625. return TRUE;
  626. } // end saveComboBoxData
  627. // saveRadioButtonData ========================================================
  628. /** Save radio button specific data */
  629. //=============================================================================
  630. static Bool saveRadioButtonData( GameWindow *window, FILE *fp, Int dataIndent )
  631. {
  632. RadioButtonData *radioData = (RadioButtonData *)window->winGetUserData();
  633. if( radioData == NULL )
  634. {
  635. DEBUG_LOG(( "No radio button data to save for window '%d'\n",
  636. window->winGetWindowId() ));
  637. assert( 0 );
  638. return FALSE;
  639. } // end if
  640. sprintf( &buffer[ dataIndent ], "RADIOBUTTONDATA = GROUP: %d;\n", radioData->group );
  641. writeBufferToFile( fp, buffer );
  642. return TRUE;
  643. } // end saveRadioButtonData
  644. // saveSliderData =============================================================
  645. /** Save slider specific data */
  646. //=============================================================================
  647. static Bool saveSliderData( GameWindow *window, FILE *fp, Int dataIndent )
  648. {
  649. SliderData *sliderData = (SliderData *)window->winGetUserData();
  650. // sanity
  651. if( sliderData == NULL )
  652. {
  653. DEBUG_LOG(( "No slider data in window to save for window %d\n",
  654. window->winGetWindowId() ));
  655. assert( 0 );
  656. return FALSE;
  657. } // end if
  658. sprintf( &buffer[ dataIndent ], "SLIDERDATA = MINVALUE: %d,\n", sliderData->minVal );
  659. writeBufferToFile( fp, buffer );
  660. sprintf( &buffer[ dataIndent ], " MAXVALUE: %d;\n", sliderData->maxVal );
  661. writeBufferToFile( fp, buffer );
  662. // save data about the slider thumb
  663. GameWindow *thumb = window->winGetChild();
  664. if( thumb )
  665. {
  666. saveDrawData( "SLIDERTHUMBENABLEDDRAWDATA", thumb, fp, dataIndent );
  667. saveDrawData( "SLIDERTHUMBDISABLEDDRAWDATA", thumb, fp, dataIndent );
  668. saveDrawData( "SLIDERTHUMBHILITEDRAWDATA", thumb, fp, dataIndent );
  669. } // end if
  670. return TRUE;
  671. } // end saveSliderData
  672. // saveStaticTextData =========================================================
  673. /** Save static text data entry */
  674. //=============================================================================
  675. static Bool saveStaticTextData( GameWindow *window, FILE *fp, Int dataIndent )
  676. {
  677. TextData *textData = (TextData *)window->winGetUserData();
  678. // sanity
  679. if( textData == NULL )
  680. {
  681. DEBUG_LOG(( "No text data in window to save for window %d\n",
  682. window->winGetWindowId() ));
  683. assert( 0 );
  684. return FALSE;
  685. } // end if
  686. sprintf( &buffer[ dataIndent ], "STATICTEXTDATA = CENTERED: %d;\n", textData->centered );
  687. writeBufferToFile( fp, buffer );
  688. return TRUE;
  689. } // end saveStaticTextData
  690. // saveTextEntryData ==========================================================
  691. /** Save static text data entry */
  692. //=============================================================================
  693. static Bool saveTextEntryData( GameWindow *window, FILE *fp, Int dataIndent )
  694. {
  695. EntryData *entryData = (EntryData *)window->winGetUserData();
  696. // sanity
  697. if( entryData == NULL )
  698. {
  699. DEBUG_LOG(( "No text entry data in window to save for window %d\n",
  700. window->winGetWindowId() ));
  701. assert( 0 );
  702. return FALSE;
  703. } // end if
  704. sprintf( &buffer[ dataIndent ], "TEXTENTRYDATA = MAXLEN: %d,\n", entryData->maxTextLen );
  705. writeBufferToFile( fp, buffer );
  706. sprintf( &buffer[ dataIndent ], " SECRETTEXT: %d,\n", entryData->secretText );
  707. writeBufferToFile( fp, buffer );
  708. sprintf( &buffer[ dataIndent ], " NUMERICALONLY: %d,\n", entryData->numericalOnly );
  709. writeBufferToFile( fp, buffer );
  710. sprintf( &buffer[ dataIndent ], " ALPHANUMERICALONLY: %d,\n", entryData->alphaNumericalOnly );
  711. writeBufferToFile( fp, buffer );
  712. sprintf( &buffer[ dataIndent ], " ASCIIONLY: %d;\n", entryData->aSCIIOnly );
  713. writeBufferToFile( fp, buffer );
  714. return TRUE;
  715. } // end saveTextEntryData
  716. // saveTabControlData ==========================================================
  717. /** Save tab control entry */
  718. //=============================================================================
  719. static Bool saveTabControlData( GameWindow *window, FILE *fp, Int dataIndent )
  720. {
  721. TabControlData *tabControlData = (TabControlData *)window->winGetUserData();
  722. // sanity
  723. if( tabControlData == NULL )
  724. {
  725. DEBUG_LOG(( "No text entry data in window to save for window %d\n",
  726. window->winGetWindowId() ));
  727. assert( 0 );
  728. return FALSE;
  729. } // end if
  730. sprintf( &buffer[ dataIndent ], "TABCONTROLDATA = TABORIENTATION: %d,\n", tabControlData->tabOrientation );
  731. writeBufferToFile( fp, buffer );
  732. sprintf( &buffer[ dataIndent ], " TABEDGE: %d,\n", tabControlData->tabEdge );
  733. writeBufferToFile( fp, buffer );
  734. sprintf( &buffer[ dataIndent ], " TABWIDTH: %d,\n", tabControlData->tabWidth );
  735. writeBufferToFile( fp, buffer );
  736. sprintf( &buffer[ dataIndent ], " TABHEIGHT: %d,\n", tabControlData->tabHeight );
  737. writeBufferToFile( fp, buffer );
  738. sprintf( &buffer[ dataIndent ], " TABCOUNT: %d,\n", tabControlData->tabCount );
  739. writeBufferToFile( fp, buffer );
  740. sprintf( &buffer[ dataIndent ], " PANEBORDER: %d,\n", tabControlData->paneBorder );
  741. writeBufferToFile( fp, buffer );
  742. sprintf( &buffer[ dataIndent ], " PANEDISABLED: %d,", NUM_TAB_PANES );//number of entries to follow
  743. writeBufferToFile( fp, buffer );
  744. for( Int paneIndex = 0; paneIndex < NUM_TAB_PANES; paneIndex ++ )
  745. {
  746. if( paneIndex == NUM_TAB_PANES - 1 )
  747. sprintf( &buffer[ dataIndent ], "%d;", tabControlData->subPaneDisabled[paneIndex] );
  748. else
  749. sprintf( &buffer[ dataIndent ], "%d,", tabControlData->subPaneDisabled[paneIndex] );
  750. writeBufferToFile( fp, buffer );
  751. }
  752. sprintf( &buffer[ dataIndent ], "\n" );
  753. writeBufferToFile( fp, buffer );
  754. return TRUE;
  755. }
  756. // saveGadgetData =============================================================
  757. /** Save data for specific gadgets */
  758. //=============================================================================
  759. static Bool saveGadgetData( GameWindow *window, FILE *fp, Int dataIndent )
  760. {
  761. if( BitTest( window->winGetStyle(), GWS_SCROLL_LISTBOX ) )
  762. return saveListboxData( window, fp, dataIndent );
  763. else if( BitTest( window->winGetStyle(), GWS_COMBO_BOX ) )
  764. return saveComboBoxData( window, fp, dataIndent );
  765. else if( BitTest( window->winGetStyle(), GWS_RADIO_BUTTON ) )
  766. return saveRadioButtonData( window, fp, dataIndent );
  767. else if( BitTest( window->winGetStyle(), GWS_VERT_SLIDER |
  768. GWS_HORZ_SLIDER ) )
  769. return saveSliderData( window, fp, dataIndent );
  770. else if( BitTest( window->winGetStyle(), GWS_STATIC_TEXT ) )
  771. return saveStaticTextData( window, fp, dataIndent );
  772. else if( BitTest( window->winGetStyle(), GWS_ENTRY_FIELD ) )
  773. return saveTextEntryData( window, fp, dataIndent );
  774. else if( BitTest( window->winGetStyle(), GWS_TAB_CONTROL ) )
  775. return saveTabControlData( window, fp, dataIndent );
  776. return TRUE;
  777. } // end saveGadgetData
  778. // saveWindow =================================================================
  779. /** Save a single window and any of its child windows. Note that child
  780. * widows are saved in reverse order just as the main window list is
  781. * so that the same widow will be restored upon loading */
  782. //=============================================================================
  783. static Bool saveWindow( FILE *fp, GameWindow *window, Int indent )
  784. {
  785. GameWindow *child;
  786. Bool success = TRUE;
  787. Int dataIndent = indent + INDENT_SIZE;
  788. // WinInstanceData *instData = window->winGetInstanceData();
  789. // clear the buffer with all spaces
  790. clearBufferToSpaces();
  791. // start window definition
  792. sprintf( &buffer[ indent ], "WINDOW\n" );
  793. writeBufferToFile( fp, buffer );
  794. clearBufferToSpaces();
  795. // save the this window data
  796. saveType( window, fp, dataIndent );
  797. savePosition( window, fp, dataIndent );
  798. saveName( window, fp, dataIndent );
  799. saveStatus( window, fp, dataIndent );
  800. saveStyle( window, fp, dataIndent );
  801. saveCallbacks( window, fp, dataIndent );
  802. saveFont( window, fp, dataIndent );
  803. saveHeaderTemplate( window, fp, dataIndent );
  804. saveTooltipText( window, fp, dataIndent );
  805. saveTooltipDelay( window, fp, dataIndent );
  806. saveText( window, fp, dataIndent );
  807. saveTextColor( window, fp, dataIndent );
  808. saveDrawData( "ENABLEDDRAWDATA", window, fp, dataIndent );
  809. saveDrawData( "DISABLEDDRAWDATA", window, fp, dataIndent );
  810. saveDrawData( "HILITEDRAWDATA", window, fp, dataIndent );
  811. if( BitTest( window->winGetStyle(), GWS_TAB_CONTROL ) )
  812. {//Seems cleaner to put this before the children list since this Gadget needs both
  813. saveGadgetData( window, fp, dataIndent );
  814. }
  815. //
  816. // save child data if present, we do not save child data of GUI controls
  817. // themselves, only generic stuff, except for the Tab Control again, which
  818. // is the gadget with children exception
  819. //
  820. if( (TheEditor->windowIsGadget( window ) == FALSE) || BitTest(window->winGetStyle(), GWS_TAB_CONTROL) )
  821. {
  822. child = window->winGetChild();
  823. if( child )
  824. {
  825. // traverse to end of child list
  826. while( child->winGetNext() != NULL )
  827. child = child->winGetNext();
  828. // save children windows in reverse order
  829. while( child )
  830. {
  831. // write child marker
  832. sprintf( &buffer[ dataIndent ], "CHILD\n" );
  833. writeBufferToFile( fp, buffer );
  834. // save child data
  835. success = saveWindow( fp, child, indent + INDENT_SIZE );
  836. if( success == FALSE )
  837. break;
  838. // previous child
  839. child = child->winGetPrev();
  840. } // end while
  841. // all children saved
  842. sprintf( &buffer[ dataIndent ], "ENDALLCHILDREN\n" );
  843. writeBufferToFile( fp, buffer );
  844. } // end if, children present
  845. } // end if
  846. else
  847. {
  848. // save specific gadget data
  849. saveGadgetData( window, fp, dataIndent );
  850. } // end else
  851. // end of window definition
  852. sprintf( &buffer[ indent ], "END\n" );
  853. writeBufferToFile( fp, buffer );
  854. return success;
  855. } // end saveWindow
  856. // GUIEdit::validateNames =====================================================
  857. /** Stored in the m_decorated field for each window is a name given
  858. * by the user. When we write this name into the window file it
  859. * will be prefixed by the filename and a : such as (MainMenu.wnd:OKButton).
  860. * When we re-load these window definitions the whole decorated name
  861. * will be read and loaded into the decorated name field, therefore we
  862. * must make sure the entire name once decorated will fit into the field
  863. */
  864. //=============================================================================
  865. void GUIEdit::validateNames( GameWindow *root, char *filename, Bool *valid )
  866. {
  867. // the end of recursion
  868. if( root == NULL )
  869. return;
  870. // trivial case
  871. if( strlen( filename ) >= MAX_WINDOW_NAME_LEN )
  872. {
  873. sprintf( offendingNames, "Filename '%s' is too long. The max is '%d' for filename AND window name!\n",
  874. filename, MAX_WINDOW_NAME_LEN );
  875. *valid = FALSE;
  876. return;
  877. } // end if
  878. // check this name for too long
  879. WinInstanceData *instData = root->winGetInstanceData();
  880. if( strlen( filename ) + instData->m_decoratedNameString.getLength() >= MAX_WINDOW_NAME_LEN )
  881. {
  882. strcat( offendingNames, "[Too Long] " );
  883. strcat( offendingNames, filename );
  884. strcat( offendingNames, ":" );
  885. strcat( offendingNames, instData->m_decoratedNameString.str() );
  886. strcat( offendingNames, "\n");
  887. *valid = FALSE;
  888. } // end if
  889. // check for a duplicate filename
  890. if( TheEditor->isNameDuplicate( TheWindowManager->winGetWindowList(),
  891. root, instData->m_decoratedNameString ) )
  892. {
  893. strcat( offendingNames, "[Duplicate] " );
  894. strcat( offendingNames, filename );
  895. strcat( offendingNames, ":" );
  896. strcat( offendingNames, instData->m_decoratedNameString.str() );
  897. strcat( offendingNames, "\n" );
  898. *valid = FALSE;
  899. } // end if
  900. //You only call this on the first child since the call right after it will handle siblings (depth first)
  901. GameWindow *child = root->winGetChild();
  902. validateNames( child, filename, valid );
  903. // onto the next window
  904. validateNames( root->winGetNext(), filename, valid );
  905. } // end validateNames
  906. // GUIEdit::updateRadioScreenIdentifiers ======================================
  907. /** update all radio button screen identifiers with the new identifier */
  908. //=============================================================================
  909. void GUIEdit::updateRadioScreenIdentifiers( GameWindow *window, Int screenID )
  910. {
  911. // end recursion
  912. if( window == NULL )
  913. return;
  914. // is this a radio button
  915. if( BitTest( window->winGetStyle(), GWS_RADIO_BUTTON ) )
  916. {
  917. RadioButtonData *radioData = (RadioButtonData *)window->winGetUserData();
  918. GadgetRadioSetGroup( window, radioData->group, screenID );
  919. } // end if
  920. // check our children
  921. GameWindow *child;
  922. for( child = window->winGetChild(); child; child = child->winGetNext() )
  923. updateRadioScreenIdentifiers( child, screenID );
  924. // check the next one
  925. updateRadioScreenIdentifiers( window->winGetNext(), screenID );
  926. } // end updateRadioScreenIdentifiers
  927. //-------------------------------------------------------------------------------------------------
  928. /** Write layout block for a window file */
  929. //-------------------------------------------------------------------------------------------------
  930. static void writeLayoutBlock( FILE *fp )
  931. {
  932. // start marker
  933. fprintf( fp, "STARTLAYOUTBLOCK\n" );
  934. // callback methods
  935. fprintf( fp, " LAYOUTINIT = %s;\n", TheEditor->getLayoutInit().str() );
  936. fprintf( fp, " LAYOUTUPDATE = %s;\n", TheEditor->getLayoutUpdate().str() );
  937. fprintf( fp, " LAYOUTSHUTDOWN = %s;\n", TheEditor->getLayoutShutdown().str() );
  938. // end marker
  939. fprintf( fp, "ENDLAYOUTBLOCK\n" );
  940. } // end writeLayoutBlock
  941. // GUIEdit::saveData ==========================================================
  942. /** Save all our data to the file specified in filePath, which is a full
  943. * absolute path to a filename */
  944. //=============================================================================
  945. Bool GUIEdit::saveData( char *filePathAndFilename, char *filename )
  946. {
  947. Int version = WindowLayoutCurrentVersion;
  948. FILE *fp;
  949. GameWindow *window;
  950. Bool success = TRUE;
  951. // write the editor config file
  952. writeConfigFile( GUIEDIT_CONFIG_FILENAME );
  953. // write our loaded fonts into the font file if we can
  954. writeFontFile( GUIEDIT_FONT_FILENAME );
  955. // sanity
  956. if( filePathAndFilename == NULL )
  957. return FALSE;
  958. // check for empty layout and just get out of here
  959. window = TheWindowManager->winGetWindowList();
  960. if( window == NULL )
  961. return TRUE;
  962. // check all the names for sizes once decorated with filename
  963. Bool valid = TRUE;
  964. sprintf( offendingNames, "\nOne or more window names are illegal. A window name PLUS the filename must be under '%d' characters and names cannot be duplicates.\n\nList of illegal window names:\n\n",
  965. MAX_WINDOW_NAME_LEN );
  966. validateNames( window, filename, &valid );
  967. if( valid == FALSE )
  968. {
  969. MessageBox( TheEditor->getWindowHandle(), offendingNames, "Window Name Error", MB_OK );
  970. return FALSE;
  971. } // end if
  972. // update all radio button screen identifiers with the filename
  973. updateRadioScreenIdentifiers( TheWindowManager->winGetWindowList(),
  974. TheNameKeyGenerator->nameToKey( AsciiString(m_saveFilename) ) );
  975. // open the file
  976. fp = fopen( filePathAndFilename, "w" );
  977. if( fp == NULL )
  978. return FALSE;
  979. // write out a single line for our window file version
  980. fprintf( fp, "FILE_VERSION = %d;\n", version );
  981. // write the layout block for the file
  982. writeLayoutBlock( fp );
  983. //
  984. // save each of the windows in reverse order, when we load a layout
  985. // file in this reverse order, the original window order we presently
  986. // see in the editor will be recreated because windows loaded after
  987. // other windows are placed on the top of the widnow stack
  988. //
  989. // go to end of window list
  990. window = TheWindowManager->winGetWindowList();
  991. while( window->winGetNext() != NULL )
  992. window = window->winGetNext();
  993. // loop backwards saving all windows
  994. while( window )
  995. {
  996. success = saveWindow( fp, window, 0 );
  997. if( success == FALSE )
  998. break;
  999. window = window->winGetPrev();
  1000. } // end while
  1001. // close the file
  1002. fclose( fp );
  1003. return success;
  1004. } // end saveData
  1005. ///////////////////////////////////////////////////////////////////////////////
  1006. // PUBLIC FUNCTIONS ///////////////////////////////////////////////////////////
  1007. ///////////////////////////////////////////////////////////////////////////////