src/station_gui.cpp
branchNewGRF_ports
changeset 10242 52b4a9006029
parent 10184 fcf5fb2548eb
child 10274 b3c58f3df92b
equal deleted inserted replaced
10211:c1391c8ed5c6 10242:52b4a9006029
    92 	STR_SORT_BY_RATING_MAX,
    92 	STR_SORT_BY_RATING_MAX,
    93 	INVALID_STRING_ID
    93 	INVALID_STRING_ID
    94 };
    94 };
    95 
    95 
    96 static char _bufcache[64];
    96 static char _bufcache[64];
    97 static const Station* _last_station;
    97 static const Station *_last_station;
    98 static int _internal_sort_order;
    98 static int _internal_sort_order;
    99 
    99 
   100 static int CDECL StationNameSorter(const void *a, const void *b)
   100 static int CDECL StationNameSorter(const void *a, const void *b)
   101 {
   101 {
   102 	const Station* st1 = *(const Station**)a;
   102 	const Station *st1 = *(const Station**)a;
   103 	const Station* st2 = *(const Station**)b;
   103 	const Station *st2 = *(const Station**)b;
   104 	char buf1[64];
   104 	char buf1[64];
   105 	int r;
       
   106 
   105 
   107 	SetDParam(0, st1->index);
   106 	SetDParam(0, st1->index);
   108 	GetString(buf1, STR_STATION, lastof(buf1));
   107 	GetString(buf1, STR_STATION, lastof(buf1));
   109 
   108 
   110 	if (st2 != _last_station) {
   109 	if (st2 != _last_station) {
   111 		_last_station = st2;
   110 		_last_station = st2;
   112 		SetDParam(0, st2->index);
   111 		SetDParam(0, st2->index);
   113 		GetString(_bufcache, STR_STATION, lastof(_bufcache));
   112 		GetString(_bufcache, STR_STATION, lastof(_bufcache));
   114 	}
   113 	}
   115 
   114 
   116 	r = strcmp(buf1, _bufcache); // sort by name
   115 	int r = strcmp(buf1, _bufcache); // sort by name
   117 	return (_internal_sort_order & 1) ? -r : r;
   116 	return (_internal_sort_order & 1) ? -r : r;
   118 }
   117 }
   119 
   118 
   120 static int CDECL StationTypeSorter(const void *a, const void *b)
   119 static int CDECL StationTypeSorter(const void *a, const void *b)
   121 {
   120 {
   122 	const Station* st1 = *(const Station**)a;
   121 	const Station *st1 = *(const Station**)a;
   123 	const Station* st2 = *(const Station**)b;
   122 	const Station *st2 = *(const Station**)b;
   124 	return (_internal_sort_order & 1) ? st2->facilities - st1->facilities : st1->facilities - st2->facilities;
   123 	return (_internal_sort_order & 1) ? st2->facilities - st1->facilities : st1->facilities - st2->facilities;
   125 }
   124 }
   126 
   125 
   127 static const uint32 _cargo_filter_max = ~0;
   126 static const uint32 _cargo_filter_max = UINT32_MAX;
   128 static uint32 _cargo_filter = _cargo_filter_max;
   127 static uint32 _cargo_filter = _cargo_filter_max;
   129 
   128 
   130 static int CDECL StationWaitingSorter(const void *a, const void *b)
   129 static int CDECL StationWaitingSorter(const void *a, const void *b)
   131 {
   130 {
   132 	const Station* st1 = *(const Station**)a;
   131 	const Station *st1 = *(const Station**)a;
   133 	const Station* st2 = *(const Station**)b;
   132 	const Station *st2 = *(const Station**)b;
   134 	Money sum1 = 0, sum2 = 0;
   133 	Money sum1 = 0, sum2 = 0;
   135 
   134 
   136 	for (CargoID j = 0; j < NUM_CARGO; j++) {
   135 	for (CargoID j = 0; j < NUM_CARGO; j++) {
   137 		if (!HasBit(_cargo_filter, j)) continue;
   136 		if (!HasBit(_cargo_filter, j)) continue;
   138 		if (!st1->goods[j].cargo.Empty()) sum1 += GetTransportedGoodsIncome(st1->goods[j].cargo.Count(), 20, 50, j);
   137 		if (!st1->goods[j].cargo.Empty()) sum1 += GetTransportedGoodsIncome(st1->goods[j].cargo.Count(), 20, 50, j);
   150  * @retval >0 a should come before b in the list
   149  * @retval >0 a should come before b in the list
   151  * @retval <0 b should come before a in the list
   150  * @retval <0 b should come before a in the list
   152  */
   151  */
   153 static int CDECL StationRatingMaxSorter(const void *a, const void *b)
   152 static int CDECL StationRatingMaxSorter(const void *a, const void *b)
   154 {
   153 {
   155 	const Station* st1 = *(const Station**)a;
   154 	const Station *st1 = *(const Station**)a;
   156 	const Station* st2 = *(const Station**)b;
   155 	const Station *st2 = *(const Station**)b;
   157 	byte maxr1 = 0;
   156 	byte maxr1 = 0;
   158 	byte maxr2 = 0;
   157 	byte maxr2 = 0;
   159 
   158 
   160 	for (CargoID j = 0; j < NUM_CARGO; j++) {
   159 	for (CargoID j = 0; j < NUM_CARGO; j++) {
   161 		if (HasBit(st1->goods[j].acceptance_pickup, GoodsEntry::PICKUP)) maxr1 = max(maxr1, st1->goods[j].rating);
   160 		if (HasBit(st1->goods[j].acceptance_pickup, GoodsEntry::PICKUP)) maxr1 = max(maxr1, st1->goods[j].rating);
   174 
   173 
   175 DECLARE_ENUM_AS_BIT_SET(StationListFlags);
   174 DECLARE_ENUM_AS_BIT_SET(StationListFlags);
   176 
   175 
   177 /** Information about station list */
   176 /** Information about station list */
   178 struct plstations_d {
   177 struct plstations_d {
   179 	const Station** sort_list; ///< Pointer to list of stations
   178 	const Station **sort_list; ///< Pointer to list of stations
   180 	uint16 list_length;        ///< Number of stations in list
   179 	uint16 list_length;        ///< Number of stations in list
   181 	uint16 resort_timer;       ///< Tick counter to resort the list
   180 	uint16 resort_timer;       ///< Tick counter to resort the list
   182 	byte sort_type;            ///< Sort type - name, waiting, ...
   181 	byte sort_type;            ///< Sort type - name, waiting, ...
   183 	byte flags;                ///< Flags - SL_ORDER, SL_RESORT, SL_REBUILD
   182 	byte flags;                ///< Flags - SL_ORDER, SL_RESORT, SL_REBUILD
   184 };
   183 };
   187 /**
   186 /**
   188  * Set the 'SL_REBUILD' flag for all station lists
   187  * Set the 'SL_REBUILD' flag for all station lists
   189  */
   188  */
   190 void RebuildStationLists()
   189 void RebuildStationLists()
   191 {
   190 {
   192 	Window* const *wz;
   191 	Window *const *wz;
   193 
   192 
   194 	FOR_ALL_WINDOWS(wz) {
   193 	FOR_ALL_WINDOWS(wz) {
   195 		Window *w = *wz;
   194 		Window *w = *wz;
   196 		if (w->window_class == WC_STATION_LIST) {
   195 		if (w->window_class == WC_STATION_LIST) {
   197 			WP(w, plstations_d).flags |= SL_REBUILD;
   196 			WP(w, plstations_d).flags |= SL_REBUILD;
   203 /**
   202 /**
   204  * Set the 'SL_RESORT' flag for all station lists
   203  * Set the 'SL_RESORT' flag for all station lists
   205  */
   204  */
   206 void ResortStationLists()
   205 void ResortStationLists()
   207 {
   206 {
   208 	Window* const *wz;
   207 	Window *const *wz;
   209 
   208 
   210 	FOR_ALL_WINDOWS(wz) {
   209 	FOR_ALL_WINDOWS(wz) {
   211 		Window *w = *wz;
   210 		Window *w = *wz;
   212 		if (w->window_class == WC_STATION_LIST) {
   211 		if (w->window_class == WC_STATION_LIST) {
   213 			WP(w, plstations_d).flags |= SL_RESORT;
   212 			WP(w, plstations_d).flags |= SL_RESORT;
   223  * @param owner player whose stations are to be in list
   222  * @param owner player whose stations are to be in list
   224  * @param facilities types of stations of interest
   223  * @param facilities types of stations of interest
   225  * @param cargo_filter bitmap of cargo types to include
   224  * @param cargo_filter bitmap of cargo types to include
   226  * @param include_empty whether we should include stations without waiting cargo
   225  * @param include_empty whether we should include stations without waiting cargo
   227  */
   226  */
   228 static void BuildStationsList(plstations_d* sl, PlayerID owner, byte facilities, uint32 cargo_filter, bool include_empty)
   227 static void BuildStationsList(plstations_d *sl, PlayerID owner, byte facilities, uint32 cargo_filter, bool include_empty)
   229 {
   228 {
   230 	uint n = 0;
   229 	uint n = 0;
   231 	const Station *st;
   230 	const Station *st;
   232 
   231 
   233 	if (!(sl->flags & SL_REBUILD)) return;
   232 	if (!(sl->flags & SL_REBUILD)) return;
   234 
   233 
   235 	/* Create array for sorting */
   234 	/* Create array for sorting */
   236 	const Station** station_sort = MallocT<const Station*>(GetMaxStationIndex() + 1);
   235 	const Station **station_sort = MallocT<const Station*>(GetMaxStationIndex() + 1);
   237 
   236 
   238 	DEBUG(misc, 3, "Building station list for player %d", owner);
   237 	DEBUG(misc, 3, "Building station list for player %d", owner);
   239 
   238 
   240 	FOR_ALL_STATIONS(st) {
   239 	FOR_ALL_STATIONS(st) {
   241 		if (st->owner == owner || (st->owner == OWNER_NONE && !st->IsBuoy() && HasStationInUse(st->index, owner))) {
   240 		if (st->owner == owner || (st->owner == OWNER_NONE && !st->IsBuoy() && HasStationInUse(st->index, owner))) {
   275  *
   274  *
   276  * @param sl pointer to plstations_d (station list and flags)
   275  * @param sl pointer to plstations_d (station list and flags)
   277  */
   276  */
   278 static void SortStationsList(plstations_d *sl)
   277 static void SortStationsList(plstations_d *sl)
   279 {
   278 {
   280 	static StationSortListingTypeFunction* const _station_sorter[] = {
   279 	static StationSortListingTypeFunction *const _station_sorter[] = {
   281 		&StationNameSorter,
   280 		&StationNameSorter,
   282 		&StationTypeSorter,
   281 		&StationTypeSorter,
   283 		&StationWaitingSorter,
   282 		&StationWaitingSorter,
   284 		&StationRatingMaxSorter
   283 		&StationRatingMaxSorter
   285 	};
   284 	};
   747  * @param w pointer to window
   746  * @param w pointer to window
   748  */
   747  */
   749 static void DrawStationViewWindow(Window *w)
   748 static void DrawStationViewWindow(Window *w)
   750 {
   749 {
   751 	StationID station_id = w->window_number;
   750 	StationID station_id = w->window_number;
   752 	const Station* st = GetStation(station_id);
   751 	const Station *st = GetStation(station_id);
   753 	int x, y;     ///< coordinates used for printing waiting/accepted/rating of cargo
       
   754 	int pos;      ///< = w->vscroll.pos
       
   755 	StringID str;
       
   756 	CargoDataList cargolist;
   752 	CargoDataList cargolist;
   757 	uint32 transfers = 0;
   753 	uint32 transfers = 0;
   758 
   754 
   759 	/* count types of cargos waiting in station */
   755 	/* count types of cargos waiting in station */
   760 	for (CargoID i = 0; i < NUM_CARGO; i++) {
   756 	for (CargoID i = 0; i < NUM_CARGO; i++) {
   806 
   802 
   807 	SetDParam(0, st->index);
   803 	SetDParam(0, st->index);
   808 	SetDParam(1, st->facilities);
   804 	SetDParam(1, st->facilities);
   809 	DrawWindowWidgets(w);
   805 	DrawWindowWidgets(w);
   810 
   806 
   811 	x = 2;
   807 	int x = 2;  ///< coordinates used for printing waiting/accepted/rating of cargo
   812 	y = 15;
   808 	int y = 15;
   813 	pos = w->vscroll.pos;
   809 	int pos = w->vscroll.pos; ///< = w->vscroll.pos
   814 
   810 
   815 	uint width = w->widget[SVW_WAITING].right - w->widget[SVW_WAITING].left - 4;
   811 	uint width = w->widget[SVW_WAITING].right - w->widget[SVW_WAITING].left - 4;
   816 	int maxrows = w->vscroll.cap;
   812 	int maxrows = w->vscroll.cap;
       
   813 
       
   814 	StringID str;
   817 
   815 
   818 	if (--pos < 0) {
   816 	if (--pos < 0) {
   819 		str = STR_00D0_NOTHING;
   817 		str = STR_00D0_NOTHING;
   820 		for (CargoID i = 0; i < NUM_CARGO; i++) {
   818 		for (CargoID i = 0; i < NUM_CARGO; i++) {
   821 			if (!st->goods[i].cargo.Empty()) str = STR_EMPTY;
   819 			if (!st->goods[i].cargo.Empty()) str = STR_EMPTY;