2006-09-26 16:47:51 +00:00
/* $Id$ */
2009-08-21 20:21:05 +00:00
/*
* This file is part of OpenTTD .
* OpenTTD is free software ; you can redistribute it and / or modify it under the terms of the GNU General Public License as published by the Free Software Foundation , version 2.
* OpenTTD is distributed in the hope that it will be useful , but WITHOUT ANY WARRANTY ; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE .
* See the GNU General Public License for more details . You should have received a copy of the GNU General Public License along with OpenTTD . If not , see < http : //www.gnu.org/licenses/>.
*/
2008-05-06 15:11:33 +00:00
/** @file depot_gui.cpp The GUI for depots. */
2007-02-23 18:55:07 +00:00
2010-01-15 16:41:15 +00:00
# include "stdafx.h"
# include "engine_base.h"
2006-09-27 15:47:00 +00:00
# include "train.h"
2006-09-26 16:47:51 +00:00
# include "ship.h"
2006-09-27 15:40:55 +00:00
# include "aircraft.h"
2009-05-22 20:22:20 +00:00
# include "roadveh.h"
2006-09-26 16:47:51 +00:00
# include "gui.h"
2007-12-19 20:45:46 +00:00
# include "textbuf_gui.h"
2008-01-09 09:45:45 +00:00
# include "viewport_func.h"
2007-12-21 21:50:46 +00:00
# include "command_func.h"
2008-04-17 19:10:30 +00:00
# include "depot_base.h"
2006-09-26 16:47:51 +00:00
# include "vehicle_gui.h"
# include "newgrf_engine.h"
2007-02-10 13:37:32 +00:00
# include "spritecache.h"
2007-12-21 19:49:27 +00:00
# include "strings_func.h"
2007-12-25 11:26:07 +00:00
# include "window_func.h"
2007-12-27 13:35:39 +00:00
# include "vehicle_func.h"
2008-09-30 20:51:04 +00:00
# include "company_func.h"
2008-05-07 13:10:15 +00:00
# include "tilehighlight_func.h"
2008-05-17 13:01:30 +00:00
# include "window_gui.h"
2008-05-28 11:56:21 +00:00
# include "vehiclelist.h"
2006-09-27 13:01:56 +00:00
2008-01-13 01:21:35 +00:00
# include "table/strings.h"
# include "table/sprites.h"
2006-09-27 13:01:56 +00:00
/*
* Since all depot window sizes aren ' t the same , we need to modify sizes a little .
* It ' s done with the following arrays of widget indexes . Each of them tells if a widget side should be moved and in what direction .
* How long they should be moved and for what window types are controlled in ShowDepotWindow ( )
*/
2006-09-27 11:34:27 +00:00
/* Names of the widgets. Keep them in the same order as in the widget array */
2006-12-07 00:51:20 +00:00
enum DepotWindowWidgets {
2006-09-27 11:34:27 +00:00
DEPOT_WIDGET_CAPTION ,
DEPOT_WIDGET_SELL ,
2006-09-27 22:44:39 +00:00
DEPOT_WIDGET_SELL_CHAIN ,
2006-09-27 11:34:27 +00:00
DEPOT_WIDGET_SELL_ALL ,
2006-10-01 16:02:29 +00:00
DEPOT_WIDGET_AUTOREPLACE ,
2006-09-27 11:34:27 +00:00
DEPOT_WIDGET_MATRIX ,
2007-02-23 18:55:07 +00:00
DEPOT_WIDGET_V_SCROLL , ///< Vertical scrollbar
DEPOT_WIDGET_H_SCROLL , ///< Horizontal scrollbar
2006-09-27 11:34:27 +00:00
DEPOT_WIDGET_BUILD ,
DEPOT_WIDGET_CLONE ,
DEPOT_WIDGET_LOCATION ,
2006-09-30 13:39:34 +00:00
DEPOT_WIDGET_VEHICLE_LIST ,
2006-10-01 16:02:29 +00:00
DEPOT_WIDGET_STOP_ALL ,
DEPOT_WIDGET_START_ALL ,
2006-09-27 13:01:56 +00:00
} ;
2009-09-26 19:21:20 +00:00
/** Nested widget definition for train depots. */
static const NWidgetPart _nested_train_depot_widgets [ ] = {
NWidget ( NWID_HORIZONTAL ) ,
2009-11-24 18:05:55 +00:00
NWidget ( WWT_CLOSEBOX , COLOUR_GREY ) ,
2010-05-12 18:19:36 +00:00
NWidget ( WWT_CAPTION , COLOUR_GREY , DEPOT_WIDGET_CAPTION ) , SetDataTip ( STR_DEPOT_CAPTION , STR_NULL ) ,
2009-12-21 16:24:29 +00:00
NWidget ( WWT_SHADEBOX , COLOUR_GREY ) ,
2009-11-24 18:05:55 +00:00
NWidget ( WWT_STICKYBOX , COLOUR_GREY ) ,
2009-09-26 19:21:20 +00:00
EndContainer ( ) ,
NWidget ( NWID_HORIZONTAL ) ,
NWidget ( NWID_VERTICAL ) ,
2009-11-17 23:32:18 +00:00
NWidget ( WWT_MATRIX , COLOUR_GREY , DEPOT_WIDGET_MATRIX ) , SetDataTip ( 0x0 , STR_NULL ) , SetResize ( 1 , 1 ) ,
2009-09-26 19:21:20 +00:00
NWidget ( WWT_HSCROLLBAR , COLOUR_GREY , DEPOT_WIDGET_H_SCROLL ) ,
EndContainer ( ) ,
NWidget ( NWID_VERTICAL ) ,
2009-11-22 18:26:01 +00:00
NWidget ( WWT_IMGBTN , COLOUR_GREY , DEPOT_WIDGET_SELL ) , SetDataTip ( 0x0 , STR_NULL ) , SetResize ( 0 , 1 ) , SetFill ( 0 , 1 ) ,
NWidget ( WWT_IMGBTN , COLOUR_GREY , DEPOT_WIDGET_SELL_CHAIN ) , SetDataTip ( SPR_SELL_CHAIN_TRAIN , STR_DEPOT_DRAG_WHOLE_TRAIN_TO_SELL_TOOLTIP ) , SetResize ( 0 , 1 ) , SetFill ( 0 , 1 ) ,
2009-09-26 19:21:20 +00:00
NWidget ( WWT_PUSHIMGBTN , COLOUR_GREY , DEPOT_WIDGET_SELL_ALL ) , SetDataTip ( 0x0 , STR_NULL ) ,
NWidget ( WWT_PUSHIMGBTN , COLOUR_GREY , DEPOT_WIDGET_AUTOREPLACE ) , SetDataTip ( 0x0 , STR_NULL ) ,
EndContainer ( ) ,
NWidget ( WWT_SCROLLBAR , COLOUR_GREY , DEPOT_WIDGET_V_SCROLL ) ,
EndContainer ( ) ,
NWidget ( NWID_HORIZONTAL , NC_EQUALSIZE ) ,
2009-11-22 18:26:01 +00:00
NWidget ( WWT_PUSHTXTBTN , COLOUR_GREY , DEPOT_WIDGET_BUILD ) , SetDataTip ( 0x0 , STR_NULL ) , SetFill ( 1 , 1 ) , SetResize ( 1 , 0 ) ,
NWidget ( WWT_TEXTBTN , COLOUR_GREY , DEPOT_WIDGET_CLONE ) , SetDataTip ( 0x0 , STR_NULL ) , SetFill ( 1 , 1 ) , SetResize ( 1 , 0 ) ,
NWidget ( WWT_PUSHTXTBTN , COLOUR_GREY , DEPOT_WIDGET_LOCATION ) , SetDataTip ( STR_BUTTON_LOCATION , STR_NULL ) , SetFill ( 1 , 1 ) , SetResize ( 1 , 0 ) ,
NWidget ( WWT_PUSHTXTBTN , COLOUR_GREY , DEPOT_WIDGET_VEHICLE_LIST ) , SetDataTip ( 0x0 , STR_NULL ) , SetFill ( 0 , 1 ) ,
NWidget ( WWT_PUSHIMGBTN , COLOUR_GREY , DEPOT_WIDGET_STOP_ALL ) , SetDataTip ( SPR_FLAG_VEH_STOPPED , STR_NULL ) , SetFill ( 0 , 1 ) ,
NWidget ( WWT_PUSHIMGBTN , COLOUR_GREY , DEPOT_WIDGET_START_ALL ) , SetDataTip ( SPR_FLAG_VEH_RUNNING , STR_NULL ) , SetFill ( 0 , 1 ) ,
2009-11-24 18:05:55 +00:00
NWidget ( WWT_RESIZEBOX , COLOUR_GREY ) ,
2009-09-26 19:21:20 +00:00
EndContainer ( ) ,
2006-09-26 16:47:51 +00:00
} ;
2009-03-15 15:12:06 +00:00
static const WindowDesc _train_depot_desc (
2009-11-28 14:42:35 +00:00
WDP_AUTO , 362 , 123 ,
2007-02-01 15:49:12 +00:00
WC_VEHICLE_DEPOT , WC_NONE ,
2009-11-24 17:28:29 +00:00
WDF_UNCLICK_BUTTONS ,
2009-11-15 10:26:01 +00:00
_nested_train_depot_widgets , lengthof ( _nested_train_depot_widgets )
2009-03-15 15:12:06 +00:00
) ;
2006-09-26 16:47:51 +00:00
2009-03-15 15:12:06 +00:00
static const WindowDesc _road_depot_desc (
2009-11-28 14:42:35 +00:00
WDP_AUTO , 316 , 97 ,
2007-02-01 15:49:12 +00:00
WC_VEHICLE_DEPOT , WC_NONE ,
2009-11-24 17:28:29 +00:00
WDF_UNCLICK_BUTTONS ,
2009-11-15 10:26:01 +00:00
_nested_train_depot_widgets , lengthof ( _nested_train_depot_widgets )
2009-03-15 15:12:06 +00:00
) ;
2006-09-26 16:47:51 +00:00
2009-03-15 15:12:06 +00:00
static const WindowDesc _ship_depot_desc (
2009-11-28 14:42:35 +00:00
WDP_AUTO , 306 , 99 ,
2007-02-01 15:49:12 +00:00
WC_VEHICLE_DEPOT , WC_NONE ,
2009-11-24 17:28:29 +00:00
WDF_UNCLICK_BUTTONS ,
2009-11-15 10:26:01 +00:00
_nested_train_depot_widgets , lengthof ( _nested_train_depot_widgets )
2009-03-15 15:12:06 +00:00
) ;
2006-09-26 16:47:51 +00:00
2009-03-15 15:12:06 +00:00
static const WindowDesc _aircraft_depot_desc (
2009-11-28 14:42:35 +00:00
WDP_AUTO , 332 , 99 ,
2007-02-01 15:49:12 +00:00
WC_VEHICLE_DEPOT , WC_NONE ,
2009-11-24 17:28:29 +00:00
WDF_UNCLICK_BUTTONS ,
2009-11-15 10:26:01 +00:00
_nested_train_depot_widgets , lengthof ( _nested_train_depot_widgets )
2009-03-15 15:12:06 +00:00
) ;
2006-09-26 16:47:51 +00:00
2008-05-25 17:22:49 +00:00
extern void DepotSortList ( VehicleList * list ) ;
2006-09-26 16:47:51 +00:00
2007-08-26 21:21:59 +00:00
/**
* This is the Callback method after the cloning attempt of a vehicle
2010-01-11 18:46:09 +00:00
* @ param result the result of the cloning command
2007-08-26 21:21:59 +00:00
* @ param tile unused
* @ param p1 unused
* @ param p2 unused
*/
2010-01-11 18:46:09 +00:00
void CcCloneVehicle ( const CommandCost & result , TileIndex tile , uint32 p1 , uint32 p2 )
2006-09-26 16:47:51 +00:00
{
2010-01-11 18:46:09 +00:00
if ( result . Failed ( ) ) return ;
2007-08-26 21:21:59 +00:00
2009-05-16 23:34:14 +00:00
const Vehicle * v = Vehicle : : Get ( _new_vehicle_id ) ;
2007-08-26 21:21:59 +00:00
2007-08-29 20:50:58 +00:00
ShowVehicleViewWindow ( v ) ;
2006-09-26 16:47:51 +00:00
}
2008-05-25 09:40:44 +00:00
static void TrainDepotMoveVehicle ( const Vehicle * wagon , VehicleID sel , const Vehicle * head )
2006-09-26 16:47:51 +00:00
{
2009-05-16 23:34:14 +00:00
const Vehicle * v = Vehicle : : Get ( sel ) ;
2006-09-26 16:47:51 +00:00
if ( v = = wagon ) return ;
if ( wagon = = NULL ) {
2009-07-20 19:58:33 +00:00
if ( head ! = NULL ) wagon = head - > Last ( ) ;
2009-08-20 10:23:39 +00:00
} else {
2007-08-30 21:11:12 +00:00
wagon = wagon - > Previous ( ) ;
2006-09-26 16:47:51 +00:00
if ( wagon = = NULL ) return ;
}
if ( wagon = = v ) return ;
2009-04-21 23:40:56 +00:00
DoCommandP ( v - > tile , v - > index + ( ( wagon = = NULL ? INVALID_VEHICLE : wagon - > index ) < < 16 ) , _ctrl_pressed ? 1 : 0 , CMD_MOVE_RAIL_VEHICLE | CMD_MSG ( STR_ERROR_CAN_T_MOVE_VEHICLE ) ) ;
2006-09-26 16:47:51 +00:00
}
2009-09-23 20:48:30 +00:00
/** Array containing the cell size in pixels of the #DEPOT_WIDGET_MATRIX widget for each vehicle type.
* @ note The train vehicle type uses the entire row for each train . */
2009-11-17 22:58:41 +00:00
static Dimension _base_block_sizes [ 4 ] ;
2007-02-10 13:37:32 +00:00
2009-09-27 08:28:49 +00:00
static void InitBlocksizeForShipAircraft ( VehicleType type )
2007-02-10 13:37:32 +00:00
{
uint max_width = 0 ;
uint max_height = 0 ;
2008-04-29 21:31:29 +00:00
const Engine * e ;
FOR_ALL_ENGINES_OF_TYPE ( e , type ) {
EngineID eid = e - > index ;
2007-02-10 13:37:32 +00:00
uint x , y ;
switch ( type ) {
default : NOT_REACHED ( ) ;
2008-04-29 07:11:54 +00:00
case VEH_SHIP : GetShipSpriteSize ( eid , x , y ) ; break ;
case VEH_AIRCRAFT : GetAircraftSpriteSize ( eid , x , y ) ; break ;
2007-02-10 13:37:32 +00:00
}
if ( x > max_width ) max_width = x ;
if ( y > max_height ) max_height = y ;
}
switch ( type ) {
default : NOT_REACHED ( ) ;
2007-03-08 16:27:54 +00:00
case VEH_SHIP :
2009-11-17 22:58:41 +00:00
_base_block_sizes [ VEH_SHIP ] . width = max ( 76U , max_width ) ;
2007-02-10 13:37:32 +00:00
break ;
2007-03-08 16:27:54 +00:00
case VEH_AIRCRAFT :
2009-11-17 22:58:41 +00:00
_base_block_sizes [ VEH_AIRCRAFT ] . width = max ( 67U , max_width ) ;
2007-02-10 13:37:32 +00:00
break ;
}
2009-11-17 22:58:41 +00:00
_base_block_sizes [ type ] . height = max ( GetVehicleHeight ( type ) , max_height ) ;
2007-02-10 13:37:32 +00:00
}
2009-09-27 08:28:49 +00:00
/** Set the size of the blocks in the window so we can be sure that they are big enough for the vehicle sprites in the current game.
* @ note Calling this function once for each game is enough . */
2007-02-10 13:37:32 +00:00
void InitDepotWindowBlockSizes ( )
{
2009-11-17 22:58:41 +00:00
_base_block_sizes [ VEH_TRAIN ] . width = 0 ;
_base_block_sizes [ VEH_TRAIN ] . height = GetVehicleHeight ( VEH_TRAIN ) ;
2009-09-27 08:28:49 +00:00
2009-11-17 22:58:41 +00:00
_base_block_sizes [ VEH_ROAD ] . width = 32 ;
_base_block_sizes [ VEH_ROAD ] . height = GetVehicleHeight ( VEH_ROAD ) ;
2009-09-27 08:28:49 +00:00
InitBlocksizeForShipAircraft ( VEH_SHIP ) ;
InitBlocksizeForShipAircraft ( VEH_AIRCRAFT ) ;
2007-02-10 13:37:32 +00:00
}
2008-05-13 13:39:50 +00:00
static void DepotSellAllConfirmationCallback ( Window * w , bool confirmed ) ;
const Sprite * GetAircraftSprite ( EngineID engine ) ;
struct DepotWindow : Window {
VehicleID sel ;
VehicleType type ;
bool generate_list ;
2008-05-25 17:22:49 +00:00
VehicleList vehicle_list ;
VehicleList wagon_list ;
2006-12-07 00:51:20 +00:00
2009-09-26 19:21:20 +00:00
DepotWindow ( const WindowDesc * desc , TileIndex tile , VehicleType type ) : Window ( )
2008-05-13 13:39:50 +00:00
{
2009-11-16 20:34:57 +00:00
assert ( IsCompanyBuildableVehicleType ( type ) ) ; // ensure that we make the call with a valid type
2008-05-13 13:39:50 +00:00
this - > sel = INVALID_VEHICLE ;
this - > generate_list = true ;
2009-09-26 18:47:41 +00:00
this - > type = type ;
2007-02-10 13:37:32 +00:00
2009-09-26 19:21:20 +00:00
this - > CreateNestedTree ( desc ) ;
this - > SetupWidgetData ( type ) ;
this - > FinishInitNested ( desc , tile ) ;
2009-10-20 21:25:25 +00:00
2009-09-26 19:21:20 +00:00
this - > owner = GetTileOwner ( tile ) ;
2009-11-16 20:34:57 +00:00
_backup_orders_tile = 0 ;
2008-05-13 13:39:50 +00:00
}
~ DepotWindow ( )
{
DeleteWindowById ( WC_BUILD_VEHICLE , this - > window_number ) ;
}
2006-12-07 00:51:20 +00:00
2009-09-26 18:15:35 +00:00
/** Draw a vehicle in the depot window in the box with the top left corner at x,y.
* @ param v Vehicle to draw .
2009-11-17 16:03:51 +00:00
* @ param left Left side of the box to draw in .
* @ param right Right side of the box to draw in .
2009-09-26 18:15:35 +00:00
* @ param y Top of the box to draw in .
2009-03-14 18:16:29 +00:00
*/
2009-11-17 16:03:51 +00:00
void DrawVehicleInDepot ( const Vehicle * v , int left , int right , int y ) const
2008-05-13 13:39:50 +00:00
{
2009-07-18 17:38:18 +00:00
bool free_wagon = false ;
2009-11-17 22:58:41 +00:00
int sprite_y = y + ( this - > resize . step_height - GetVehicleHeight ( v - > type ) ) / 2 ;
2008-05-13 13:39:50 +00:00
2009-11-18 10:45:49 +00:00
bool rtl = _dynlang . text_dir = = TD_RTL ;
int image_left = rtl ? left + this - > count_width : left + this - > header_width ;
int image_right = rtl ? right - this - > header_width : right - this - > count_width ;
2008-05-13 13:39:50 +00:00
switch ( v - > type ) {
2009-07-18 17:38:18 +00:00
case VEH_TRAIN : {
const Train * u = Train : : From ( v ) ;
free_wagon = u - > IsFreeWagon ( ) ;
uint x_space = free_wagon ? TRAININFO_DEFAULT_VEHICLE_WIDTH : 0 ;
2009-11-18 10:45:49 +00:00
DrawTrainImage ( u , image_left + ( rtl ? 0 : x_space ) , image_right - ( rtl ? x_space : 0 ) , sprite_y - 1 , this - > sel , free_wagon ? 0 : this - > hscroll . GetPosition ( ) ) ;
2008-05-13 13:39:50 +00:00
/* Number of wagons relative to a standard length wagon (rounded up) */
2010-04-18 14:56:05 +00:00
SetDParam ( 0 , CeilDiv ( u - > tcache . cached_total_length , 8 ) ) ;
2009-11-18 10:45:49 +00:00
DrawString ( rtl ? left + WD_FRAMERECT_LEFT : right - this - > count_width , rtl ? left + this - > count_width : right - WD_FRAMERECT_RIGHT , y + ( this - > resize . step_height - FONT_HEIGHT_SMALL ) / 2 , STR_TINY_BLACK_COMA , TC_FROMSTRING , SA_RIGHT ) ; // Draw the counter
2008-05-13 13:39:50 +00:00
break ;
2009-07-18 17:38:18 +00:00
}
2008-05-13 13:39:50 +00:00
2009-11-18 10:45:49 +00:00
case VEH_ROAD : DrawRoadVehImage ( v , image_left , image_right , sprite_y , this - > sel ) ; break ;
case VEH_SHIP : DrawShipImage ( v , image_left , image_right , sprite_y , this - > sel ) ; break ;
2008-05-13 13:39:50 +00:00
case VEH_AIRCRAFT : {
2008-09-02 15:20:38 +00:00
const Sprite * spr = GetSprite ( v - > GetImage ( DIR_W ) , ST_NORMAL ) ;
2009-11-18 10:45:49 +00:00
DrawAircraftImage ( v , image_left , image_right ,
2008-05-13 13:39:50 +00:00
y + max ( spr - > height + spr - > y_offs - 14 , 0 ) , // tall sprites needs an y offset
this - > sel ) ;
} break ;
default : NOT_REACHED ( ) ;
}
2006-12-07 00:51:20 +00:00
2009-11-18 10:45:49 +00:00
uint diff_x , diff_y ;
if ( v - > type = = VEH_TRAIN | | v - > type = = VEH_ROAD ) {
/* Arrange unitnumber and flag horizontally */
diff_x = this - > flag_width + WD_FRAMERECT_LEFT ;
diff_y = ( this - > resize . step_height - this - > flag_height ) / 2 - 2 ;
2008-05-13 13:39:50 +00:00
} else {
2009-11-18 10:45:49 +00:00
/* Arrange unitnumber and flag vertically */
diff_x = WD_FRAMERECT_LEFT ;
diff_y = FONT_HEIGHT_NORMAL + WD_PAR_VSEP_NORMAL ;
}
int text_left = rtl ? right - this - > header_width - 1 : left + diff_x ;
int text_right = rtl ? right - diff_x : left + this - > header_width - 1 ;
2006-12-07 00:51:20 +00:00
2009-11-18 10:45:49 +00:00
if ( free_wagon ) {
DrawString ( text_left , text_right , y + 2 , STR_DEPOT_NO_ENGINE ) ;
} else {
DrawSprite ( ( v - > vehstatus & VS_STOPPED ) ? SPR_FLAG_VEH_STOPPED : SPR_FLAG_VEH_RUNNING , PAL_NONE , rtl ? right - this - > flag_width : left + WD_FRAMERECT_LEFT , y + diff_y ) ;
2007-02-10 13:37:32 +00:00
2009-07-18 17:38:18 +00:00
SetDParam ( 0 , v - > unitnumber ) ;
2009-11-18 10:45:49 +00:00
DrawString ( text_left , text_right , y + 2 , ( uint16 ) ( v - > max_age - DAYS_IN_LEAP_YEAR ) > = v - > age ? STR_BLACK_COMMA : STR_RED_COMMA ) ;
2009-07-18 17:38:18 +00:00
}
2006-12-07 00:51:20 +00:00
}
2009-09-26 19:21:20 +00:00
void DrawWidget ( const Rect & r , int widget ) const
2008-05-13 13:39:50 +00:00
{
2009-09-26 19:21:20 +00:00
if ( widget ! = DEPOT_WIDGET_MATRIX ) return ;
2006-12-07 00:51:20 +00:00
2009-11-18 10:45:49 +00:00
bool rtl = _dynlang . text_dir = = TD_RTL ;
2009-09-26 19:21:20 +00:00
/* Set the row and number of boxes in each row based on the number of boxes drawn in the matrix */
uint16 mat_data = this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_MATRIX ) - > widget_data ;
uint16 rows_in_display = GB ( mat_data , MAT_ROW_START , MAT_ROW_BITS ) ;
uint16 boxes_in_each_row = GB ( mat_data , MAT_COL_START , MAT_COL_BITS ) ;
2006-12-07 00:51:20 +00:00
2009-09-02 07:36:39 +00:00
uint16 num = this - > vscroll . GetPosition ( ) * boxes_in_each_row ;
2009-09-26 16:06:54 +00:00
int maxval = min ( this - > vehicle_list . Length ( ) , num + ( rows_in_display * boxes_in_each_row ) ) ;
2009-11-17 16:03:51 +00:00
int y ;
for ( y = r . top + 1 ; num < maxval ; y + = this - > resize . step_height ) { // Draw the rows
2009-11-18 10:45:49 +00:00
for ( byte i = 0 ; i < boxes_in_each_row & & num < maxval ; i + + , num + + ) {
2008-05-13 13:39:50 +00:00
/* Draw all vehicles in the current row */
2008-05-25 17:22:49 +00:00
const Vehicle * v = this - > vehicle_list [ num ] ;
2009-11-18 10:45:49 +00:00
if ( boxes_in_each_row = = 1 ) {
this - > DrawVehicleInDepot ( v , r . left , r . right , y ) ;
} else {
int x = r . left + ( rtl ? ( boxes_in_each_row - i - 1 ) : i ) * this - > resize . step_width ;
this - > DrawVehicleInDepot ( v , x , x + this - > resize . step_width - 1 , y ) ;
}
2008-05-13 13:39:50 +00:00
}
}
2006-10-05 13:11:17 +00:00
2009-09-02 07:36:39 +00:00
maxval = min ( this - > vehicle_list . Length ( ) + this - > wagon_list . Length ( ) , ( this - > vscroll . GetPosition ( ) * boxes_in_each_row ) + ( rows_in_display * boxes_in_each_row ) ) ;
2006-10-05 12:59:28 +00:00
2008-05-13 13:39:50 +00:00
/* draw the train wagons, that do not have an engine in front */
2009-12-06 11:46:57 +00:00
for ( ; num < maxval ; num + + , y + = this - > resize . step_height ) {
2009-07-18 17:38:18 +00:00
const Vehicle * v = this - > wagon_list [ num - this - > vehicle_list . Length ( ) ] ;
2009-11-17 16:03:51 +00:00
this - > DrawVehicleInDepot ( v , r . left , r . right , y ) ;
2009-09-26 19:21:20 +00:00
}
}
void SetStringParameters ( int widget ) const
{
if ( widget ! = DEPOT_WIDGET_CAPTION ) return ;
/* locate the depot struct */
TileIndex tile = this - > window_number ;
2010-05-12 18:19:36 +00:00
SetDParam ( 0 , this - > type ) ;
SetDParam ( 1 , ( this - > type = = VEH_AIRCRAFT ) ? GetStationIndex ( tile ) : GetDepotIndex ( tile ) ) ;
2008-05-13 13:39:50 +00:00
}
struct GetDepotVehiclePtData {
2008-05-25 09:40:44 +00:00
const Vehicle * head ;
const Vehicle * wagon ;
2008-05-13 13:39:50 +00:00
} ;
enum DepotGUIAction {
MODE_ERROR ,
MODE_DRAG_VEHICLE ,
MODE_SHOW_VEHICLE ,
MODE_START_STOP ,
} ;
2008-05-25 09:40:44 +00:00
DepotGUIAction GetVehicleFromDepotWndPt ( int x , int y , const Vehicle * * veh , GetDepotVehiclePtData * d ) const
2008-05-13 13:39:50 +00:00
{
2009-11-18 10:45:49 +00:00
const NWidgetCore * matrix_widget = this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_MATRIX ) ;
/* In case of RTL the widgets are swapped as a whole */
if ( _dynlang . text_dir = = TD_RTL ) x = matrix_widget - > current_x - x ;
2009-11-17 22:58:41 +00:00
uint xt = 0 , xm = 0 , ym = 0 ;
2008-05-13 13:39:50 +00:00
if ( this - > type = = VEH_TRAIN ) {
2009-11-17 22:58:41 +00:00
xm = x ;
2008-05-13 13:39:50 +00:00
} else {
xt = x / this - > resize . step_width ;
xm = x % this - > resize . step_width ;
2009-09-02 07:36:39 +00:00
if ( xt > = this - > hscroll . GetCapacity ( ) ) return MODE_ERROR ;
2008-05-13 13:39:50 +00:00
}
2009-11-17 22:58:41 +00:00
ym = y % this - > resize . step_height ;
2008-05-13 13:39:50 +00:00
2009-10-20 21:41:44 +00:00
uint row = y / this - > resize . step_height ;
2009-09-02 07:36:39 +00:00
if ( row > = this - > vscroll . GetCapacity ( ) ) return MODE_ERROR ;
2008-05-13 13:39:50 +00:00
2009-11-18 10:45:49 +00:00
uint boxes_in_each_row = GB ( matrix_widget - > widget_data , MAT_COL_START , MAT_COL_BITS ) ;
2009-11-17 22:58:41 +00:00
uint pos = ( ( row + this - > vscroll . GetPosition ( ) ) * boxes_in_each_row ) + xt ;
2008-05-13 13:39:50 +00:00
2009-11-17 22:58:41 +00:00
if ( this - > vehicle_list . Length ( ) + this - > wagon_list . Length ( ) < = pos ) {
/* Clicking on 'line' / 'block' without a vehicle */
2008-05-13 13:39:50 +00:00
if ( this - > type = = VEH_TRAIN ) {
2009-11-17 22:58:41 +00:00
/* End the dragging */
2008-05-13 13:39:50 +00:00
d - > head = NULL ;
d - > wagon = NULL ;
return MODE_DRAG_VEHICLE ;
2006-10-05 12:59:28 +00:00
} else {
2008-05-13 13:39:50 +00:00
return MODE_ERROR ; // empty block, so no vehicle is selected
2006-10-05 12:59:28 +00:00
}
2008-05-13 13:39:50 +00:00
}
2006-09-26 16:47:51 +00:00
2009-11-18 10:45:49 +00:00
bool wagon = false ;
2009-11-17 22:58:41 +00:00
if ( this - > vehicle_list . Length ( ) > pos ) {
2008-05-25 17:22:49 +00:00
* veh = this - > vehicle_list [ pos ] ;
2009-11-17 22:58:41 +00:00
/* Skip vehicles that are scrolled off the list */
x + = this - > hscroll . GetPosition ( ) ;
2008-05-13 13:39:50 +00:00
} else {
2008-05-25 17:22:49 +00:00
pos - = this - > vehicle_list . Length ( ) ;
* veh = this - > wagon_list [ pos ] ;
2008-05-13 13:39:50 +00:00
/* free wagons don't have an initial loco. */
2009-07-17 22:00:13 +00:00
x - = VEHICLEINFO_FULL_VEHICLE_WIDTH ;
2009-11-18 10:45:49 +00:00
wagon = true ;
2008-05-13 13:39:50 +00:00
}
2006-09-26 16:47:51 +00:00
2009-11-17 22:58:41 +00:00
const Train * v = NULL ;
if ( this - > type = = VEH_TRAIN ) {
v = Train : : From ( * veh ) ;
d - > head = d - > wagon = v ;
}
2006-09-26 16:47:51 +00:00
2009-11-17 22:58:41 +00:00
if ( xm < = this - > header_width ) {
switch ( this - > type ) {
case VEH_TRAIN :
2009-11-18 10:45:49 +00:00
if ( wagon ) return MODE_ERROR ;
2009-11-17 22:58:41 +00:00
case VEH_ROAD :
if ( xm < = this - > flag_width ) return MODE_START_STOP ;
break ;
2006-09-26 19:20:35 +00:00
2009-11-17 22:58:41 +00:00
case VEH_SHIP :
case VEH_AIRCRAFT :
if ( xm < = this - > flag_width & & ym > = ( uint ) ( FONT_HEIGHT_NORMAL + WD_PAR_VSEP_NORMAL ) ) return MODE_START_STOP ;
break ;
2006-09-27 22:44:39 +00:00
2009-11-17 22:58:41 +00:00
default : NOT_REACHED ( ) ;
2009-07-13 19:30:37 +00:00
}
2009-11-17 22:58:41 +00:00
return MODE_SHOW_VEHICLE ;
}
2006-09-30 13:39:34 +00:00
2009-11-17 22:58:41 +00:00
if ( this - > type ! = VEH_TRAIN ) return MODE_DRAG_VEHICLE ;
2006-09-26 16:47:51 +00:00
2009-11-18 10:45:49 +00:00
/* Clicking on the counter */
if ( xm > = matrix_widget - > current_x - this - > count_width ) return wagon ? MODE_ERROR : MODE_SHOW_VEHICLE ;
2009-11-17 22:58:41 +00:00
/* Account for the header */
x - = this - > header_width ;
2006-09-26 16:47:51 +00:00
2009-11-17 22:58:41 +00:00
/* find the vehicle in this row that was clicked */
for ( ; v ! = NULL ; v = v - > Next ( ) ) {
x - = v - > GetDisplayImageWidth ( ) ;
if ( x < 0 ) break ;
2008-05-13 13:39:50 +00:00
}
2009-11-17 22:58:41 +00:00
d - > wagon = ( v ! = NULL ? v - > GetFirstEnginePart ( ) : NULL ) ;
return MODE_DRAG_VEHICLE ;
2008-05-13 13:39:50 +00:00
}
2008-02-17 12:21:05 +00:00
2009-10-20 21:41:44 +00:00
/** Handle click in the depot matrix.
* @ param x Horizontal position in the matrix widget in pixels .
* @ param y Vertical position in the matrix widget in pixels .
*/
2008-05-13 13:39:50 +00:00
void DepotClick ( int x , int y )
{
2008-05-13 22:02:14 +00:00
GetDepotVehiclePtData gdvp = { NULL , NULL } ;
2008-05-25 09:40:44 +00:00
const Vehicle * v = NULL ;
2008-05-13 13:39:50 +00:00
DepotGUIAction mode = this - > GetVehicleFromDepotWndPt ( x , y , & v , & gdvp ) ;
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
/* share / copy orders */
2009-04-19 10:31:30 +00:00
if ( _thd . place_mode ! = HT_NONE & & mode ! = MODE_ERROR ) {
2008-05-13 13:39:50 +00:00
_place_clicked_vehicle = ( this - > type = = VEH_TRAIN ? gdvp . head : v ) ;
return ;
}
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
if ( this - > type = = VEH_TRAIN ) v = gdvp . wagon ;
switch ( mode ) {
case MODE_ERROR : // invalid
return ;
case MODE_DRAG_VEHICLE : { // start dragging of vehicle
VehicleID sel = this - > sel ;
if ( this - > type = = VEH_TRAIN & & sel ! = INVALID_VEHICLE ) {
this - > sel = INVALID_VEHICLE ;
TrainDepotMoveVehicle ( v , sel , gdvp . head ) ;
} else if ( v ! = NULL ) {
int image = v - > GetImage ( DIR_W ) ;
this - > sel = v - > index ;
this - > SetDirty ( ) ;
2009-04-19 10:31:30 +00:00
SetObjectToPlaceWnd ( image , GetVehiclePalette ( v ) , HT_DRAG , this ) ;
2008-07-20 19:21:18 +00:00
switch ( v - > type ) {
case VEH_TRAIN :
2009-06-06 16:54:22 +00:00
_cursor . short_vehicle_offset = 16 - Train : : From ( v ) - > tcache . cached_veh_length * 2 ;
2008-07-20 19:21:18 +00:00
break ;
case VEH_ROAD :
2009-06-06 16:54:22 +00:00
_cursor . short_vehicle_offset = 16 - RoadVehicle : : From ( v ) - > rcache . cached_veh_length * 2 ;
2008-07-20 19:21:18 +00:00
break ;
default :
_cursor . short_vehicle_offset = 0 ;
break ;
}
2008-05-13 13:39:50 +00:00
_cursor . vehchain = _ctrl_pressed ;
}
} break ;
case MODE_SHOW_VEHICLE : // show info window
ShowVehicleViewWindow ( v ) ;
break ;
2010-04-24 14:29:30 +00:00
case MODE_START_STOP : // click start/stop flag
2010-04-24 20:55:51 +00:00
StartStopVehicle ( v , false ) ;
2010-04-24 14:29:30 +00:00
break ;
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
default : NOT_REACHED ( ) ;
}
}
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
/**
2009-03-14 18:16:29 +00:00
* Clones a vehicle
* @ param * v is the original vehicle to clone
*/
2009-07-13 22:07:07 +00:00
void HandleCloneVehClick ( const Vehicle * v )
2008-05-13 13:39:50 +00:00
{
2009-07-22 20:17:07 +00:00
if ( v = = NULL | | ! IsCompanyBuildableVehicleType ( v ) ) return ;
2008-05-13 13:39:50 +00:00
if ( ! v - > IsPrimaryVehicle ( ) ) {
v = v - > First ( ) ;
/* Do nothing when clicking on a train in depot with no loc attached */
2009-07-01 22:22:01 +00:00
if ( v - > type = = VEH_TRAIN & & ! Train : : From ( v ) - > IsFrontEngine ( ) ) return ;
2008-05-13 13:39:50 +00:00
}
2006-09-26 16:47:51 +00:00
2009-09-07 08:59:43 +00:00
DoCommandP ( this - > window_number , v - > index , _ctrl_pressed ? 1 : 0 , CMD_CLONE_VEHICLE | CMD_MSG ( STR_ERROR_CAN_T_BUY_TRAIN + v - > type ) , CcCloneVehicle ) ;
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
ResetObjectToPlace ( ) ;
}
2006-09-26 16:47:51 +00:00
2009-09-26 19:21:20 +00:00
/* Function to set up vehicle specific widgets (mainly sprites and strings).
2008-05-13 13:39:50 +00:00
* Only use this if it ' s the same widget , that ' s used for more than one vehicle type and it needs different text / sprites
2009-09-26 19:21:20 +00:00
* Vehicle specific text / sprites , that ' s in a widget , that ' s only shown for one vehicle type ( like sell whole train ) is set in the nested widget array
2008-05-13 13:39:50 +00:00
*/
2009-09-26 19:21:20 +00:00
void SetupWidgetData ( VehicleType type )
2008-05-13 13:39:50 +00:00
{
2009-11-22 18:26:01 +00:00
if ( type ! = VEH_TRAIN ) this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL_CHAIN ) - > fill_y = 0 ; // Disable vertical filling of chain-sell widget for non-train windows.
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_STOP_ALL ) - > tool_tip = STR_DEPOT_MASS_STOP_DEPOT_TRAIN_TOOLTIP + type ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_START_ALL ) - > tool_tip = STR_DEPOT_MASS_START_DEPOT_TRAIN_TOOLTIP + type ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL ) - > tool_tip = STR_DEPOT_TRAIN_SELL_TOOLTIP + type ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL_ALL ) - > tool_tip = STR_DEPOT_SELL_ALL_BUTTON_TRAIN_TOOLTIP + type ;
2009-07-22 20:17:07 +00:00
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_BUILD ) - > SetDataTip ( STR_DEPOT_TRAIN_NEW_VEHICLES_BUTTON + type , STR_DEPOT_TRAIN_NEW_VEHICLES_TOOLTIP + type ) ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_CLONE ) - > SetDataTip ( STR_DEPOT_CLONE_TRAIN + type , STR_DEPOT_CLONE_TRAIN_DEPOT_INFO + type ) ;
2009-07-22 20:17:07 +00:00
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_LOCATION ) - > tool_tip = STR_DEPOT_TRAIN_LOCATION_TOOLTIP + type ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_VEHICLE_LIST ) - > tool_tip = STR_DEPOT_VEHICLE_ORDER_LIST_TRAIN_TOOLTIP + type ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_AUTOREPLACE ) - > tool_tip = STR_DEPOT_AUTOREPLACE_TRAIN_TOOLTIP + type ;
2009-07-22 20:17:07 +00:00
2008-05-13 13:39:50 +00:00
switch ( type ) {
default : NOT_REACHED ( ) ;
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
case VEH_TRAIN :
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_VEHICLE_LIST ) - > widget_data = STR_TRAIN ;
2008-05-13 13:39:50 +00:00
/* Sprites */
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL ) - > widget_data = SPR_SELL_TRAIN ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL_ALL ) - > widget_data = SPR_SELL_ALL_TRAIN ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_AUTOREPLACE ) - > widget_data = SPR_REPLACE_TRAIN ;
2008-05-13 13:39:50 +00:00
break ;
case VEH_ROAD :
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_VEHICLE_LIST ) - > widget_data = STR_LORRY ;
2008-05-13 13:39:50 +00:00
/* Sprites */
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL ) - > widget_data = SPR_SELL_ROADVEH ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL_ALL ) - > widget_data = SPR_SELL_ALL_ROADVEH ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_AUTOREPLACE ) - > widget_data = SPR_REPLACE_ROADVEH ;
2008-05-13 13:39:50 +00:00
break ;
case VEH_SHIP :
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_VEHICLE_LIST ) - > widget_data = STR_SHIP ;
2008-05-13 13:39:50 +00:00
/* Sprites */
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL ) - > widget_data = SPR_SELL_SHIP ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL_ALL ) - > widget_data = SPR_SELL_ALL_SHIP ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_AUTOREPLACE ) - > widget_data = SPR_REPLACE_SHIP ;
2008-05-13 13:39:50 +00:00
break ;
case VEH_AIRCRAFT :
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_VEHICLE_LIST ) - > widget_data = STR_PLANE ;
2008-05-13 13:39:50 +00:00
/* Sprites */
2009-09-26 19:21:20 +00:00
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL ) - > widget_data = SPR_SELL_AIRCRAFT ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_SELL_ALL ) - > widget_data = SPR_SELL_ALL_AIRCRAFT ;
this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_AUTOREPLACE ) - > widget_data = SPR_REPLACE_AIRCRAFT ;
2008-05-13 13:39:50 +00:00
break ;
}
}
2009-11-17 22:58:41 +00:00
uint count_width ;
uint header_width ;
uint flag_width ;
uint flag_height ;
2009-11-22 18:28:14 +00:00
virtual void UpdateWidgetSize ( int widget , Dimension * size , const Dimension & padding , Dimension * fill , Dimension * resize )
2009-09-26 19:21:20 +00:00
{
switch ( widget ) {
case DEPOT_WIDGET_SELL_CHAIN :
case DEPOT_WIDGET_H_SCROLL :
/* Hide the 'sell chain' and the horizontal scrollbar when not a train depot. */
if ( this - > type ! = VEH_TRAIN ) {
size - > height = 0 ;
resize - > height = 0 ;
}
break ;
2008-05-13 13:39:50 +00:00
2009-11-17 22:58:41 +00:00
case DEPOT_WIDGET_MATRIX : {
uint min_height = 0 ;
if ( this - > type = = VEH_TRAIN ) {
SetDParam ( 0 , 100 ) ;
this - > count_width = GetStringBoundingBox ( STR_TINY_BLACK_COMA ) . width + WD_FRAMERECT_LEFT + WD_FRAMERECT_RIGHT ;
2009-11-18 10:45:49 +00:00
} else {
this - > count_width = 0 ;
2009-11-17 22:58:41 +00:00
}
2009-12-20 16:42:35 +00:00
Dimension unumber = { GetDigitWidth ( ) * 4 , FONT_HEIGHT_NORMAL } ;
2009-11-17 22:58:41 +00:00
const Sprite * spr = GetSprite ( SPR_FLAG_VEH_STOPPED , ST_NORMAL ) ;
this - > flag_width = spr - > width + WD_FRAMERECT_RIGHT ;
this - > flag_height = spr - > height ;
if ( this - > type = = VEH_TRAIN | | this - > type = = VEH_ROAD ) {
min_height = max < uint > ( unumber . height + WD_MATRIX_TOP , spr - > height ) ;
2009-12-20 16:42:35 +00:00
this - > header_width = unumber . width + this - > flag_width + WD_FRAMERECT_LEFT ;
2009-11-17 22:58:41 +00:00
} else {
min_height = unumber . height + spr - > height + WD_MATRIX_TOP + WD_PAR_VSEP_NORMAL + WD_MATRIX_BOTTOM ;
this - > header_width = max < uint > ( unumber . width , this - > flag_width ) + WD_FRAMERECT_RIGHT ;
}
2009-11-18 10:45:49 +00:00
int base_width = this - > count_width + this - > header_width ;
2009-11-17 22:58:41 +00:00
resize - > height = max ( _base_block_sizes [ this - > type ] . height , min_height ) ;
if ( this - > type = = VEH_TRAIN ) {
resize - > width = 1 ;
2009-11-17 23:32:18 +00:00
size - > width = base_width + 2 * 29 ; // about 2 parts
size - > height = resize - > height * 6 ;
2009-11-17 22:58:41 +00:00
} else {
resize - > width = base_width + _base_block_sizes [ this - > type ] . width ;
size - > width = resize - > width * ( this - > type = = VEH_ROAD ? 5 : 3 ) ;
size - > height = resize - > height * ( this - > type = = VEH_ROAD ? 5 : 3 ) ;
}
2009-11-22 18:29:52 +00:00
fill - > width = resize - > width ;
fill - > height = resize - > height ;
2009-11-17 22:58:41 +00:00
} break ;
2009-09-26 19:21:20 +00:00
}
2008-05-13 13:39:50 +00:00
}
virtual void OnInvalidateData ( int data )
{
this - > generate_list = true ;
}
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
virtual void OnPaint ( )
{
if ( this - > generate_list ) {
/* Generate the vehicle list
* It ' s ok to use the wagon pointers for non - trains as they will be ignored */
2008-05-25 17:22:49 +00:00
BuildDepotVehicleList ( this - > type , this - > window_number , & this - > vehicle_list , & this - > wagon_list ) ;
2008-05-13 13:39:50 +00:00
this - > generate_list = false ;
2008-05-25 17:22:49 +00:00
DepotSortList ( & this - > vehicle_list ) ;
2008-05-13 13:39:50 +00:00
}
2009-09-26 19:21:20 +00:00
/* determine amount of items for scroller */
if ( this - > type = = VEH_TRAIN ) {
uint max_width = VEHICLEINFO_FULL_VEHICLE_WIDTH ;
for ( uint num = 0 ; num < this - > vehicle_list . Length ( ) ; num + + ) {
uint width = 0 ;
for ( const Train * v = Train : : From ( this - > vehicle_list [ num ] ) ; v ! = NULL ; v = v - > Next ( ) ) {
width + = v - > GetDisplayImageWidth ( ) ;
}
max_width = max ( max_width , width ) ;
}
/* Always have 1 empty row, so people can change the setting of the train */
this - > vscroll . SetCount ( this - > vehicle_list . Length ( ) + this - > wagon_list . Length ( ) + 1 ) ;
this - > hscroll . SetCount ( max_width ) ;
} else {
2010-04-18 14:56:05 +00:00
this - > vscroll . SetCount ( CeilDiv ( this - > vehicle_list . Length ( ) , this - > hscroll . GetCapacity ( ) ) ) ;
2009-09-26 19:21:20 +00:00
}
2009-10-11 08:23:30 +00:00
/* Setup disabled buttons. */
TileIndex tile = this - > window_number ;
this - > SetWidgetsDisabledState ( ! IsTileOwner ( tile , _local_company ) ,
DEPOT_WIDGET_STOP_ALL ,
DEPOT_WIDGET_START_ALL ,
DEPOT_WIDGET_SELL ,
DEPOT_WIDGET_SELL_CHAIN ,
DEPOT_WIDGET_SELL_ALL ,
DEPOT_WIDGET_BUILD ,
DEPOT_WIDGET_CLONE ,
DEPOT_WIDGET_AUTOREPLACE ,
WIDGET_LIST_END ) ;
2009-09-26 19:21:20 +00:00
this - > DrawWidgets ( ) ;
2008-05-13 13:39:50 +00:00
}
2010-01-30 18:34:48 +00:00
virtual void OnClick ( Point pt , int widget , int click_count )
2008-05-13 13:39:50 +00:00
{
switch ( widget ) {
2009-10-20 21:41:44 +00:00
case DEPOT_WIDGET_MATRIX : { // List
NWidgetBase * nwi = this - > GetWidget < NWidgetBase > ( DEPOT_WIDGET_MATRIX ) ;
this - > DepotClick ( pt . x - nwi - > pos_x , pt . y - nwi - > pos_y ) ;
2008-05-13 13:39:50 +00:00
break ;
2009-10-20 21:41:44 +00:00
}
2008-05-13 13:39:50 +00:00
case DEPOT_WIDGET_BUILD : // Build vehicle
ResetObjectToPlace ( ) ;
ShowBuildVehicleWindow ( this - > window_number , this - > type ) ;
break ;
case DEPOT_WIDGET_CLONE : // Clone button
2009-09-13 19:15:59 +00:00
this - > SetWidgetDirty ( DEPOT_WIDGET_CLONE ) ;
2008-05-13 13:39:50 +00:00
this - > ToggleWidgetLoweredState ( DEPOT_WIDGET_CLONE ) ;
if ( this - > IsWidgetLowered ( DEPOT_WIDGET_CLONE ) ) {
static const CursorID clone_icons [ ] = {
SPR_CURSOR_CLONE_TRAIN , SPR_CURSOR_CLONE_ROADVEH ,
SPR_CURSOR_CLONE_SHIP , SPR_CURSOR_CLONE_AIRPLANE
} ;
_place_clicked_vehicle = NULL ;
2009-04-19 10:31:30 +00:00
SetObjectToPlaceWnd ( clone_icons [ this - > type ] , PAL_NONE , HT_RECT , this ) ;
2008-05-13 13:39:50 +00:00
} else {
ResetObjectToPlace ( ) ;
}
break ;
case DEPOT_WIDGET_LOCATION :
if ( _ctrl_pressed ) {
ShowExtraViewPortWindow ( this - > window_number ) ;
} else {
ScrollMainWindowToTile ( this - > window_number ) ;
}
break ;
case DEPOT_WIDGET_STOP_ALL :
case DEPOT_WIDGET_START_ALL :
2008-12-28 14:37:19 +00:00
DoCommandP ( this - > window_number , 0 , this - > type | ( widget = = DEPOT_WIDGET_START_ALL ? ( 1 < < 5 ) : 0 ) , CMD_MASS_START_STOP ) ;
2008-05-13 13:39:50 +00:00
break ;
case DEPOT_WIDGET_SELL_ALL :
/* Only open the confimation window if there are anything to sell */
2008-05-25 17:22:49 +00:00
if ( this - > vehicle_list . Length ( ) ! = 0 | | this - > wagon_list . Length ( ) ! = 0 ) {
2008-05-13 13:39:50 +00:00
TileIndex tile = this - > window_number ;
byte vehtype = this - > type ;
2010-05-12 18:19:36 +00:00
SetDParam ( 0 , vehtype ) ;
SetDParam ( 1 , ( vehtype = = VEH_AIRCRAFT ) ? GetStationIndex ( tile ) : GetDepotIndex ( tile ) ) ;
2008-05-13 13:39:50 +00:00
ShowQuery (
2010-05-12 18:19:36 +00:00
STR_DEPOT_CAPTION ,
2008-05-13 13:39:50 +00:00
STR_DEPOT_SELL_CONFIRMATION_TEXT ,
this ,
DepotSellAllConfirmationCallback
) ;
}
break ;
case DEPOT_WIDGET_VEHICLE_LIST :
ShowVehicleListWindow ( GetTileOwner ( this - > window_number ) , this - > type , ( TileIndex ) this - > window_number ) ;
break ;
case DEPOT_WIDGET_AUTOREPLACE :
2008-12-28 14:37:19 +00:00
DoCommandP ( this - > window_number , this - > type , 0 , CMD_DEPOT_MASS_AUTOREPLACE ) ;
2008-05-13 13:39:50 +00:00
break ;
}
}
2008-08-02 12:43:45 +00:00
virtual void OnRightClick ( Point pt , int widget )
{
if ( widget ! = DEPOT_WIDGET_MATRIX ) return ;
GetDepotVehiclePtData gdvp = { NULL , NULL } ;
const Vehicle * v = NULL ;
2009-10-20 21:41:44 +00:00
NWidgetBase * nwi = this - > GetWidget < NWidgetBase > ( DEPOT_WIDGET_MATRIX ) ;
DepotGUIAction mode = this - > GetVehicleFromDepotWndPt ( pt . x - nwi - > pos_x , pt . y - nwi - > pos_y , & v , & gdvp ) ;
2008-08-02 12:43:45 +00:00
if ( this - > type = = VEH_TRAIN ) v = gdvp . wagon ;
if ( v ! = NULL & & mode = = MODE_DRAG_VEHICLE ) {
2009-06-27 18:26:50 +00:00
CargoArray capacity , loaded ;
2008-08-02 12:43:45 +00:00
/* Display info for single (articulated) vehicle, or for whole chain starting with selected vehicle */
bool whole_chain = ( this - > type = = VEH_TRAIN & & _ctrl_pressed ) ;
/* loop through vehicle chain and collect cargos */
uint num = 0 ;
for ( const Vehicle * w = v ; w ! = NULL ; w = w - > Next ( ) ) {
if ( w - > cargo_cap > 0 & & w - > cargo_type < NUM_CARGO ) {
capacity [ w - > cargo_type ] + = w - > cargo_cap ;
loaded [ w - > cargo_type ] + = w - > cargo . Count ( ) ;
}
2009-07-02 09:06:15 +00:00
if ( w - > type = = VEH_TRAIN & & ! Train : : From ( w ) - > HasArticulatedPart ( ) ) {
2008-08-02 12:43:45 +00:00
num + + ;
if ( ! whole_chain ) break ;
}
}
/* Build tooltipstring */
static char details [ 1024 ] ;
details [ 0 ] = ' \0 ' ;
char * pos = details ;
for ( CargoID cargo_type = 0 ; cargo_type < NUM_CARGO ; cargo_type + + ) {
if ( capacity [ cargo_type ] = = 0 ) continue ;
SetDParam ( 0 , cargo_type ) ; // {CARGO} #1
SetDParam ( 1 , loaded [ cargo_type ] ) ; // {CARGO} #2
SetDParam ( 2 , cargo_type ) ; // {SHORTCARGO} #1
SetDParam ( 3 , capacity [ cargo_type ] ) ; // {SHORTCARGO} #2
pos = GetString ( pos , STR_DEPOT_VEHICLE_TOOLTIP_CARGO , lastof ( details ) ) ;
}
/* Show tooltip window */
uint64 args [ 2 ] ;
args [ 0 ] = ( whole_chain ? num : v - > engine_type ) ;
2008-08-02 23:30:50 +00:00
args [ 1 ] = ( uint64 ) ( size_t ) details ;
2008-08-02 12:43:45 +00:00
GuiShowTooltips ( whole_chain ? STR_DEPOT_VEHICLE_TOOLTIP_CHAIN : STR_DEPOT_VEHICLE_TOOLTIP , 2 , args ) ;
} else {
/* Show tooltip help */
2009-07-22 20:17:07 +00:00
GuiShowTooltips ( STR_DEPOT_TRAIN_LIST_TOOLTIP + this - > type ) ;
2008-08-02 12:43:45 +00:00
}
}
2008-05-13 13:39:50 +00:00
virtual void OnPlaceObject ( Point pt , TileIndex tile )
{
const Vehicle * v = CheckMouseOverVehicle ( ) ;
2009-07-13 22:07:07 +00:00
if ( v ! = NULL ) this - > HandleCloneVehClick ( v ) ;
2008-05-13 13:39:50 +00:00
}
virtual void OnPlaceObjectAbort ( )
{
/* abort clone */
this - > RaiseWidget ( DEPOT_WIDGET_CLONE ) ;
2009-09-13 19:15:59 +00:00
this - > SetWidgetDirty ( DEPOT_WIDGET_CLONE ) ;
2008-05-13 13:39:50 +00:00
/* abort drag & drop */
this - > sel = INVALID_VEHICLE ;
2009-09-13 19:15:59 +00:00
this - > SetWidgetDirty ( DEPOT_WIDGET_MATRIX ) ;
2008-05-13 13:39:50 +00:00
} ;
/* check if a vehicle in a depot was clicked.. */
virtual void OnMouseLoop ( )
{
const Vehicle * v = _place_clicked_vehicle ;
/* since OTTD checks all open depot windows, we will make sure that it triggers the one with a clicked clone button */
if ( v ! = NULL & & this - > IsWidgetLowered ( DEPOT_WIDGET_CLONE ) ) {
_place_clicked_vehicle = NULL ;
2009-07-13 22:07:07 +00:00
this - > HandleCloneVehClick ( v ) ;
2008-05-13 13:39:50 +00:00
}
}
virtual void OnDragDrop ( Point pt , int widget )
{
switch ( widget ) {
case DEPOT_WIDGET_MATRIX : {
2008-05-25 09:40:44 +00:00
const Vehicle * v = NULL ;
2008-05-13 13:39:50 +00:00
VehicleID sel = this - > sel ;
this - > sel = INVALID_VEHICLE ;
this - > SetDirty ( ) ;
2009-10-20 21:41:44 +00:00
NWidgetBase * nwi = this - > GetWidget < NWidgetBase > ( DEPOT_WIDGET_MATRIX ) ;
2008-05-13 13:39:50 +00:00
if ( this - > type = = VEH_TRAIN ) {
2008-05-14 18:35:15 +00:00
GetDepotVehiclePtData gdvp = { NULL , NULL } ;
2008-05-13 13:39:50 +00:00
2009-10-20 21:41:44 +00:00
if ( this - > GetVehicleFromDepotWndPt ( pt . x - nwi - > pos_x , pt . y - nwi - > pos_y , & v , & gdvp ) = = MODE_DRAG_VEHICLE & & sel ! = INVALID_VEHICLE ) {
2008-05-13 13:39:50 +00:00
if ( gdvp . wagon ! = NULL & & gdvp . wagon - > index = = sel & & _ctrl_pressed ) {
2009-09-26 18:47:41 +00:00
DoCommandP ( Vehicle : : Get ( sel ) - > tile , Vehicle : : Get ( sel ) - > index , true ,
2009-10-20 21:41:44 +00:00
CMD_REVERSE_TRAIN_DIRECTION | CMD_MSG ( STR_ERROR_CAN_T_REVERSE_DIRECTION_RAIL_VEHICLE ) ) ;
2008-05-13 13:39:50 +00:00
} else if ( gdvp . wagon = = NULL | | gdvp . wagon - > index ! = sel ) {
TrainDepotMoveVehicle ( gdvp . wagon , sel , gdvp . head ) ;
2009-07-01 22:22:01 +00:00
} else if ( gdvp . head ! = NULL & & Train : : From ( gdvp . head ) - > IsFrontEngine ( ) ) {
2008-05-13 13:39:50 +00:00
ShowVehicleViewWindow ( gdvp . head ) ;
2006-09-26 16:47:51 +00:00
}
2008-05-13 13:39:50 +00:00
}
2009-10-20 21:41:44 +00:00
} else if ( this - > GetVehicleFromDepotWndPt ( pt . x - nwi - > pos_x , pt . y - nwi - > pos_y , & v , NULL ) = = MODE_DRAG_VEHICLE & & v ! = NULL & & sel = = v - > index ) {
2008-05-13 13:39:50 +00:00
ShowVehicleViewWindow ( v ) ;
}
} break ;
2009-09-26 19:26:08 +00:00
case DEPOT_WIDGET_SELL : case DEPOT_WIDGET_SELL_CHAIN : {
if ( this - > IsWidgetDisabled ( widget ) ) return ;
if ( this - > sel = = INVALID_VEHICLE ) return ;
2008-05-13 13:39:50 +00:00
2009-09-26 19:26:08 +00:00
this - > HandleButtonClick ( widget ) ;
2006-09-26 16:47:51 +00:00
2009-09-26 19:26:08 +00:00
const Vehicle * v = Vehicle : : Get ( this - > sel ) ;
this - > sel = INVALID_VEHICLE ;
this - > SetDirty ( ) ;
2008-05-13 13:39:50 +00:00
2009-09-26 19:26:08 +00:00
int sell_cmd = ( v - > type = = VEH_TRAIN & & ( widget = = DEPOT_WIDGET_SELL_CHAIN | | _ctrl_pressed ) ) ? 1 : 0 ;
2008-05-13 13:39:50 +00:00
2009-09-26 19:26:08 +00:00
bool is_engine = ( v - > type ! = VEH_TRAIN | | Train : : From ( v ) - > IsFrontEngine ( ) ) ;
2008-05-13 13:39:50 +00:00
2009-09-26 19:26:08 +00:00
if ( is_engine ) {
_backup_orders_tile = v - > tile ;
BackupVehicleOrders ( v ) ;
}
2008-05-13 13:39:50 +00:00
2009-09-26 19:26:08 +00:00
if ( ! DoCommandP ( v - > tile , v - > index , sell_cmd , GetCmdSellVeh ( v - > type ) ) & & is_engine ) _backup_orders_tile = 0 ;
} break ;
2006-09-26 16:47:51 +00:00
2008-05-13 13:39:50 +00:00
default :
this - > sel = INVALID_VEHICLE ;
this - > SetDirty ( ) ;
}
_cursor . vehchain = false ;
}
2009-08-15 20:59:49 +00:00
virtual void OnTimeout ( )
{
if ( ! this - > IsWidgetDisabled ( DEPOT_WIDGET_SELL ) ) {
this - > RaiseWidget ( DEPOT_WIDGET_SELL ) ;
2009-09-13 19:15:59 +00:00
this - > SetWidgetDirty ( DEPOT_WIDGET_SELL ) ;
2009-08-15 20:59:49 +00:00
}
2009-09-26 19:21:20 +00:00
if ( this - > nested_array [ DEPOT_WIDGET_SELL ] ! = NULL & & ! this - > IsWidgetDisabled ( DEPOT_WIDGET_SELL_CHAIN ) ) {
2009-08-15 20:59:49 +00:00
this - > RaiseWidget ( DEPOT_WIDGET_SELL_CHAIN ) ;
2009-09-13 19:15:59 +00:00
this - > SetWidgetDirty ( DEPOT_WIDGET_SELL_CHAIN ) ;
2009-08-15 20:59:49 +00:00
}
}
2009-10-24 14:53:55 +00:00
virtual void OnResize ( )
2008-05-13 13:39:50 +00:00
{
2009-11-22 13:22:53 +00:00
NWidgetCore * nwi = this - > GetWidget < NWidgetCore > ( DEPOT_WIDGET_MATRIX ) ;
2009-12-20 20:08:39 +00:00
this - > vscroll . SetCapacityFromWidget ( this , DEPOT_WIDGET_MATRIX ) ;
2009-11-17 16:03:51 +00:00
if ( this - > type = = VEH_TRAIN ) {
2009-11-22 13:22:53 +00:00
this - > hscroll . SetCapacity ( nwi - > current_x - this - > header_width - this - > count_width ) ;
nwi - > widget_data = ( this - > vscroll . GetCapacity ( ) < < MAT_ROW_START ) + ( 1 < < MAT_COL_START ) ;
2009-11-17 16:03:51 +00:00
} else {
2009-12-20 20:08:39 +00:00
this - > hscroll . SetCapacityFromWidget ( this , DEPOT_WIDGET_MATRIX ) ;
2009-11-22 13:22:53 +00:00
nwi - > widget_data = ( this - > vscroll . GetCapacity ( ) < < MAT_ROW_START ) + ( this - > hscroll . GetCapacity ( ) < < MAT_COL_START ) ;
2009-11-17 16:03:51 +00:00
}
2008-05-13 13:39:50 +00:00
}
2008-05-17 23:11:06 +00:00
virtual EventState OnCTRLStateChange ( )
2008-05-13 13:39:50 +00:00
{
if ( this - > sel ! = INVALID_VEHICLE ) {
_cursor . vehchain = _ctrl_pressed ;
2009-09-13 19:15:59 +00:00
this - > SetWidgetDirty ( DEPOT_WIDGET_MATRIX ) ;
2008-08-16 18:01:23 +00:00
return ES_HANDLED ;
2008-05-13 13:39:50 +00:00
}
2008-08-16 18:01:23 +00:00
return ES_NOT_HANDLED ;
2008-05-13 13:39:50 +00:00
}
} ;
static void DepotSellAllConfirmationCallback ( Window * win , bool confirmed )
{
if ( confirmed ) {
DepotWindow * w = ( DepotWindow * ) win ;
TileIndex tile = w - > window_number ;
byte vehtype = w - > type ;
2008-12-28 14:37:19 +00:00
DoCommandP ( tile , vehtype , 0 , CMD_DEPOT_SELL_ALL_VEHICLES ) ;
2006-09-26 16:47:51 +00:00
}
}
/** Opens a depot window
* @ param tile The tile where the depot / hangar is located
* @ param type The type of vehicles in the depot
*/
2007-05-18 17:31:41 +00:00
void ShowDepotWindow ( TileIndex tile , VehicleType type )
2006-09-26 16:47:51 +00:00
{
2008-12-28 20:53:19 +00:00
if ( BringWindowToFrontById ( WC_VEHICLE_DEPOT , tile ) ! = NULL ) return ;
2006-09-26 16:47:51 +00:00
2008-12-28 20:53:19 +00:00
const WindowDesc * desc ;
2006-09-26 16:47:51 +00:00
switch ( type ) {
2006-12-07 00:51:20 +00:00
default : NOT_REACHED ( ) ;
2008-12-28 20:53:19 +00:00
case VEH_TRAIN : desc = & _train_depot_desc ; break ;
case VEH_ROAD : desc = & _road_depot_desc ; break ;
case VEH_SHIP : desc = & _ship_depot_desc ; break ;
case VEH_AIRCRAFT : desc = & _aircraft_depot_desc ; break ;
2006-09-26 16:47:51 +00:00
}
2008-12-28 20:53:19 +00:00
new DepotWindow ( desc , tile , type ) ;
2006-09-26 16:47:51 +00:00
}
2006-12-05 22:40:42 +00:00
/** Removes the highlight of a vehicle in a depot window
* @ param * v Vehicle to remove all highlights from
*/
void DeleteDepotHighlightOfVehicle ( const Vehicle * v )
{
2008-05-13 13:39:50 +00:00
DepotWindow * w ;
2006-12-05 22:40:42 +00:00
2006-12-06 00:03:24 +00:00
/* If we haven't got any vehicles on the mouse pointer, we haven't got any highlighted in any depots either
2008-05-13 13:39:50 +00:00
* If that is the case , we can skip looping though the windows and save time
*/
2006-12-06 00:03:24 +00:00
if ( _special_mouse_mode ! = WSM_DRAGDROP ) return ;
2008-05-13 13:39:50 +00:00
w = dynamic_cast < DepotWindow * > ( FindWindowById ( WC_VEHICLE_DEPOT , v - > tile ) ) ;
2006-12-06 17:31:16 +00:00
if ( w ! = NULL ) {
2009-01-08 21:13:20 +00:00
if ( w - > sel = = v - > index ) ResetObjectToPlace ( ) ;
2006-12-05 22:40:42 +00:00
}
}