settings_gui.c
changeset 543 946badd71033
parent 536 03d80fecb999
child 545 ab2098c1da75
equal deleted inserted replaced
542:de27e74b11bd 543:946badd71033
     6 #include "gfx.h"
     6 #include "gfx.h"
     7 #include "command.h"
     7 #include "command.h"
     8 #include "engine.h"
     8 #include "engine.h"
     9 #include "screenshot.h"
     9 #include "screenshot.h"
    10 #include "newgrf.h"
    10 #include "newgrf.h"
       
    11 #include "network.h"
    11 
    12 
    12 static uint32 _difficulty_click_a;
    13 static uint32 _difficulty_click_a;
    13 static uint32 _difficulty_click_b;
    14 static uint32 _difficulty_click_b;
    14 static byte _difficulty_timeout;
    15 static byte _difficulty_timeout;
    15 
    16 
   293 	uint32 x = *b;
   294 	uint32 x = *b;
   294 	*b >>= 1;
   295 	*b >>= 1;
   295 	return (x&1) != 0;
   296 	return (x&1) != 0;
   296 }
   297 }
   297 
   298 
   298 static GameOptions _opt_mod_temp;
       
   299 
       
   300 static const int16 _default_game_diff[3][GAME_DIFFICULTY_NUM] = {
   299 static const int16 _default_game_diff[3][GAME_DIFFICULTY_NUM] = {
   301 	{2, 2, 1, 3, 300, 2, 0, 2, 0, 1, 2, 0, 1, 0, 0, 0, 0, 0},
   300 	{2, 2, 1, 3, 300, 2, 0, 2, 0, 1, 2, 0, 1, 0, 0, 0, 0, 0},
   302 	{4, 1, 1, 2, 150, 3, 1, 3, 1, 2, 1, 1, 2, 1, 1, 1, 1, 1},
   301 	{4, 1, 1, 2, 150, 3, 1, 3, 1, 2, 1, 1, 2, 1, 1, 1, 1, 1},
   303 	{7, 0, 2, 2, 100, 4, 1, 3, 2, 2, 0, 2, 3, 2, 1, 1, 1, 2},
   302 	{7, 0, 2, 2, 100, 4, 1, 3, 2, 2, 0, 2, 3, 2, 1, 1, 1, 2},
   304 };
   303 };
   325 		int i;
   324 		int i;
   326 		int x,y,value;
   325 		int x,y,value;
   327 
   326 
   328 		w->click_state = (1 << 4) << _opt_mod_temp.diff_level;
   327 		w->click_state = (1 << 4) << _opt_mod_temp.diff_level;
   329 		w->disabled_state = (_game_mode != GM_NORMAL) ? 0 : (1 << 4) | (1 << 5) | (1 << 6) | (1 << 7);
   328 		w->disabled_state = (_game_mode != GM_NORMAL) ? 0 : (1 << 4) | (1 << 5) | (1 << 6) | (1 << 7);
       
   329 		// Disable save-button in multiplayer (and if client)
       
   330 		if (_networking && !_network_server)
       
   331 			w->disabled_state |= (1 << 10);
   330 		DrawWindowWidgets(w);
   332 		DrawWindowWidgets(w);
   331 
   333 
   332 		click_a = _difficulty_click_a;
   334 		click_a = _difficulty_click_a;
   333 		click_b = _difficulty_click_b;
   335 		click_b = _difficulty_click_b;
   334 
   336 
       
   337 		/* XXX - This is most likely the worst way I have ever seen
       
   338 		     to disable some buttons and to enable others.
       
   339 		     What the value means, is this:
       
   340 		       if bit1 is enabled, setting 1 is disabled
       
   341 		       then it is shifted to the left, and the story
       
   342 		       repeats....
       
   343 		   -- TrueLight */
   335 		disabled = _game_mode == GM_NORMAL ? 0x383E : 0;
   344 		disabled = _game_mode == GM_NORMAL ? 0x383E : 0;
   336 		// XXX
       
   337 
   345 
   338 		x = 0;
   346 		x = 0;
   339 		y = 32;
   347 		y = 32;
   340 		for (i = 0; i != GAME_DIFFICULTY_NUM; i++) {
   348 		for (i = 0; i != GAME_DIFFICULTY_NUM; i++) {
   341 			DrawFrameRect(x+5, y+1, x+5+9, y+9, 3, GetBitAndShift(&click_a)?0x20:0);
   349 			DrawFrameRect(x+5, y+1, x+5+9, y+9, 3, GetBitAndShift(&click_a)?0x20:0);
   342 			DrawFrameRect(x+15, y+1, x+15+9, y+9, 3, GetBitAndShift(&click_b)?0x20:0);
   350 			DrawFrameRect(x+15, y+1, x+15+9, y+9, 3, GetBitAndShift(&click_b)?0x20:0);
   343 			if (GetBitAndShift(&disabled)) {
   351 			if (GetBitAndShift(&disabled) || (_networking && !_network_server)) {
   344 				int color = 0x8000 | _color_list[3].unk2;
   352 				int color = 0x8000 | _color_list[3].unk2;
   345 				GfxFillRect(x+6, y+2, x+6+8, y+9, color);
   353 				GfxFillRect(x+6, y+2, x+6+8, y+9, color);
   346 				GfxFillRect(x+16, y+2, x+16+8, y+9, color);
   354 				GfxFillRect(x+16, y+2, x+16+8, y+9, color);
   347 			}
   355 			}
   348 
   356 
   364 		case 3: {
   372 		case 3: {
   365 			int x,y;
   373 			int x,y;
   366 			uint btn, dis;
   374 			uint btn, dis;
   367 			int val;
   375 			int val;
   368 			const GameSettingData *info;
   376 			const GameSettingData *info;
       
   377 
       
   378 			// Don't allow clients to make any changes
       
   379 			if  (_networking && !_network_server)
       
   380 				return;
   369 
   381 
   370 			x = e->click.pt.x - 5;
   382 			x = e->click.pt.x - 5;
   371 			if (!IS_INT_INSIDE(x, 0, 21))
   383 			if (!IS_INT_INSIDE(x, 0, 21))
   372 				return;
   384 				return;
   373 
   385 
   561 	PE_CURRENCY	= 5,
   573 	PE_CURRENCY	= 5,
   562 
   574 
   563 	PF_0ISDIS				= 1,
   575 	PF_0ISDIS				= 1,
   564 	PF_NOCOMMA			= 2,
   576 	PF_NOCOMMA			= 2,
   565 	PF_MULTISTRING	= 4,
   577 	PF_MULTISTRING	= 4,
       
   578 	PF_PLAYERBASED	= 8, // This has to match the entries that are in settings.c, patch_player_settings
   566 };
   579 };
   567 
   580 
   568 static const PatchEntry _patches_ui[] = {
   581 static const PatchEntry _patches_ui[] = {
   569 	{PE_BOOL,		0, STR_CONFIG_PATCHES_VEHICLESPEED,			&_patches.vehicle_speed,						0,  0,  0, NULL},
   582 	{PE_BOOL,		PF_PLAYERBASED, STR_CONFIG_PATCHES_VEHICLESPEED,			&_patches.vehicle_speed,						0,  0,  0, NULL},
   570 	{PE_BOOL,		0, STR_CONFIG_PATCHES_LONGDATE,					&_patches.status_long_date,					0,  0,  0, NULL},
   583 	{PE_BOOL,		PF_PLAYERBASED, STR_CONFIG_PATCHES_LONGDATE,					&_patches.status_long_date,					0,  0,  0, NULL},
   571 	{PE_BOOL,		0, STR_CONFIG_PATCHES_SHOWFINANCES,			&_patches.show_finances,						0,  0,  0, NULL},
   584 	{PE_BOOL,		PF_PLAYERBASED, STR_CONFIG_PATCHES_SHOWFINANCES,			&_patches.show_finances,						0,  0,  0, NULL},
   572 	{PE_BOOL,		0, STR_CONFIG_PATCHES_AUTOSCROLL,				&_patches.autoscroll,								0,  0,  0, NULL},
   585 	{PE_BOOL,		PF_PLAYERBASED, STR_CONFIG_PATCHES_AUTOSCROLL,				&_patches.autoscroll,								0,  0,  0, NULL},
   573 
   586 
   574 	{PE_UINT8,	0, STR_CONFIG_PATCHES_ERRMSG_DURATION,	&_patches.errmsg_duration,					0, 20,  1, NULL},
   587 	{PE_UINT8,	PF_PLAYERBASED, STR_CONFIG_PATCHES_ERRMSG_DURATION,	&_patches.errmsg_duration,					0, 20,  1, NULL},
   575 
   588 
   576 	{PE_UINT8,	PF_MULTISTRING, STR_CONFIG_PATCHES_TOOLBAR_POS, &_patches.toolbar_pos,			0,  2,  1, &v_PositionMainToolbar},
   589 	{PE_UINT8,	PF_MULTISTRING, STR_CONFIG_PATCHES_TOOLBAR_POS, &_patches.toolbar_pos,			0,  2,  1, &v_PositionMainToolbar},
   577 	{PE_UINT8, PF_0ISDIS, STR_CONFIG_PATCHES_SNAP_RADIUS, &_patches.window_snap_radius,     1, 32,  1, NULL},
   590 	{PE_UINT8,	PF_MULTISTRING | PF_PLAYERBASED, STR_CONFIG_PATCHES_TOOLBAR_POS, &_patches.toolbar_pos,			0,  2,  1, &v_PositionMainToolbar},
   578 	{PE_BOOL,		0, STR_CONFIG_PATCHES_INVISIBLE_TREES,	&_patches.invisible_trees,					0,  1,  1, &InvisibleTreesActive},
   591 	{PE_UINT8,	PF_0ISDIS, STR_CONFIG_PATCHES_SNAP_RADIUS, &_patches.window_snap_radius,     1, 32,  1, NULL},
       
   592 	{PE_BOOL,		PF_PLAYERBASED, STR_CONFIG_PATCHES_INVISIBLE_TREES,	&_patches.invisible_trees,					0,  1,  1, &InvisibleTreesActive},
   579 };
   593 };
   580 
   594 
   581 static const PatchEntry _patches_construction[] = {
   595 static const PatchEntry _patches_construction[] = {
   582 	{PE_BOOL,		0, STR_CONFIG_PATCHES_BUILDONSLOPES,		&_patches.build_on_slopes,					0,  0,  0, NULL},
   596 	{PE_BOOL,		0, STR_CONFIG_PATCHES_BUILDONSLOPES,		&_patches.build_on_slopes,					0,  0,  0, NULL},
   583 	{PE_BOOL,		0, STR_CONFIG_PATCHES_EXTRADYNAMITE,		&_patches.extra_dynamite,						0,  0,  0, NULL},
   597 	{PE_BOOL,		0, STR_CONFIG_PATCHES_EXTRADYNAMITE,		&_patches.extra_dynamite,						0,  0,  0, NULL},
   584 	{PE_BOOL,		0, STR_CONFIG_PATCHES_LONGBRIDGES,			&_patches.longbridges,							0,  0,  0, NULL},
   598 	{PE_BOOL,		0, STR_CONFIG_PATCHES_LONGBRIDGES,			&_patches.longbridges,							0,  0,  0, NULL},
   585 	{PE_BOOL,		0, STR_CONFIG_PATCHES_SIGNALSIDE,				&_patches.signal_side,							0,  0,  0, NULL},
   599 	{PE_BOOL,		0, STR_CONFIG_PATCHES_SIGNALSIDE,				&_patches.signal_side,							0,  0,  0, NULL},
   586 
   600 
   587 	{PE_BOOL,		0, STR_CONFIG_PATCHES_SMALL_AIRPORTS,		&_patches.always_small_airport,			0,  0,  0, NULL},
   601 	{PE_BOOL,		0, STR_CONFIG_PATCHES_SMALL_AIRPORTS,		&_patches.always_small_airport,			0,  0,  0, NULL},
   588 	{PE_UINT8,	0, STR_CONFIG_PATCHES_DRAG_SIGNALS_DENSITY, &_patches.drag_signals_density, 1, 20,  1, NULL},
   602 	{PE_UINT8,	PF_PLAYERBASED, STR_CONFIG_PATCHES_DRAG_SIGNALS_DENSITY, &_patches.drag_signals_density, 1, 20,  1, NULL},
   589 
   603 
   590 };
   604 };
   591 
   605 
   592 static const PatchEntry _patches_vehicles[] = {
   606 static const PatchEntry _patches_vehicles[] = {
   593 	{PE_BOOL,		0, STR_CONFIG_PATCHES_REALISTICACCEL,		&_patches.realistic_acceleration,		0,  0,  0, NULL},
   607 	{PE_BOOL,		0, STR_CONFIG_PATCHES_REALISTICACCEL,		&_patches.realistic_acceleration,		0,  0,  0, NULL},
   595 	{PE_BOOL,		0, STR_CONFIG_PATCHES_GOTODEPOT,				&_patches.gotodepot,								0,  0,  0, NULL},
   609 	{PE_BOOL,		0, STR_CONFIG_PATCHES_GOTODEPOT,				&_patches.gotodepot,								0,  0,  0, NULL},
   596 	{PE_BOOL,		0, STR_CONFIG_PATCHES_ROADVEH_QUEUE,		&_patches.roadveh_queue,						0,  0,  0, NULL},
   610 	{PE_BOOL,		0, STR_CONFIG_PATCHES_ROADVEH_QUEUE,		&_patches.roadveh_queue,						0,  0,  0, NULL},
   597 	{PE_BOOL,		0, STR_CONFIG_PATCHES_NEW_DEPOT_FINDING,&_patches.new_depot_finding,				0,  0,  0, NULL},
   611 	{PE_BOOL,		0, STR_CONFIG_PATCHES_NEW_DEPOT_FINDING,&_patches.new_depot_finding,				0,  0,  0, NULL},
   598 	{PE_BOOL,		0, STR_CONFIG_PATCHES_NEW_TRAIN_PATHFIND,				&_patches.new_pathfinding,	0,  0,  0, NULL},
   612 	{PE_BOOL,		0, STR_CONFIG_PATCHES_NEW_TRAIN_PATHFIND,				&_patches.new_pathfinding,	0,  0,  0, NULL},
   599 
   613 
   600 	{PE_BOOL,		0, STR_CONFIG_PATCHES_WARN_INCOME_LESS, &_patches.train_income_warn,				0,  0,  0, NULL},
   614 	{PE_BOOL,		PF_PLAYERBASED, STR_CONFIG_PATCHES_WARN_INCOME_LESS, &_patches.train_income_warn,				0,  0,  0, NULL},
   601 	{PE_UINT8,	PF_MULTISTRING, STR_CONFIG_PATCHES_ORDER_REVIEW,&_patches.order_review_system,0,2,  1, NULL},
   615 	{PE_UINT8,	PF_MULTISTRING | PF_PLAYERBASED, STR_CONFIG_PATCHES_ORDER_REVIEW,&_patches.order_review_system,0,2,  1, NULL},
   602 	{PE_BOOL,		0, STR_CONFIG_PATCHES_NEVER_EXPIRE_VEHICLES,		&_patches.never_expire_vehicles,0,0,0, NULL},
   616 	{PE_BOOL,		0, STR_CONFIG_PATCHES_NEVER_EXPIRE_VEHICLES,		&_patches.never_expire_vehicles,0,0,0, NULL},
   603 
   617 
   604 	{PE_UINT16, PF_0ISDIS, STR_CONFIG_PATCHES_LOST_TRAIN_DAYS, &_patches.lost_train_days,	180,720, 60, NULL},
   618 	{PE_UINT16, PF_0ISDIS | PF_PLAYERBASED, STR_CONFIG_PATCHES_LOST_TRAIN_DAYS, &_patches.lost_train_days,	180,720, 60, NULL},
   605 	{PE_BOOL,		0, STR_CONFIG_PATCHES_AUTORENEW_VEHICLE,&_patches.autorenew,								0,  0,  0, NULL},
   619 	{PE_BOOL,		0, STR_CONFIG_PATCHES_AUTORENEW_VEHICLE,&_patches.autorenew,								0,  0,  0, NULL},
   606 	{PE_INT16,	0, STR_CONFIG_PATCHES_AUTORENEW_MONTHS, &_patches.autorenew_months,				-12, 12,  1, NULL},
   620 	{PE_INT16,	0, STR_CONFIG_PATCHES_AUTORENEW_MONTHS, &_patches.autorenew_months,				-12, 12,  1, NULL},
   607 	{PE_CURRENCY, 0, STR_CONFIG_PATCHES_AUTORENEW_MONEY,&_patches.autorenew_money,					0, 2000000, 100000, NULL},
   621 	{PE_CURRENCY, 0, STR_CONFIG_PATCHES_AUTORENEW_MONEY,&_patches.autorenew_money,					0, 2000000, 100000, NULL},
   608 
   622 
   609 	{PE_UINT8,	0, STR_CONFIG_PATCHES_MAX_TRAINS,				&_patches.max_trains,								0,240, 10, NULL},
   623 	{PE_UINT8,	0, STR_CONFIG_PATCHES_MAX_TRAINS,				&_patches.max_trains,								0,240, 10, NULL},
   726 									*(int32*)pe->variable = (int32)pe->min;
   740 									*(int32*)pe->variable = (int32)pe->min;
   727 								else
   741 								else
   728 									*(int32*)pe->variable = val;
   742 									*(int32*)pe->variable = val;
   729 								break;
   743 								break;
   730 
   744 
   731 	case PE_CURRENCY: val /= GetCurrentCurrencyRate();
   745 	case PE_CURRENCY: if ((int64)val > (int64)pe->max)
   732 								if ((int64)val > (int64)pe->max)
       
   733 									*(int64*)pe->variable = (int64)pe->max;
   746 									*(int64*)pe->variable = (int64)pe->max;
   734 								else if ((int64)val < (int64)pe->min)
   747 								else if ((int64)val < (int64)pe->min)
   735 									*(int64*)pe->variable = (int64)pe->min;
   748 									*(int64*)pe->variable = (int64)pe->min;
   736 								else
   749 								else
   737 									*(int64*)pe->variable = val;
   750 									*(int64*)pe->variable = val;
   760 		y = 46;
   773 		y = 46;
   761 		clk = WP(w,def_d).data_2;
   774 		clk = WP(w,def_d).data_2;
   762 		page = &_patches_page[WP(w,def_d).data_1];
   775 		page = &_patches_page[WP(w,def_d).data_1];
   763 		for(i=0,pe=page->entries; i!=page->num; i++,pe++) {
   776 		for(i=0,pe=page->entries; i!=page->num; i++,pe++) {
   764 			bool disabled = false;
   777 			bool disabled = false;
       
   778 			bool editable = true;
       
   779 			// We do not allow changes of some items when we are a client in a networkgame
       
   780 			if (!(pe->flags & PF_PLAYERBASED) && _networking && !_network_server)
       
   781 				editable = false;
   765 			if (pe->type == PE_BOOL) {
   782 			if (pe->type == PE_BOOL) {
   766 				DrawFrameRect(x+5, y+1, x+15+9, y+9, (*(bool*)pe->variable)?6:4, (*(bool*)pe->variable)?0x20:0);
   783 				if (editable)
       
   784 					DrawFrameRect(x+5, y+1, x+15+9, y+9, (*(bool*)pe->variable)?6:4, (*(bool*)pe->variable)?0x20:0);
       
   785 				else
       
   786 					DrawFrameRect(x+5, y+1, x+15+9, y+9, (*(bool*)pe->variable)?7:9, (*(bool*)pe->variable)?0x20:0);
   767 				SetDParam(0, *(bool*)pe->variable ? STR_CONFIG_PATCHES_ON : STR_CONFIG_PATCHES_OFF);
   787 				SetDParam(0, *(bool*)pe->variable ? STR_CONFIG_PATCHES_ON : STR_CONFIG_PATCHES_OFF);
   768 			} else {
   788 			} else {
   769 				DrawFrameRect(x+5, y+1, x+5+9, y+9, 3, clk == i*2+1 ? 0x20 : 0);
   789 				DrawFrameRect(x+5, y+1, x+5+9, y+9, 3, clk == i*2+1 ? 0x20 : 0);
   770 				DrawFrameRect(x+15, y+1, x+15+9, y+9, 3, clk == i*2+2 ? 0x20 : 0);
   790 				DrawFrameRect(x+15, y+1, x+15+9, y+9, 3, clk == i*2+2 ? 0x20 : 0);
       
   791 				if (!editable) {
       
   792 					int color = 0x8000 | _color_list[3].unk2;
       
   793 					GfxFillRect(x+6, y+2, x+6+8, y+9, color);
       
   794 					GfxFillRect(x+16, y+2, x+16+8, y+9, color);
       
   795 				}
   771 				DrawStringCentered(x+10, y+1, STR_6819, 0);
   796 				DrawStringCentered(x+10, y+1, STR_6819, 0);
   772 				DrawStringCentered(x+20, y+1, STR_681A, 0);
   797 				DrawStringCentered(x+20, y+1, STR_681A, 0);
   773 
   798 
   774 				val = ReadPE(pe);
   799 				val = ReadPE(pe);
   775 				if (pe->type == PE_CURRENCY)
   800 				if (pe->type == PE_CURRENCY)
   814 			pe = &page->entries[btn];
   839 			pe = &page->entries[btn];
   815 
   840 
   816 			x = e->click.pt.x - 5;
   841 			x = e->click.pt.x - 5;
   817 			if (x < 0) return;
   842 			if (x < 0) return;
   818 
   843 
       
   844 			if (!(pe->flags & PF_PLAYERBASED) && _networking && !_network_server)
       
   845 				return;
       
   846 
   819 			if (x < 21) { // clicked on the icon on the left side. Either scroller or bool on/off
   847 			if (x < 21) { // clicked on the icon on the left side. Either scroller or bool on/off
   820 				int32 val = ReadPE(pe), oval = val;
   848 				int32 val = ReadPE(pe), oval = val;
   821 
   849 
   822 				switch(pe->type) {
   850 				switch(pe->type) {
   823 				case PE_BOOL:
   851 				case PE_BOOL:
   857 						_left_button_clicked = false;
   885 						_left_button_clicked = false;
   858 					}
   886 					}
   859 					break;
   887 					break;
   860 				}
   888 				}
   861 				if (val != oval) {
   889 				if (val != oval) {
   862 					WritePE(pe, val);
   890 					// To make patch-changes network-safe
       
   891 					if (pe->type == PE_CURRENCY) {
       
   892 						val /= GetCurrentCurrencyRate();
       
   893 					}
       
   894 					// If an item is playerbased, we do not send it over the network (if any)
       
   895 					if (pe->flags & PF_PLAYERBASED) {
       
   896 						WritePE(pe, val);
       
   897 					} else {
       
   898 						// Else we do
       
   899 						DoCommandP(0, (byte)WP(w,def_d).data_1 + ((byte)btn << 8), val, NULL, CMD_CHANGE_PATCH_SETTING);
       
   900 					}
   863 					SetWindowDirty(w);
   901 					SetWindowDirty(w);
   864 
   902 
   865 					if (pe->click_proc != NULL) // call callback function
   903 					if (pe->click_proc != NULL) // call callback function
   866 						pe->click_proc(val);
   904 						pe->click_proc(val);
   867 				}
   905 				}
   890 
   928 
   891 	case WE_ON_EDIT_TEXT: {
   929 	case WE_ON_EDIT_TEXT: {
   892 		if (*e->edittext.str) {
   930 		if (*e->edittext.str) {
   893 			const PatchPage *page = &_patches_page[WP(w,def_d).data_1];
   931 			const PatchPage *page = &_patches_page[WP(w,def_d).data_1];
   894 			const PatchEntry *pe = &page->entries[WP(w,def_d).data_3];
   932 			const PatchEntry *pe = &page->entries[WP(w,def_d).data_3];
   895 			WritePE(pe, atoi(e->edittext.str));
   933 			int32 val;
       
   934 			val = atoi(e->edittext.str);
       
   935 			if (pe->type == PE_CURRENCY) {
       
   936 				val /= GetCurrentCurrencyRate();
       
   937 			}
       
   938 			// If an item is playerbased, we do not send it over the network (if any)
       
   939 			if (pe->flags & PF_PLAYERBASED) {
       
   940 				WritePE(pe, val);
       
   941 			} else {
       
   942 				// Else we do
       
   943 				DoCommandP(0, (byte)WP(w,def_d).data_1 + ((byte)WP(w,def_d).data_3 << 8), val, NULL, CMD_CHANGE_PATCH_SETTING);
       
   944 			}
   896 			SetWindowDirty(w);
   945 			SetWindowDirty(w);
   897 
   946 
   898 			if (pe->click_proc != NULL) // call callback function
   947 			if (pe->click_proc != NULL) // call callback function
   899 				pe->click_proc(*(int32*)pe->variable);
   948 				pe->click_proc(*(int32*)pe->variable);
   900 		}
   949 		}
   903 
   952 
   904 	case WE_DESTROY:
   953 	case WE_DESTROY:
   905 		DeleteWindowById(WC_QUERY_STRING, 0);
   954 		DeleteWindowById(WC_QUERY_STRING, 0);
   906 		break;
   955 		break;
   907 	}
   956 	}
       
   957 }
       
   958 
       
   959 int32 CmdChangePatchSetting(int x, int y, uint32 flags, uint32 p1, uint32 p2)
       
   960 {
       
   961 	const PatchPage *page;
       
   962 	const PatchEntry *pe;
       
   963 
       
   964 	if (flags & DC_EXEC) {
       
   965 		page = &_patches_page[(byte)p1];
       
   966 		if (page == NULL) return 0;
       
   967 		pe = &page->entries[(byte)(p1 >> 8)];
       
   968 		if (pe == NULL) return 0;
       
   969 
       
   970 		WritePE(pe, (int32)p2);
       
   971 
       
   972 		InvalidateWindow(WC_GAME_OPTIONS, 0);
       
   973 	}
       
   974 
       
   975 	return 0;
   908 }
   976 }
   909 
   977 
   910 static const Widget _patches_selection_widgets[] = {
   978 static const Widget _patches_selection_widgets[] = {
   911 {   WWT_CLOSEBOX,    10,     0,    10,     0,    13, STR_00C5,												STR_018B_CLOSE_WINDOW},
   979 {   WWT_CLOSEBOX,    10,     0,    10,     0,    13, STR_00C5,												STR_018B_CLOSE_WINDOW},
   912 {    WWT_CAPTION,    10,    11,   369,     0,    13, STR_CONFIG_PATCHES_CAPTION,			STR_018C_WINDOW_TITLE_DRAG_THIS},
   980 {    WWT_CAPTION,    10,    11,   369,     0,    13, STR_CONFIG_PATCHES_CAPTION,			STR_018C_WINDOW_TITLE_DRAG_THIS},
   950 		int x, y = NEWGRF_WND_PROC_OFFSET_TOP_WIDGET;
  1018 		int x, y = NEWGRF_WND_PROC_OFFSET_TOP_WIDGET;
   951 		uint16 i = 0;
  1019 		uint16 i = 0;
   952 		struct GRFFile *c = _first_grffile;
  1020 		struct GRFFile *c = _first_grffile;
   953 
  1021 
   954 		DrawWindowWidgets(w);
  1022 		DrawWindowWidgets(w);
   955 		
  1023 
   956 		if (_first_grffile == NULL) { // no grf sets installed
  1024 		if (_first_grffile == NULL) { // no grf sets installed
   957 			DrawStringMultiCenter(140, 210, STR_NEWGRF_NO_FILES_INSTALLED, 250);
  1025 			DrawStringMultiCenter(140, 210, STR_NEWGRF_NO_FILES_INSTALLED, 250);
   958 			break;
  1026 			break;
   959 		}
  1027 		}
   960 
  1028 
   961 		// draw list of all grf files
  1029 		// draw list of all grf files
   962 		while (c != NULL) {
  1030 		while (c != NULL) {
   963 			if (i >= w->vscroll.pos) { // draw files according to scrollbar position
  1031 			if (i >= w->vscroll.pos) { // draw files according to scrollbar position
   964 				bool h = (_sel_grffile==c);
  1032 				bool h = (_sel_grffile==c);
   965 				// show highlighted item with a different background and highlighted text
  1033 				// show highlighted item with a different background and highlighted text
   966 				if(h) GfxFillRect(1, y + 1, 267, y + 12, 156); 
  1034 				if(h) GfxFillRect(1, y + 1, 267, y + 12, 156);
   967 				// XXX - will be grf name later
  1035 				// XXX - will be grf name later
   968 				DoDrawString(c->filename, 25, y + 2, h ? 0xC : 0x10); 
  1036 				DoDrawString(c->filename, 25, y + 2, h ? 0xC : 0x10);
   969 				DrawSprite(SPRITE_PALETTE(0x2EB | 0x30b8000), 5, y + 3);
  1037 				DrawSprite(SPRITE_PALETTE(0x2EB | 0x30b8000), 5, y + 3);
   970 				y += NEWGRF_WND_PROC_ROWSIZE;
  1038 				y += NEWGRF_WND_PROC_ROWSIZE;
   971 			}
  1039 			}
   972 			
  1040 
   973 			c = c->next;
  1041 			c = c->next;
   974 			if (++i == w->vscroll.cap + w->vscroll.pos) break; // stop after displaying 12 items
  1042 			if (++i == w->vscroll.cap + w->vscroll.pos) break; // stop after displaying 12 items
   975 		}
  1043 		}
   976 
  1044 
   977 // 		DoDrawString(_sel_grffile->setname, 120, 200, 0x01); // draw grf name
  1045 // 		DoDrawString(_sel_grffile->setname, 120, 200, 0x01); // draw grf name
   980 			DrawStringMultiCenter(140, 210, STR_NEWGRF_TIP, 250);
  1048 			DrawStringMultiCenter(140, 210, STR_NEWGRF_TIP, 250);
   981 		} else {
  1049 		} else {
   982 			// draw filename
  1050 			// draw filename
   983 			x = DrawString(5, 199, STR_NEWGRF_FILENAME, 0);
  1051 			x = DrawString(5, 199, STR_NEWGRF_FILENAME, 0);
   984 			DoDrawString(_sel_grffile->filename, x + 2, 199, 0x01);
  1052 			DoDrawString(_sel_grffile->filename, x + 2, 199, 0x01);
   985 	
  1053 
   986 			// draw grf id
  1054 			// draw grf id
   987 			x = DrawString(5, 209, STR_NEWGRF_GRF_ID, 0);
  1055 			x = DrawString(5, 209, STR_NEWGRF_GRF_ID, 0);
   988 			snprintf(_userstring, USERSTRING_LEN, "%08X", _sel_grffile->grfid);
  1056 			snprintf(_userstring, USERSTRING_LEN, "%08X", _sel_grffile->grfid);
   989 			DrawString(x + 2, 209, STR_SPEC_USERSTRING, 0x01);
  1057 			DrawString(x + 2, 209, STR_SPEC_USERSTRING, 0x01);
   990 		}
  1058 		}