# cheat_gui.cpp

Go to the documentation of this file.

    00001 /* $Id: cheat_gui.cpp 15564 2009-02-23 22:00:29Z yexo $ */
    00002
    00005 #include "stdafx.h"
    00006 #include "command_func.h"
    00007 #include "cheat_type.h"
    00008 #include "company_base.h"
    00009 #include "company_func.h"
    00010 #include "gfx_func.h"
    00011 #include "date_func.h"
    00012 #include "saveload/saveload.h"
    00013 #include "window_gui.h"
    00014 #include "newgrf.h"
    00015 #include "settings_type.h"
    00016 #include "strings_func.h"
    00017 #include "window_func.h"
    00018 #include "rail_gui.h"
    00019 #include "gui.h"
    00020 #include "company_gui.h"
    00021 #include "gamelog.h"
    00022
    00023 #include "table/strings.h"
    00024 #include "table/sprites.h"
    00025
    00026
    00032 static int32 _money_cheat_amount = 10000000;
    00033
    00034 static int32 ClickMoneyCheat(int32 p1, int32 p2)
    00035 {
    00036   DoCommandP(0, (uint32)(p2 * _money_cheat_amount), 0, CMD_MONEY_CHEAT);
    00037   return _money_cheat_amount;
    00038 }
    00039
    00044 static int32 ClickChangeCompanyCheat(int32 p1, int32 p2)
    00045 {
    00046   while ((uint)p1 < GetCompanyPoolSize()) {
    00047     if (IsValidCompanyID((CompanyID)p1)) {
    00048       SetLocalCompany((CompanyID)p1);
    00049       return _local_company;
    00050     }
    00051     p1 += p2;
    00052   }
    00053
    00054   return _local_company;
    00055 }
    00056
    00061 static int32 ClickSetProdCheat(int32 p1, int32 p2)
    00062 {
    00063   InvalidateWindowClasses(WC_INDUSTRY_VIEW);
    00064   return p1;
    00065 }
    00066
    00071 static int32 ClickChangeClimateCheat(int32 p1, int32 p2)
    00072 {
    00073   if (p1 == -1) p1 = 3;
    00074   if (p1 ==  4) p1 = 0;
    00075   _settings_game.game_creation.landscape = p1;
    00076
    00077   GamelogStartAction(GLAT_CHEAT);
    00078   GamelogTestMode();
    00079   ReloadNewGRFData();
    00080   GamelogStopAction();
    00081
    00082   return _settings_game.game_creation.landscape;
    00083 }
    00084
    00085 extern void EnginesMonthlyLoop();
    00086
    00091 static int32 ClickChangeDateCheat(int32 p1, int32 p2)
    00092 {
    00093   YearMonthDay ymd;
    00094   ConvertDateToYMD(_date, &ymd);
    00095
    00096   if ((ymd.year == MIN_YEAR && p2 == -1) || (ymd.year == MAX_YEAR && p2 == 1)) return _cur_year;
    00097
    00098   SetDate(ConvertYMDToDate(_cur_year + p2, ymd.month, ymd.day));
    00099   EnginesMonthlyLoop();
    00100   SetWindowDirty(FindWindowById(WC_STATUS_BAR, 0));
    00101   ResetSignalVariant();
    00102   return _cur_year;
    00103 }
    00104
    00105 typedef int32 CheckButtonClick(int32, int32);
    00106
    00107 struct CheatEntry {
    00108   VarType type;
    00109   StringID str;
    00110   void *variable;
    00111   bool *been_used;
    00112   CheckButtonClick *proc;
    00113 };
    00114
    00115 static const CheatEntry _cheats_ui[] = {
    00116   {SLE_INT32, STR_CHEAT_MONEY,           &_money_cheat_amount,                    &_cheats.money.been_used,            &ClickMoneyCheat         },
    00117   {SLE_UINT8, STR_CHEAT_CHANGE_COMPANY,  &_local_company,                         &_cheats.switch_company.been_used,   &ClickChangeCompanyCheat },
    00118   {SLE_BOOL,  STR_CHEAT_EXTRA_DYNAMITE,  &_cheats.magic_bulldozer.value,          &_cheats.magic_bulldozer.been_used,  NULL                     },
    00119   {SLE_BOOL,  STR_CHEAT_CROSSINGTUNNELS, &_cheats.crossing_tunnels.value,         &_cheats.crossing_tunnels.been_used, NULL                     },
    00120   {SLE_BOOL,  STR_CHEAT_BUILD_IN_PAUSE,  &_cheats.build_in_pause.value,           &_cheats.build_in_pause.been_used,   NULL                     },
    00121   {SLE_BOOL,  STR_CHEAT_NO_JETCRASH,     &_cheats.no_jetcrash.value,              &_cheats.no_jetcrash.been_used,      NULL                     },
    00122   {SLE_BOOL,  STR_CHEAT_SETUP_PROD,      &_cheats.setup_prod.value,               &_cheats.setup_prod.been_used,       &ClickSetProdCheat       },
    00123   {SLE_UINT8, STR_CHEAT_SWITCH_CLIMATE,  &_settings_game.game_creation.landscape, &_cheats.switch_climate.been_used,   &ClickChangeClimateCheat },
    00124   {SLE_INT32, STR_CHEAT_CHANGE_DATE,     &_cur_year,                              &_cheats.change_date.been_used,      &ClickChangeDateCheat    },
    00125 };
    00126
    00127
    00128 static const Widget _cheat_widgets[] = {
    00129 {   WWT_CLOSEBOX,   RESIZE_NONE,  COLOUR_GREY,     0,    10,     0,    13, STR_00C5,   STR_018B_CLOSE_WINDOW},
    00130 {    WWT_CAPTION,   RESIZE_NONE,  COLOUR_GREY,    11,   399,     0,    13, STR_CHEATS, STR_018C_WINDOW_TITLE_DRAG_THIS},
    00131 {      WWT_PANEL,   RESIZE_NONE,  COLOUR_GREY,     0,   399,    14,   169, 0x0,        STR_NULL},
    00132 {      WWT_PANEL,   RESIZE_NONE,  COLOUR_GREY,     0,   399,    14,   169, 0x0,        STR_CHEATS_TIP},
    00133 {   WIDGETS_END},
    00134 };
    00135
    00136 struct CheatWindow : Window {
    00137   int clicked;
    00138
    00139   CheatWindow(const WindowDesc *desc) : Window(desc)
    00140   {
    00141     this->FindWindowPlacementAndResize(desc);
    00142   }
    00143
    00144   virtual void OnPaint()
    00145   {
    00146     this->DrawWidgets();
    00147     DrawStringMultiCenter(200, 25, STR_CHEATS_WARNING, width - 50);
    00148
    00149     for (int i = 0, x = 0, y = 45; i != lengthof(_cheats_ui); i++) {
    00150       const CheatEntry *ce = &_cheats_ui[i];
    00151
    00152       DrawSprite((*ce->been_used) ? SPR_BOX_CHECKED : SPR_BOX_EMPTY, PAL_NONE, x + 5, y + 2);
    00153
    00154       switch (ce->type) {
    00155         case SLE_BOOL: {
    00156           bool on = (*(bool*)ce->variable);
    00157
    00158           DrawFrameRect(x + 20, y + 1, x + 30 + 9, y + 9, on ? COLOUR_GREEN : COLOUR_RED, on ? FR_LOWERED : FR_NONE);
    00159           SetDParam(0, on ? STR_CONFIG_SETTING_ON : STR_CONFIG_SETTING_OFF);
    00160         } break;
    00161
    00162         default: {
    00163           int32 val = (int32)ReadValue(ce->variable, ce->type);
    00164           char buf[512];
    00165
    00166           /* Draw [<][>] boxes for settings of an integer-type */
    00167           DrawArrowButtons(x + 20, y, COLOUR_YELLOW, clicked - (i * 2), true, true);
    00168
    00169           switch (ce->str) {
    00170             /* Display date for change date cheat */
    00171             case STR_CHEAT_CHANGE_DATE: SetDParam(0, _date); break;
    00172
    00173             /* Draw coloured flag for change company cheat */
    00174             case STR_CHEAT_CHANGE_COMPANY:
    00175               SetDParam(0, val + 1);
    00176               GetString(buf, STR_CHEAT_CHANGE_COMPANY, lastof(buf));
    00177               DrawCompanyIcon(_local_company, 60 + GetStringBoundingBox(buf).width, y + 2);
    00178               break;
    00179
    00180             /* Set correct string for switch climate cheat */
    00181             case STR_CHEAT_SWITCH_CLIMATE: val += STR_TEMPERATE_LANDSCAPE;
    00182
    00183             /* Fallthrough */
    00184             default: SetDParam(0, val);
    00185           }
    00186         } break;
    00187       }
    00188
    00189       DrawString(50, y + 1, ce->str, TC_FROMSTRING);
    00190
    00191       y += 12;
    00192     }
    00193   }
    00194
    00195   virtual void OnClick(Point pt, int widget)
    00196   {
    00197     uint btn = (pt.y - 46) / 12;
    00198     uint x = pt.x;
    00199
    00200     /* Not clicking a button? */
    00201     if (!IsInsideMM(x, 20, 40) || btn >= lengthof(_cheats_ui)) return;
    00202
    00203     const CheatEntry *ce = &_cheats_ui[btn];
    00204     int value = (int32)ReadValue(ce->variable, ce->type);
    00205     int oldvalue = value;
    00206
    00207     *ce->been_used = true;
    00208
    00209     switch (ce->type) {
    00210       case SLE_BOOL:
    00211         value ^= 1;
    00212         if (ce->proc != NULL) ce->proc(value, 0);
    00213         break;
    00214
    00215       default:
    00216         /* Take whatever the function returns */
    00217         value = ce->proc(value + ((x >= 30) ? 1 : -1), (x >= 30) ? 1 : -1);
    00218
    00219         /* The first cheat (money), doesn't return a different value. */
    00220         if (value != oldvalue || btn == 0) this->clicked = btn * 2 + 1 + ((x >= 30) ? 1 : 0);
    00221         break;
    00222     }
    00223
    00224     if (value != oldvalue) WriteValue(ce->variable, ce->type, (int64)value);
    00225
    00226     this->flags4 |= WF_TIMEOUT_BEGIN;
    00227
    00228     SetDirty();
    00229   }
    00230
    00231   virtual void OnTimeout()
    00232   {
    00233     this->clicked = 0;
    00234     this->SetDirty();
    00235   }
    00236 };
    00237
    00238 static const WindowDesc _cheats_desc = {
    00239   240, 22, 400, 170, 400, 170,
    00240   WC_CHEATS, WC_NONE,
    00241   WDF_STD_TOOLTIPS | WDF_STD_BTN | WDF_DEF_WIDGET | WDF_UNCLICK_BUTTONS,
    00242   _cheat_widgets,
    00243 };
    00244
    00245
    00246 void ShowCheatWindow()
    00247 {
    00248   DeleteWindowById(WC_CHEATS, 0);
    00249   new CheatWindow(&_cheats_desc);
    00250 }