(svn r9343) [0.5] -Backport from trunk (r9000, r9001, r9097, r9137): 0.5
authorrubidium
Mon, 19 Mar 2007 19:22:26 +0000
branch0.5
changeset 5461 03285c9589f9
parent 5460 c86169e59c08
child 5462 6d16b7e4f85d
(svn r9343) [0.5] -Backport from trunk (r9000, r9001, r9097, r9137):
- Fix: new locomotive names were not announced in the news, it said "new railway locomotive available - railway locomotive" (r9000, r9001)
- Feature: add an extra news group for opening and closing of industries (r9097)
- Fix: when all news-setting buttons are 'full', make the for-all button show 'full' too (r9137)
engine.c
engine_gui.c
industry_cmd.c
lang/english.txt
news.h
news_gui.c
settings.c
--- a/engine.c	Mon Mar 19 18:54:48 2007 +0000
+++ b/engine.c	Mon Mar 19 19:22:26 2007 +0000
@@ -332,15 +332,7 @@
 		}
 	}
 
-	if (index < NUM_TRAIN_ENGINES) {
-		AddNewsItem(index, NEWS_FLAGS(NM_CALLBACK, 0, NT_NEW_VEHICLES, DNC_TRAINAVAIL), 0, 0);
-	} else if (index < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES) {
-		AddNewsItem(index, NEWS_FLAGS(NM_CALLBACK, 0, NT_NEW_VEHICLES, DNC_ROADAVAIL), 0, 0);
-	} else if (index < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES + NUM_SHIP_ENGINES) {
-		AddNewsItem(index, NEWS_FLAGS(NM_CALLBACK, 0, NT_NEW_VEHICLES, DNC_SHIPAVAIL), 0, 0);
-	} else {
-		AddNewsItem(index, NEWS_FLAGS(NM_CALLBACK, 0, NT_NEW_VEHICLES, DNC_AIRCRAFTAVAIL), 0, 0);
-	}
+	AddNewsItem(index, NEWS_FLAGS(NM_CALLBACK, 0, NT_NEW_VEHICLES, DNC_VEHICLEAVAIL), 0, 0);
 }
 
 void EnginesMonthlyLoop(void)
--- a/engine_gui.c	Mon Mar 19 18:54:48 2007 +0000
+++ b/engine_gui.c	Mon Mar 19 19:22:26 2007 +0000
@@ -14,26 +14,25 @@
 #include "news.h"
 #include "variables.h"
 #include "newgrf_engine.h"
+#include "vehicle.h"
 
 
 static StringID GetEngineCategoryName(EngineID engine)
 {
-	if (engine < NUM_TRAIN_ENGINES) {
-		switch (GetEngine(engine)->railtype) {
-			case RAILTYPE_RAIL:     return STR_8102_RAILROAD_LOCOMOTIVE;
-			case RAILTYPE_ELECTRIC: return STR_8102_RAILROAD_LOCOMOTIVE;
-			case RAILTYPE_MONO:     return STR_8106_MONORAIL_LOCOMOTIVE;
-			case RAILTYPE_MAGLEV:   return STR_8107_MAGLEV_LOCOMOTIVE;
-		}
+	switch (GetEngine(engine)->type) {
+		default: NOT_REACHED();
+		case VEH_Road:              return STR_8103_ROAD_VEHICLE;
+		case VEH_Aircraft:          return STR_8104_AIRCRAFT;
+		case VEH_Ship:              return STR_8105_SHIP;
+		case VEH_Train:
+			switch (GetEngine(engine)->railtype) {
+				default: NOT_REACHED();
+				case RAILTYPE_RAIL:     return STR_8102_RAILROAD_LOCOMOTIVE;
+				case RAILTYPE_ELECTRIC: return STR_8102_RAILROAD_LOCOMOTIVE;
+				case RAILTYPE_MONO:     return STR_8106_MONORAIL_LOCOMOTIVE;
+				case RAILTYPE_MAGLEV:   return STR_8107_MAGLEV_LOCOMOTIVE;
+			}
 	}
-
-	if (engine < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES)
-		return STR_8103_ROAD_VEHICLE;
-
-	if (engine < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES + NUM_SHIP_ENGINES)
-		return STR_8105_SHIP;
-
-	return STR_8104_AIRCRAFT;
 }
 
 static const Widget _engine_preview_widgets[] = {
@@ -59,10 +58,10 @@
 static void DrawAircraftEngineInfo(EngineID engine, int x, int y, int maxw);
 
 static const DrawEngineInfo _draw_engine_list[4] = {
-	{DrawTrainEngine,DrawTrainEngineInfo},
-	{DrawRoadVehEngine,DrawRoadVehEngineInfo},
-	{DrawShipEngine,DrawShipEngineInfo},
-	{DrawAircraftEngine,DrawAircraftEngineInfo},
+	{ DrawTrainEngine,    DrawTrainEngineInfo    },
+	{ DrawRoadVehEngine,  DrawRoadVehEngineInfo  },
+	{ DrawShipEngine,     DrawShipEngineInfo     },
+	{ DrawAircraftEngine, DrawAircraftEngineInfo },
 };
 
 static void EnginePreviewWndProc(Window *w, WindowEvent *e)
@@ -80,10 +79,7 @@
 
 		DrawStringCentered(w->width >> 1, 80, GetCustomEngineName(engine), 0x10);
 
-		(dei = _draw_engine_list,engine < NUM_TRAIN_ENGINES) ||
-		(dei++,engine < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES) ||
-		(dei++,engine < NUM_TRAIN_ENGINES + NUM_ROAD_ENGINES + NUM_SHIP_ENGINES) ||
-		(dei++, true);
+		dei = &_draw_engine_list[GetEngine(engine)->type];
 
 		width = w->width;
 		dei->engine_proc(width >> 1, 100, engine, 0);
@@ -139,35 +135,6 @@
 	DrawStringMultiCenter(x, y, STR_VEHICLE_INFO_COST_WEIGHT_SPEED_POWER, maxw);
 }
 
-void DrawNewsNewTrainAvail(Window *w)
-{
-	EngineID engine;
-
-	DrawNewsBorder(w);
-
-	engine = WP(w,news_d).ni->string_id;
-	SetDParam(0, GetEngineCategoryName(engine));
-	DrawStringMultiCenter(w->width >> 1, 20, STR_8859_NEW_NOW_AVAILABLE, w->width - 2);
-
-	GfxFillRect(25, 56, w->width - 25, w->height - 2, 10);
-
-	SetDParam(0, GetCustomEngineName(engine));
-	DrawStringMultiCenter(w->width >> 1, 57, STR_885A, w->width - 2);
-
-	DrawTrainEngine(w->width >> 1, 88, engine, 0);
-	GfxFillRect(25, 56, w->width - 56, 112, 0x323 | USE_COLORTABLE);
-	DrawTrainEngineInfo(engine, w->width >> 1, 129, w->width - 52);
-}
-
-StringID GetNewsStringNewTrainAvail(const NewsItem *ni)
-{
-	EngineID engine = ni->string_id;
-	SetDParam(0, STR_8859_NEW_NOW_AVAILABLE);
-	SetDParam(1, GetEngineCategoryName(engine));
-	SetDParam(2, GetCustomEngineName(engine));
-	return STR_02B6;
-}
-
 static void DrawAircraftEngineInfo(EngineID engine, int x, int y, int maxw)
 {
 	const AircraftVehicleInfo *avi = AircraftVehInfo(engine);
@@ -180,33 +147,6 @@
 	DrawStringMultiCenter(x, y, STR_A02E_COST_MAX_SPEED_CAPACITY, maxw);
 }
 
-void DrawNewsNewAircraftAvail(Window *w)
-{
-	EngineID engine;
-
-	DrawNewsBorder(w);
-
-	engine = WP(w,news_d).ni->string_id;
-
-	DrawStringMultiCenter(w->width >> 1, 20, STR_A02C_NEW_AIRCRAFT_NOW_AVAILABLE, w->width - 2);
-	GfxFillRect(25, 56, w->width - 25, w->height - 2, 10);
-
-	SetDParam(0, GetCustomEngineName(engine));
-	DrawStringMultiCenter(w->width >> 1, 57, STR_A02D, w->width - 2);
-
-	DrawAircraftEngine(w->width >> 1, 93, engine, 0);
-	GfxFillRect(25, 56, w->width - 56, 110, 0x323 | USE_COLORTABLE);
-	DrawAircraftEngineInfo(engine, w->width >> 1, 131, w->width - 52);
-}
-
-StringID GetNewsStringNewAircraftAvail(const NewsItem *ni)
-{
-	EngineID engine = ni->string_id;
-	SetDParam(0, STR_A02C_NEW_AIRCRAFT_NOW_AVAILABLE);
-	SetDParam(1, GetCustomEngineName(engine));
-	return STR_02B6;
-}
-
 static void DrawRoadVehEngineInfo(EngineID engine, int x, int y, int maxw)
 {
 	const RoadVehicleInfo *rvi = RoadVehInfo(engine);
@@ -220,32 +160,6 @@
 	DrawStringMultiCenter(x, y, STR_902A_COST_SPEED_RUNNING_COST, maxw);
 }
 
-void DrawNewsNewRoadVehAvail(Window *w)
-{
-	EngineID engine;
-
-	DrawNewsBorder(w);
-
-	engine = WP(w,news_d).ni->string_id;
-	DrawStringMultiCenter(w->width >> 1, 20, STR_9028_NEW_ROAD_VEHICLE_NOW_AVAILABLE, w->width - 2);
-	GfxFillRect(25, 56, w->width - 25, w->height - 2, 10);
-
-	SetDParam(0, GetCustomEngineName(engine));
-	DrawStringMultiCenter(w->width >> 1, 57, STR_9029, w->width - 2);
-
-	DrawRoadVehEngine(w->width >> 1, 88, engine, 0);
-	GfxFillRect(25, 56, w->width - 56, 112, 0x323 | USE_COLORTABLE);
-	DrawRoadVehEngineInfo(engine, w->width >> 1, 129, w->width - 52);
-}
-
-StringID GetNewsStringNewRoadVehAvail(const NewsItem *ni)
-{
-	EngineID engine = ni->string_id;
-	SetDParam(0, STR_9028_NEW_ROAD_VEHICLE_NOW_AVAILABLE);
-	SetDParam(1, GetCustomEngineName(engine));
-	return STR_02B6;
-}
-
 static void DrawShipEngineInfo(EngineID engine, int x, int y, int maxw)
 {
 	const ShipVehicleInfo *svi = ShipVehInfo(engine);
@@ -257,29 +171,30 @@
 	DrawStringMultiCenter(x, y, STR_982E_COST_MAX_SPEED_CAPACITY, maxw);
 }
 
-void DrawNewsNewShipAvail(Window *w)
+StringID GetNewsStringNewVehicleAvail(const NewsItem *ni)
+ {
+	EngineID engine = ni->string_id;
+	SetDParam(0, GetEngineCategoryName(engine));
+	SetDParam(1, GetCustomEngineName(engine));
+	return STR_NEW_VEHICLE_NOW_AVAILABLE_WITH_TYPE;
+}
+
+void DrawNewsNewVehicleAvail(Window *w)
 {
-	EngineID engine;
+	EngineID engine = WP(w, news_d).ni->string_id;
+	const DrawEngineInfo *dei = &_draw_engine_list[GetEngine(engine)->type];
 
 	DrawNewsBorder(w);
 
-	engine = WP(w,news_d).ni->string_id;
+	SetDParam(0, GetEngineCategoryName(engine));
+	DrawStringMultiCenter(w->width >> 1, 20, STR_NEW_VEHICLE_NOW_AVAILABLE, w->width - 2);
 
-	DrawStringMultiCenter(w->width >> 1, 20, STR_982C_NEW_SHIP_NOW_AVAILABLE, w->width - 2);
 	GfxFillRect(25, 56, w->width - 25, w->height - 2, 10);
 
 	SetDParam(0, GetCustomEngineName(engine));
-	DrawStringMultiCenter(w->width >> 1, 57, STR_982D, w->width - 2);
-
-	DrawShipEngine(w->width >> 1, 93, engine, 0);
-	GfxFillRect(25, 56, w->width - 56, 110, 0x323 | USE_COLORTABLE);
-	DrawShipEngineInfo(engine, w->width >> 1, 131, w->width - 52);
-}
+	DrawStringMultiCenter(w->width >> 1, 57, STR_NEW_VEHICLE_TYPE, w->width - 2);
 
-StringID GetNewsStringNewShipAvail(const NewsItem *ni)
-{
-	EngineID engine = ni->string_id;
-	SetDParam(0, STR_982C_NEW_SHIP_NOW_AVAILABLE);
-	SetDParam(1, GetCustomEngineName(engine));
-	return STR_02B6;
+	dei->engine_proc(w->width >> 1, 88, engine, 0);
+	GfxFillRect(25, 56, w->width - 56, 112, 0x323 | USE_COLORTABLE);
+	dei->info_proc(engine, w->width >> 1, 129, w->width - 52);
 }
--- a/industry_cmd.c	Mon Mar 19 18:54:48 2007 +0000
+++ b/industry_cmd.c	Mon Mar 19 19:22:26 2007 +0000
@@ -1653,7 +1653,7 @@
 		SetDParam(0, i->index);
 		AddNewsItem(
 			indspec->closure_text,
-			NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_TILE, NT_ECONOMY, 0),
+			NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_TILE, NT_OPENCLOSE, 0),
 			i->xy + TileDiffXY(1, 1), 0
 		);
 	}
@@ -1735,7 +1735,7 @@
 	AddNewsItem(
 		(type != IT_FOREST && type != IT_FRUIT_PLANTATION && type != IT_RUBBER_PLANTATION && type != IT_COTTON_CANDY) ?
 			STR_482D_NEW_UNDER_CONSTRUCTION : STR_482E_NEW_BEING_PLANTED_NEAR,
-		NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_TILE, NT_ECONOMY,0), i->xy, 0
+		NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_TILE, NT_OPENCLOSE,0), i->xy, 0
 	);
 }
 
@@ -1803,7 +1803,7 @@
 
 	if (str != STR_NULL) {
 		SetDParam(0, i->index);
-		AddNewsItem(str, NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_TILE, NT_ECONOMY, 0), i->xy + TileDiffXY(1, 1), 0);
+		AddNewsItem(str, NEWS_FLAGS(NM_THIN, NF_VIEWPORT|NF_TILE, str == indspec->closure_text ? NT_OPENCLOSE : NT_ECONOMY, 0), i->xy + TileDiffXY(1, 1), 0);
 	}
 }
 
--- a/lang/english.txt	Mon Mar 19 18:54:48 2007 +0000
+++ b/lang/english.txt	Mon Mar 19 19:22:26 2007 +0000
@@ -590,6 +590,7 @@
 STR_0207_ARRIVAL_OF_FIRST_VEHICLE                               :{YELLOW}Arrival of first vehicle at competitor's station
 STR_0208_ACCIDENTS_DISASTERS                                    :{YELLOW}Accidents / disasters
 STR_0209_COMPANY_INFORMATION                                    :{YELLOW}Company information
+STR_NEWS_OPEN_CLOSE                                             :{YELLOW}Open / close of industries
 STR_020A_ECONOMY_CHANGES                                        :{YELLOW}Economy changes
 STR_020B_ADVICE_INFORMATION_ON_PLAYER                           :{YELLOW}Advice / information on player's vehicles
 STR_020C_NEW_VEHICLES                                           :{YELLOW}New vehicles
@@ -2605,8 +2606,6 @@
 STR_8857_MAKE_THE_HIGHLIGHTED_ORDER                             :{BLACK}Make the highlighted order force the vehicle to wait for a full load
 STR_8858_MAKE_THE_HIGHLIGHTED_ORDER                             :{BLACK}Make the highlighted order force the vehicle to unload
 STR_SERVICE_HINT                                                :{BLACK}Skip this order unless a service is needed
-STR_8859_NEW_NOW_AVAILABLE                                      :{BLACK}{BIGFONT}New {STRING} now available!
-STR_885A                                                        :{BLACK}{BIGFONT}{STRING}
 STR_VEHICLE_INFO_COST_WEIGHT_SPEED_POWER                        :{BLACK}Cost: {CURRENCY} Weight: {WEIGHT_S}{}Speed: {VELOCITY}  Power: {POWER}{}Running Cost: {CURRENCY}/yr{}Capacity: {CARGO}
 STR_885C_BROKEN_DOWN                                            :{RED}Broken down
 STR_885D_AGE_RUNNING_COST_YR                                    :{BLACK}Age: {LTBLUE}{STRING2}{BLACK}   Running Cost: {LTBLUE}{CURRENCY}/yr
@@ -2633,6 +2632,10 @@
 STR_TRAIN_NO_POWER                                              :{RED}No power
 STR_TRAIN_START_NO_CATENARY                                     :This track lacks catenary, so the train can't start
 
+STR_NEW_VEHICLE_NOW_AVAILABLE                                   :{BLACK}{BIGFONT}New {STRING} now available!
+STR_NEW_VEHICLE_TYPE                                            :{BLACK}{BIGFONT}{STRING}
+STR_NEW_VEHICLE_NOW_AVAILABLE_WITH_TYPE                         :{BLACK}New {STRING} now available!  -  {STRING}
+
 ##id 0x9000
 STR_9000_ROAD_VEHICLE_IN_THE_WAY                                :{WHITE}Road vehicle in the way
 STR_9001_ROAD_VEHICLES                                          :{WHITE}{COMPANY} - {COMMA} Road Vehicle{P "" s}
@@ -2673,8 +2676,6 @@
 STR_9025_CENTER_MAIN_VIEW_ON_ROAD                               :{BLACK}Centre main view on road vehicle depot location
 STR_9026_ROAD_VEHICLE_SELECTION                                 :{BLACK}Road vehicle selection list - click on vehicle for information
 STR_9027_BUILD_THE_HIGHLIGHTED_ROAD                             :{BLACK}Build the highlighted road vehicle
-STR_9028_NEW_ROAD_VEHICLE_NOW_AVAILABLE                         :{BLACK}{BIGFONT}New road vehicle now available!
-STR_9029                                                        :{BLACK}{BIGFONT}{STRING}
 STR_902A_COST_SPEED_RUNNING_COST                                :{BLACK}Cost: {CURRENCY}{}Speed: {VELOCITY}{}Running Cost: {CURRENCY}/yr{}Capacity: {CARGO}
 
 STR_902C_NAME_ROAD_VEHICLE                                      :{WHITE}Name road vehicle
@@ -2746,8 +2747,6 @@
 STR_9829_CENTER_MAIN_VIEW_ON_SHIP                               :{BLACK}Centre main view on ship's location
 STR_982A_SEND_SHIP_TO_DEPOT                                     :{BLACK}Send ship to depot. CTRL+click will only service
 STR_982B_SHOW_SHIP_DETAILS                                      :{BLACK}Show ship details
-STR_982C_NEW_SHIP_NOW_AVAILABLE                                 :{BLACK}{BIGFONT}New ship now available!
-STR_982D                                                        :{BLACK}{BIGFONT}{STRING}
 STR_982E_COST_MAX_SPEED_CAPACITY                                :{BLACK}Cost: {CURRENCY} Max. Speed: {VELOCITY}{}Capacity: {CARGO}{}Running Cost: {CURRENCY}/yr
 STR_982F_NAME_SHIP                                              :{BLACK}Name ship
 
@@ -2820,8 +2819,6 @@
 STR_A029_CENTER_MAIN_VIEW_ON_AIRCRAFT                           :{BLACK}Centre main view on aircraft's location
 STR_A02A_SEND_AIRCRAFT_TO_HANGAR                                :{BLACK}Send aircraft to hangar. CTRL+click will only service
 STR_A02B_SHOW_AIRCRAFT_DETAILS                                  :{BLACK}Show aircraft details
-STR_A02C_NEW_AIRCRAFT_NOW_AVAILABLE                             :{BLACK}{BIGFONT}New aircraft now available!
-STR_A02D                                                        :{BLACK}{BIGFONT}{STRING}
 STR_A02E_COST_MAX_SPEED_CAPACITY                                :{BLACK}Cost: {CURRENCY} Max. Speed: {VELOCITY}{}Capacity: {COMMA} passengers, {COMMA} bags of mail{}Running Cost: {CURRENCY}/yr
 
 STR_A030_NAME_AIRCRAFT                                          :{WHITE}Name aircraft
--- a/news.h	Mon Mar 19 18:54:48 2007 +0000
+++ b/news.h	Mon Mar 19 19:22:26 2007 +0000
@@ -31,18 +31,22 @@
 VARDEF NewsItem _statusbar_news_item;
 
 enum NewsType {
-	NT_ARRIVAL_PLAYER = 0,
-	NT_ARRIVAL_OTHER  = 1,
-	NT_ACCIDENT       = 2,
-	NT_COMPANY_INFO   = 3,
-	NT_ECONOMY        = 4,
-	NT_ADVICE         = 5,
-	NT_NEW_VEHICLES   = 6,
-	NT_ACCEPTANCE     = 7,
-	NT_SUBSIDIES      = 8,
-	NT_GENERAL        = 9,
+	NT_ARRIVAL_PLAYER,
+	NT_ARRIVAL_OTHER,
+	NT_ACCIDENT,
+	NT_COMPANY_INFO,
+	NT_OPENCLOSE,
+	NT_ECONOMY,
+	NT_ADVICE,
+	NT_NEW_VEHICLES,
+	NT_ACCEPTANCE,
+	NT_SUBSIDIES,
+	NT_GENERAL,
+	NT_END,
 };
 
+extern const char *_news_display_name[NT_END];
+
 enum NewsMode {
 	NM_SMALL    = 0, ///< Show only a small popup informing us about vehicle age for example
 	NM_NORMAL   = 1, ///< Show a simple news message (height 170 pixels)
@@ -59,11 +63,8 @@
 };
 
 enum NewsCallback {
-	DNC_TRAINAVAIL    = 0, ///< Show new train available message. StringID is EngineID
-	DNC_ROADAVAIL     = 1, ///< Show new road vehicle available message. StringID is EngineID
-	DNC_SHIPAVAIL     = 2, ///< Show new ship available message. StringID is EngineID
-	DNC_AIRCRAFTAVAIL = 3, ///< Show new aircraft available message. StringID is EngineID
-	DNC_BANKRUPCY     = 4, ///< Show bankrupcy message. StringID is PlayerID (0-3) and NewsBankrupcy (4-7)
+	DNC_VEHICLEAVAIL  = 0, ///< Show new vehicle available message. StringID is EngineID
+	DNC_BANKRUPCY     = 1, ///< Show bankrupcy message. StringID is PlayerID (0-3) and NewsBankrupcy (4-7)
 };
 
 enum NewsBankrupcy {
--- a/news_gui.c	Mon Mar 19 18:54:48 2007 +0000
+++ b/news_gui.c	Mon Mar 19 19:22:26 2007 +0000
@@ -53,32 +53,21 @@
 
 static byte _total_news = 0; // total news count
 
-void DrawNewsNewTrainAvail(Window *w);
-void DrawNewsNewRoadVehAvail(Window *w);
-void DrawNewsNewShipAvail(Window *w);
-void DrawNewsNewAircraftAvail(Window *w);
+void DrawNewsNewVehicleAvail(Window *w);
 void DrawNewsBankrupcy(Window *w);
 static void MoveToNextItem(void);
 
-StringID GetNewsStringNewTrainAvail(const NewsItem *ni);
-StringID GetNewsStringNewRoadVehAvail(const NewsItem *ni);
-StringID GetNewsStringNewShipAvail(const NewsItem *ni);
-StringID GetNewsStringNewAircraftAvail(const NewsItem *ni);
+StringID GetNewsStringNewVehicleAvail(const NewsItem *ni);
 StringID GetNewsStringBankrupcy(const NewsItem *ni);
 
 static DrawNewsCallbackProc * const _draw_news_callback[] = {
-	DrawNewsNewTrainAvail,    /* DNC_TRAINAVAIL */
-	DrawNewsNewRoadVehAvail,  /* DNC_ROADAVAIL */
-	DrawNewsNewShipAvail,     /* DNC_SHIPAVAIL */
-	DrawNewsNewAircraftAvail, /* DNC_AIRCRAFTAVAIL */
+	DrawNewsNewVehicleAvail,  /* DNC_VEHICLEAVAIL */
 	DrawNewsBankrupcy,        /* DNC_BANKRUPCY */
 };
 
+extern GetNewsStringCallbackProc * const _get_news_string_callback[];
 GetNewsStringCallbackProc * const _get_news_string_callback[] = {
-	GetNewsStringNewTrainAvail,    /* DNC_TRAINAVAIL */
-	GetNewsStringNewRoadVehAvail,  /* DNC_ROADAVAIL */
-	GetNewsStringNewShipAvail,     /* DNC_SHIPAVAIL */
-	GetNewsStringNewAircraftAvail, /* DNC_AIRCRAFTAVAIL */
+	GetNewsStringNewVehicleAvail,  /* DNC_VEHICLEAVAIL */
 	GetNewsStringBankrupcy,        /* DNC_BANKRUPCY */
 };
 
@@ -363,19 +352,34 @@
 	NewsWindowProc
 };
 
-static const SoundFx _news_sounds[] = {
+static const SoundFx _news_sounds[NT_END] = {
 	SND_1D_APPLAUSE,
 	SND_1D_APPLAUSE,
 	0,
 	0,
 	0,
 	0,
+	0,
 	SND_1E_OOOOH,
 	0,
 	0,
 	0
 };
 
+const char *_news_display_name[NT_END] = {
+	"arrival_player",
+	"arrival_other",
+	"accident",
+	"company_info",
+	"openclose",
+	"economy",
+	"advice",
+	"new_vehicles",
+	"acceptance",
+	"subsidies",
+	"general",
+};
+
 /** Get the value of an item of the news-display settings. This is
  * a little tricky since on/off/summary must use 2 bits to store the value
  * @param item the item whose value is requested
@@ -383,7 +387,7 @@
  */
 static inline byte GetNewsDisplayValue(byte item)
 {
-	assert(item < 10 && GB(_news_display_opt, item * 2, 2) <= 2);
+	assert(item < NT_END && GB(_news_display_opt, item * 2, 2) <= 2);
 	return GB(_news_display_opt, item * 2, 2);
 }
 
@@ -394,7 +398,7 @@
  */
 static inline void SetNewsDisplayValue(byte item, byte val)
 {
-	assert(item < 10 && val <= 2);
+	assert(item < NT_END && val <= 2);
 	SB(_news_display_opt, item * 2, 2, val);
 }
 
@@ -732,11 +736,19 @@
 	switch (e->event) {
 	case WE_CREATE: {
 		uint32 val = _news_display_opt;
+		uint32 all_val;
 		int i;
-		WP(w, def_d).data_1 = WP(w, def_d).data_2 = 0;
+		WP(w, def_d).data_1 = 0;
 
-		// Set up the initial disabled buttons in the case of 'off' or 'full'
-		for (i = 0; i != 10; i++, val >>= 2) SetMessageButtonStates(w, val & 0x3, i);
+		/* Set up the initial disabled buttons in the case of 'off' or 'full' */
+		all_val = val & 0x3;
+		for (i = 0; i != 10; i++, val >>= 2) {
+			SetMessageButtonStates(w, val & 0x3, i);
+			/* If the value doesn't match the ALL-button value, set the ALL-button value to 'off' */
+			if ((val & 0x3) != all_val) all_val = 0;
+		}
+		/* If all values are the same value, the ALL-button will take over this value */
+		WP(w, def_d).data_2 = all_val;
 	} break;
 
 	case WE_PAINT: {
@@ -744,12 +756,12 @@
 		int click_state = WP(w, def_d).data_1;
 		int i, y;
 
-		if (_news_ticker_sound) LowerWindowWidget(w, 25);
+		if (_news_ticker_sound) LowerWindowWidget(w, 27);
 		DrawWindowWidgets(w);
 
 		/* XXX - Draw the fake widgets-buttons. Can't add these to the widget-desc since
 		 * openttd currently can only handle 32 widgets. So hack it *g* */
-		for (i = 0, y = 26; i != 10; i++, y += 12, click_state >>= 1, val >>= 2) {
+		for (i = 0, y = 26; i < NT_END; i++, y += 12, click_state >>= 1, val >>= 2) {
 			bool clicked = !!(click_state & 1);
 
 			DrawFrameRect(13, y, 89, 11 + y, 3, (clicked) ? FR_LOWERED : 0);
@@ -757,7 +769,7 @@
 			DrawString(103, y + 1, i + STR_0206_ARRIVAL_OF_FIRST_VEHICLE, 0);
 		}
 
-		DrawString(  8, y + 9, message_opt[WP(w, def_d).data_2], 0x10);
+		DrawStringCentered(((13 + 89 + 1) >> 1), y + 9, message_opt[WP(w, def_d).data_2], 0x10);
 		DrawString(103, y + 9, STR_MESSAGES_ALL, 0);
 		DrawString(103, y + 9 + 12, STR_MESSAGE_SOUND, 0);
 
@@ -766,7 +778,7 @@
 	case WE_CLICK:
 		switch (e->we.click.widget) {
 		case 2: /* Clicked on any of the fake widgets */
-			if (e->we.click.pt.x > 13 && e->we.click.pt.x < 89 && e->we.click.pt.y > 26 && e->we.click.pt.y < 146) {
+			if (e->we.click.pt.x > 13 && e->we.click.pt.x < 89 && e->we.click.pt.y > 26 && e->we.click.pt.y < NT_END * 12 + 26) {
 				int element = (e->we.click.pt.y - 26) / 12;
 				byte val = (GetNewsDisplayValue(element) + 1) % 3;
 
@@ -778,17 +790,17 @@
 				SetWindowDirty(w);
 			}
 			break;
-		case 23: case 24: /* Dropdown menu for all settings */
-			ShowDropDownMenu(w, message_opt, WP(w, def_d).data_2, 24, 0, 0);
+		case 25: case 26: /* Dropdown menu for all settings */
+			ShowDropDownMenu(w, message_opt, WP(w, def_d).data_2, 26, 0, 0);
 			break;
-		case 25: /* Change ticker sound on/off */
+		case 27: /* Change ticker sound on/off */
 			_news_ticker_sound ^= 1;
 			ToggleWidgetLoweredState(w, e->we.click.widget);
 			InvalidateWidget(w, e->we.click.widget);
 			break;
 		default: { /* Clicked on the [<] .. [>] widgets */
 			int wid = e->we.click.widget;
-			if (wid > 2 && wid < 23) {
+			if (wid > 2 && wid <= NT_END * 2 + 2) {
 				int element = (wid - 3) / 2;
 				byte val = (GetNewsDisplayValue(element) + ((wid & 1) ? -1 : 1)) % 3;
 
@@ -804,9 +816,9 @@
 
 		WP(w, def_d).data_2 = e->we.dropdown.index;
 
-		for (i = 0; i != 10; i++) {
-			SB(_news_display_opt, i*2, 2, e->we.dropdown.index);
+		for (i = 0; i < NT_END; i++) {
 			SetMessageButtonStates(w, e->we.dropdown.index, i);
+			SetNewsDisplayValue(i, e->we.dropdown.index);
 		}
 		SetWindowDirty(w);
 		break;
@@ -822,7 +834,7 @@
 static const Widget _message_options_widgets[] = {
 {   WWT_CLOSEBOX,   RESIZE_NONE,    13,     0,   10,     0,    13, STR_00C5,                 STR_018B_CLOSE_WINDOW},
 {    WWT_CAPTION,   RESIZE_NONE,    13,    11,  409,     0,    13, STR_0204_MESSAGE_OPTIONS, STR_018C_WINDOW_TITLE_DRAG_THIS},
-{      WWT_PANEL,   RESIZE_NONE,    13,     0,  409,    14,   184, 0x0,                      STR_NULL},
+{      WWT_PANEL,   RESIZE_NONE,    13,     0,  409,    14,   196, 0x0,                      STR_NULL},
 
 { WWT_PUSHIMGBTN,   RESIZE_NONE,     3,     4,   12,    26,    37, SPR_ARROW_LEFT,           STR_HSCROLL_BAR_SCROLLS_LIST},
 { WWT_PUSHIMGBTN,   RESIZE_NONE,     3,    90,   98,    26,    37, SPR_ARROW_RIGHT,          STR_HSCROLL_BAR_SCROLLS_LIST},
@@ -854,16 +866,19 @@
 { WWT_PUSHIMGBTN,   RESIZE_NONE,     3,     4,   12,   134,   145, SPR_ARROW_LEFT,           STR_HSCROLL_BAR_SCROLLS_LIST},
 { WWT_PUSHIMGBTN,   RESIZE_NONE,     3,    90,   98,   134,   145, SPR_ARROW_RIGHT,          STR_HSCROLL_BAR_SCROLLS_LIST},
 
-{      WWT_PANEL,   RESIZE_NONE,     3,     4,   86,   154,   165, 0x0,                      STR_NULL},
-{    WWT_TEXTBTN,   RESIZE_NONE,     3,    87,   98,   154,   165, STR_0225,                 STR_NULL},
-{  WWT_TEXTBTN_2,   RESIZE_NONE,     3,     4,   98,   166,   177, STR_02DB_OFF,             STR_NULL},
+{ WWT_PUSHIMGBTN,   RESIZE_NONE,     3,     4,   12,   146,   157, SPR_ARROW_LEFT,           STR_HSCROLL_BAR_SCROLLS_LIST},
+{ WWT_PUSHIMGBTN,   RESIZE_NONE,     3,    90,   98,   146,   157, SPR_ARROW_RIGHT,          STR_HSCROLL_BAR_SCROLLS_LIST},
+
+{      WWT_PANEL,   RESIZE_NONE,     3,     4,   86,   166,   177, 0x0,                      STR_NULL},
+{    WWT_TEXTBTN,   RESIZE_NONE,     3,    87,   98,   166,   177, STR_0225,                 STR_NULL},
+{  WWT_TEXTBTN_2,   RESIZE_NONE,     3,     4,   98,   178,   189, STR_02DB_OFF,             STR_NULL},
 
 {      WWT_LABEL,   RESIZE_NONE,    13,     0,  409,    13,    26, STR_0205_MESSAGE_TYPES,   STR_NULL},
 {   WIDGETS_END},
 };
 
 static const WindowDesc _message_options_desc = {
-	270, 22, 410, 185,
+	270, 22, 410, 197,
 	WC_GAME_OPTIONS, 0,
 	WDF_STD_TOOLTIPS | WDF_STD_BTN | WDF_DEF_WIDGET | WDF_UNCLICK_BUTTONS,
 	_message_options_widgets,
--- a/settings.c	Mon Mar 19 18:54:48 2007 +0000
+++ b/settings.c	Mon Mar 19 19:22:26 2007 +0000
@@ -40,6 +40,7 @@
 #include "genworld.h"
 #include "date.h"
 #include "rail.h"
+#include "news.h"
 #ifdef WITH_FREETYPE
 #include "gfx.h"
 #include "fontcache.h"
@@ -1181,7 +1182,6 @@
 
 static const SettingDescGlobVarList _misc_settings[] = {
 	SDTG_MMANY("display_opt",     SLE_UINT8, S, 0, _display_opt,       (DO_SHOW_TOWN_NAMES|DO_SHOW_STATION_NAMES|DO_SHOW_SIGNS|DO_FULL_ANIMATION|DO_FULL_DETAIL|DO_TRANS_BUILDINGS|DO_WAYPOINTS), "SHOW_TOWN_NAMES|SHOW_STATION_NAMES|SHOW_SIGNS|FULL_ANIMATION|TRANS_BUILDINGS|FULL_DETAIL|WAYPOINTS", STR_NULL, NULL),
-	  SDTG_VAR("news_display_opt", SLE_UINT, S, 0, _news_display_opt,0xAAAAAAAA,0,0xAAAAAAAA,0,STR_NULL, NULL), // default to all full messages: 10101010101010101010 = 0xAAAAAAAA
 	 SDTG_BOOL("news_ticker_sound",          S, 0, _news_ticker_sound,     true,    STR_NULL, NULL),
 	 SDTG_BOOL("fullscreen",                 S, 0, _fullscreen,           false,    STR_NULL, NULL),
 	  SDTG_STR("videodriver",      SLE_STRB,C|S,0, _ini_videodriver,       NULL,    STR_NULL, NULL),
@@ -1495,6 +1495,44 @@
 #undef NO
 #undef CR
 
+static uint NewsDisplayLoadConfig(IniFile *ini, const char *grpname)
+{
+	IniGroup *group = ini_getgroup(ini, grpname, -1);
+	IniItem *item;
+	/* By default, set everything to full (0xAAAAAAAA = 1010101010101010) */
+	uint res = 0xAAAAAAAA;
+
+	/* If no group exists, return everything FULL */
+	if (group == NULL) return res;
+
+	for (item = group->item; item != NULL; item = item->next) {
+		int news_item = -1;
+		int i;
+		for (i = 0; i < NT_END; i++) {
+			if (strcasecmp(item->name, _news_display_name[i]) == 0) {
+				news_item = i;
+				break;
+			}
+		}
+		if (news_item == -1) {
+			DEBUG(misc, 0)("Invalid display option: %s", item->name);
+			continue;
+		}
+
+		if (strcasecmp(item->value, "full") == 0) {
+			SB(res, news_item * 2, 2, 2);
+		} else if (strcasecmp(item->value, "off") == 0) {
+			SB(res, news_item * 2, 2, 0);
+		} else if (strcasecmp(item->value, "summarized") == 0) {
+			SB(res, news_item * 2, 2, 1);
+		} else {
+			DEBUG(misc, 0)("Invalid display value: %s", item->value);
+			continue;
+		}
+	}
+
+	return res;
+}
 
 /* Load a GRF configuration from the given group name */
 static GRFConfig *GRFLoadConfig(IniFile *ini, const char *grpname, bool is_static)
@@ -1549,6 +1587,27 @@
 	return first;
 }
 
+static void NewsDisplaySaveConfig(IniFile *ini, const char *grpname, uint news_display)
+{
+	IniGroup *group = ini_getgroup(ini, grpname, -1);
+	IniItem **item;
+	int i;
+
+	if (group == NULL) return;
+	group->item = NULL;
+	item = &group->item;
+
+	for (i = 0; i < NT_END; i++) {
+		const char *value;
+		int v = GB(news_display, i * 2, 2);
+
+		value = (v == 0 ? "off" : (v == 1 ? "summarized" : "full"));
+
+		*item = ini_item_alloc(group, _news_display_name[i], strlen(_news_display_name[i]));
+		(*item)->value = (char*)pool_strdup(&ini->pool, value, strlen(value));
+		item = &(*item)->next;
+	}
+}
 
 /* Save a GRF configuration to the given group name */
 static void GRFSaveConfig(IniFile *ini, const char *grpname, const GRFConfig *list)
@@ -1598,6 +1657,7 @@
 	HandleSettingDescs(ini, ini_load_settings, ini_load_setting_list);
 	_grfconfig_newgame = GRFLoadConfig(ini, "newgrf", false);
 	_grfconfig_static  = GRFLoadConfig(ini, "newgrf-static", true);
+	_news_display_opt  = NewsDisplayLoadConfig(ini, "news_display");
 	ini_free(ini);
 }
 
@@ -1608,6 +1668,7 @@
 	HandleSettingDescs(ini, ini_save_settings, ini_save_setting_list);
 	GRFSaveConfig(ini, "newgrf", _grfconfig_newgame);
 	GRFSaveConfig(ini, "newgrf-static", _grfconfig_static);
+	NewsDisplaySaveConfig(ini, "news_display", _news_display_opt);
 	ini_save(_config_file, ini);
 	ini_free(ini);
 }
@@ -1817,16 +1878,6 @@
 
 void CheckConfig(void)
 {
-	// fix up news_display_opt from old to new
-	int i;
-	uint32 tmp;
-	for (i = 0, tmp = _news_display_opt; i != 10; i++, tmp >>= 2) {
-		if ((tmp & 0x3) == 0x3) { // old settings
-			_news_display_opt = 0xAAAAAAAA; // set all news-messages to full 1010101010...
-			break;
-		}
-	}
-
 	// Increase old default values for pf_maxdepth and pf_maxlength
 	// to support big networks.
 	if (_patches_newgame.pf_maxdepth == 16 && _patches_newgame.pf_maxlength == 512) {