Change house GUI picker logic to be more like object GUI window.

Deselect house on object placement abort.
Set object placement on init or house selection.
Adjust display to still work even if no house selected,
by continuing to show the previous selection.
This commit is contained in:
Jonathan G Rennison
2015-09-21 22:16:47 +01:00
parent 0007e6fda2
commit 7bd91f172b
3 changed files with 146 additions and 100 deletions

View File

@@ -614,7 +614,7 @@ struct ScenarioEditorLandscapeGenerationWindow : Window {
break; break;
case WID_ETT_PLACE_HOUSE: // Place house button case WID_ETT_PLACE_HOUSE: // Place house button
ShowBuildHousePicker(this); ShowBuildHousePicker();
break; break;
case WID_ETT_INCREASE_SIZE: case WID_ETT_INCREASE_SIZE:
@@ -682,10 +682,6 @@ struct ScenarioEditorLandscapeGenerationWindow : Window {
VpStartPlaceSizing(tile, VPM_X_AND_Y, DDSP_CREATE_DESERT); VpStartPlaceSizing(tile, VPM_X_AND_Y, DDSP_CREATE_DESERT);
break; break;
case WID_ETT_PLACE_HOUSE: // Place house button
PlaceProc_House(tile);
break;
default: NOT_REACHED(); default: NOT_REACHED();
} }
} }

View File

@@ -45,6 +45,8 @@
typedef GUIList<const Town*> GUITownList; typedef GUIList<const Town*> GUITownList;
static void PlaceProc_House(TileIndex tile);
static const NWidgetPart _nested_town_authority_widgets[] = { static const NWidgetPart _nested_town_authority_widgets[] = {
NWidget(NWID_HORIZONTAL), NWidget(NWID_HORIZONTAL),
NWidget(WWT_CLOSEBOX, COLOUR_BROWN), NWidget(WWT_CLOSEBOX, COLOUR_BROWN),
@@ -1331,12 +1333,13 @@ public:
static HouseID _cur_house = INVALID_HOUSE_ID; ///< house selected in the house picker window static HouseID _cur_house = INVALID_HOUSE_ID; ///< house selected in the house picker window
/** The window used for building houses. */ /** The window used for building houses. */
class HousePickerWindow : public PickerWindowBase { class HousePickerWindow : public Window {
protected: protected:
GUIHouseList house_list; ///< list of houses and house sets GUIHouseList house_list; ///< list of houses and house sets
uint house_offset; ///< index of selected house int house_offset; ///< index of selected house
uint house_set; ///< index of selected house set uint house_set; ///< index of selected house set
uint line_height; ///< height of a single line in the list of house sets uint line_height; ///< height of a single line in the list of house sets
HouseID display_house; ///< house ID of currently displayed house
void RestoreSelectedHouseIndex() void RestoreSelectedHouseIndex()
{ {
@@ -1345,6 +1348,7 @@ protected:
if (this->house_list.Length() == 0) { // no houses at all? if (this->house_list.Length() == 0) { // no houses at all?
_cur_house = INVALID_HOUSE_ID; _cur_house = INVALID_HOUSE_ID;
this->display_house = _cur_house;
return; return;
} }
@@ -1360,6 +1364,16 @@ protected:
} }
} }
_cur_house = this->house_list.GetHouseAtOffset(this->house_set, this->house_offset); _cur_house = this->house_list.GetHouseAtOffset(this->house_set, this->house_offset);
this->display_house = _cur_house;
}
void SelectHouseIntl(uint new_house_set, int new_house_offset)
{
SetObjectToPlaceWnd(SPR_CURSOR_TOWN, PAL_NONE, HT_RECT, this);
this->house_set = new_house_set;
this->house_offset = new_house_offset;
_cur_house = this->house_list.GetHouseAtOffset(new_house_set, new_house_offset);
this->display_house = _cur_house;
} }
/** /**
@@ -1367,14 +1381,13 @@ protected:
* @param new_house_set index of the house set * @param new_house_set index of the house set
* @param new_house_offset offset of the house * @param new_house_offset offset of the house
*/ */
void SelectOtherHouse(uint new_house_set, uint new_house_offset) void SelectOtherHouse(uint new_house_set, int new_house_offset)
{ {
assert(new_house_set < this->house_list.NumHouseSets()); assert(new_house_set < this->house_list.NumHouseSets());
assert(new_house_offset < this->house_list.NumHousesInHouseSet(new_house_set)); assert(new_house_offset < (int) this->house_list.NumHousesInHouseSet(new_house_set));
assert(new_house_offset >= 0);
_cur_house = this->house_list.GetHouseAtOffset(new_house_set, new_house_offset); SelectHouseIntl(new_house_set, new_house_offset);
this->house_set = new_house_set;
this->house_offset = new_house_offset;
NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX); NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX);
matrix->SetCount(this->house_list.NumHousesInHouseSet(this->house_set)); matrix->SetCount(this->house_list.NumHousesInHouseSet(this->house_set));
@@ -1395,24 +1408,19 @@ protected:
} }
public: public:
HousePickerWindow(WindowDesc *desc, Window *w) : PickerWindowBase(desc, w) HousePickerWindow(WindowDesc *desc, WindowNumber number) : Window(desc)
{ {
this->CreateNestedTree(); this->CreateNestedTree();
/* there is no shade box but we will shade the window if there is no house to show */ /* there is no shade box but we will shade the window if there is no house to show */
this->shade_select = this->GetWidget<NWidgetStacked>(WID_HP_MAIN_PANEL_SEL); this->shade_select = this->GetWidget<NWidgetStacked>(WID_HP_MAIN_PANEL_SEL);
NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX); NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX);
matrix->SetScrollbar(this->GetScrollbar(WID_HP_HOUSE_SELECT_SCROLL)); matrix->SetScrollbar(this->GetScrollbar(WID_HP_HOUSE_SELECT_SCROLL));
this->FinishInitNested(0); this->FinishInitNested(number);
if (_cur_house != INVALID_HOUSE_ID) matrix->SetClicked(this->house_offset); // set clicked item again to make it visible if (_cur_house != INVALID_HOUSE_ID) matrix->SetClicked(this->house_offset); // set clicked item again to make it visible
} }
~HousePickerWindow() virtual void OnInit() override
{
DeleteWindowById(WC_SELECT_TOWN, 0);
}
virtual void OnInit()
{ {
this->house_list.Build(); this->house_list.Build();
this->RestoreSelectedHouseIndex(); this->RestoreSelectedHouseIndex();
@@ -1437,30 +1445,63 @@ public:
NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX); NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX);
matrix->SetCount(this->house_list.NumHousesInHouseSet(this->house_set)); matrix->SetCount(this->house_list.NumHousesInHouseSet(this->house_set));
matrix->SetClicked(this->house_offset); matrix->SetClicked(this->house_offset);
SelectHouseIntl(this->house_set, this->house_offset);
} else {
ResetObjectToPlace();
} }
} }
virtual void SetStringParameters(int widget) const virtual void SetStringParameters(int widget) const
{ {
if (widget == WID_HP_CAPTION) {
if (this->house_list.NumHouseSets() == 1) SetDParamStr(0, this->house_list.GetNameOfHouseSet(0));
} else if (this->display_house == INVALID_HOUSE_ID) {
switch (widget) { switch (widget) {
case WID_HP_CAPTION: case WID_HP_CAPTION:
if (this->house_list.NumHouseSets() == 1) SetDParamStr(0, this->house_list.GetNameOfHouseSet(0));
break; break;
case WID_HP_HOUSE_ZONES:
for (int i = 0; i < HZB_END; i++) {
SetDParam(2 * i, STR_HOUSE_BUILD_HOUSE_ZONE_DISABLED);
SetDParam(2 * i + 1, i + 1);
}
break;
case WID_HP_HOUSE_YEARS:
SetDParam(0, STR_HOUSE_BUILD_YEARS_BAD_YEAR);
SetDParam(1, 0);
SetDParam(2, STR_HOUSE_BUILD_YEARS_BAD_YEAR);
SetDParam(3, 0);
break;
case WID_HP_HOUSE_ACCEPTANCE:
SetDParamStr(0, "");
break;
case WID_HP_HOUSE_SUPPLY:
SetDParam(0, 0);
break;
default:
SetDParam(0, STR_EMPTY);
break;
}
} else {
switch (widget) {
case WID_HP_HOUSE_NAME: case WID_HP_HOUSE_NAME:
SetDParam(0, GetHouseName(_cur_house)); SetDParam(0, GetHouseName(this->display_house));
break; break;
case WID_HP_HISTORICAL_BUILDING: case WID_HP_HISTORICAL_BUILDING:
SetDParam(0, HouseSpec::Get(_cur_house)->extra_flags & BUILDING_IS_HISTORICAL ? STR_HOUSE_BUILD_HISTORICAL_BUILDING : STR_EMPTY); SetDParam(0, HouseSpec::Get(this->display_house)->extra_flags & BUILDING_IS_HISTORICAL ? STR_HOUSE_BUILD_HISTORICAL_BUILDING : STR_EMPTY);
break; break;
case WID_HP_HOUSE_POPULATION: case WID_HP_HOUSE_POPULATION:
SetDParam(0, HouseSpec::Get(_cur_house)->population); SetDParam(0, HouseSpec::Get(this->display_house)->population);
break; break;
case WID_HP_HOUSE_ZONES: { case WID_HP_HOUSE_ZONES: {
HouseZones zones = (HouseZones)(HouseSpec::Get(_cur_house)->building_availability & HZ_ZONALL); HouseZones zones = (HouseZones)(HouseSpec::Get(this->display_house)->building_availability & HZ_ZONALL);
for (int i = 0; i < HZB_END; i++) { for (int i = 0; i < HZB_END; i++) {
/* colour: gold(enabled)/grey(disabled) */ /* colour: gold(enabled)/grey(disabled) */
SetDParam(2 * i, HasBit(zones, HZB_END - i - 1) ? STR_HOUSE_BUILD_HOUSE_ZONE_ENABLED : STR_HOUSE_BUILD_HOUSE_ZONE_DISABLED); SetDParam(2 * i, HasBit(zones, HZB_END - i - 1) ? STR_HOUSE_BUILD_HOUSE_ZONE_ENABLED : STR_HOUSE_BUILD_HOUSE_ZONE_DISABLED);
@@ -1472,7 +1513,7 @@ public:
case WID_HP_HOUSE_LANDSCAPE: { case WID_HP_HOUSE_LANDSCAPE: {
StringID info = STR_HOUSE_BUILD_LANDSCAPE_ABOVE_OR_BELOW_SNOWLINE; StringID info = STR_HOUSE_BUILD_LANDSCAPE_ABOVE_OR_BELOW_SNOWLINE;
switch (HouseSpec::Get(_cur_house)->building_availability & (HZ_SUBARTC_ABOVE | HZ_SUBARTC_BELOW)) { switch (HouseSpec::Get(this->display_house)->building_availability & (HZ_SUBARTC_ABOVE | HZ_SUBARTC_BELOW)) {
case HZ_SUBARTC_ABOVE: info = STR_HOUSE_BUILD_LANDSCAPE_ONLY_ABOVE_SNOWLINE; break; case HZ_SUBARTC_ABOVE: info = STR_HOUSE_BUILD_LANDSCAPE_ONLY_ABOVE_SNOWLINE; break;
case HZ_SUBARTC_BELOW: info = STR_HOUSE_BUILD_LANDSCAPE_ONLY_BELOW_SNOWLINE; break; case HZ_SUBARTC_BELOW: info = STR_HOUSE_BUILD_LANDSCAPE_ONLY_BELOW_SNOWLINE; break;
default: break; default: break;
@@ -1482,7 +1523,7 @@ public:
} }
case WID_HP_HOUSE_YEARS: { case WID_HP_HOUSE_YEARS: {
const HouseSpec *hs = HouseSpec::Get(_cur_house); const HouseSpec *hs = HouseSpec::Get(this->display_house);
SetDParam(0, hs->min_year <= _cur_year ? STR_HOUSE_BUILD_YEARS_GOOD_YEAR : STR_HOUSE_BUILD_YEARS_BAD_YEAR); SetDParam(0, hs->min_year <= _cur_year ? STR_HOUSE_BUILD_YEARS_GOOD_YEAR : STR_HOUSE_BUILD_YEARS_BAD_YEAR);
SetDParam(1, hs->min_year); SetDParam(1, hs->min_year);
SetDParam(2, hs->max_year >= _cur_year ? STR_HOUSE_BUILD_YEARS_GOOD_YEAR : STR_HOUSE_BUILD_YEARS_BAD_YEAR); SetDParam(2, hs->max_year >= _cur_year ? STR_HOUSE_BUILD_YEARS_GOOD_YEAR : STR_HOUSE_BUILD_YEARS_BAD_YEAR);
@@ -1495,7 +1536,7 @@ public:
char *str = buff; char *str = buff;
CargoArray cargo; CargoArray cargo;
uint32 dummy = 0; uint32 dummy = 0;
AddAcceptedHouseCargo(_cur_house, INVALID_TILE, cargo, &dummy); AddAcceptedHouseCargo(this->display_house, INVALID_TILE, cargo, &dummy);
for (uint i = 0; i < NUM_CARGO; i++) { for (uint i = 0; i < NUM_CARGO; i++) {
if (cargo[i] == 0) continue; if (cargo[i] == 0) continue;
/* If the accepted value is less than 8, show it in 1/8:ths */ /* If the accepted value is less than 8, show it in 1/8:ths */
@@ -1511,7 +1552,7 @@ public:
case WID_HP_HOUSE_SUPPLY: { case WID_HP_HOUSE_SUPPLY: {
CargoArray cargo; CargoArray cargo;
AddProducedHouseCargo(_cur_house, INVALID_TILE, cargo); AddProducedHouseCargo(this->display_house, INVALID_TILE, cargo);
uint32 cargo_mask = 0; uint32 cargo_mask = 0;
for (uint i = 0; i < NUM_CARGO; i++) if (cargo[i] != 0) SetBit(cargo_mask, i); for (uint i = 0; i < NUM_CARGO; i++) if (cargo[i] != 0) SetBit(cargo_mask, i);
SetDParam(0, cargo_mask); SetDParam(0, cargo_mask);
@@ -1521,6 +1562,7 @@ public:
default: break; default: break;
} }
} }
}
virtual void UpdateWidgetSize(int widget, Dimension *size, const Dimension &padding, Dimension *fill, Dimension *resize) virtual void UpdateWidgetSize(int widget, Dimension *size, const Dimension &padding, Dimension *fill, Dimension *resize)
{ {
@@ -1612,7 +1654,9 @@ public:
} }
case WID_HP_HOUSE_PREVIEW: case WID_HP_HOUSE_PREVIEW:
DrawHouseImage(_cur_house, r.left, r.top, r.right, r.bottom); if (this->display_house != INVALID_HOUSE_ID) {
DrawHouseImage(this->display_house, r.left, r.top, r.right, r.bottom);
}
break; break;
case WID_HP_HOUSE_SELECT: { case WID_HP_HOUSE_SELECT: {
@@ -1645,6 +1689,21 @@ public:
break; break;
} }
} }
virtual void OnPlaceObject(Point pt, TileIndex tile) override
{
PlaceProc_House(tile);
}
virtual void OnPlaceObjectAbort() override
{
this->house_offset = -1;
_cur_house = INVALID_HOUSE_ID;
NWidgetMatrix *matrix = this->GetWidget<NWidgetMatrix>(WID_HP_HOUSE_SELECT_MATRIX);
matrix->SetClicked(-1);
this->UpdateSelectSize();
this->SetDirty();
}
}; };
static const NWidgetPart _nested_house_picker_widgets[] = { static const NWidgetPart _nested_house_picker_widgets[] = {
@@ -1715,12 +1774,9 @@ static WindowDesc _house_picker_desc(
* Show our house picker. * Show our house picker.
* @param parent The toolbar window we're associated with. * @param parent The toolbar window we're associated with.
*/ */
void ShowBuildHousePicker(Window *parent) void ShowBuildHousePicker()
{ {
if (BringWindowToFrontById(WC_BUILD_HOUSE, 0) != NULL) { AllocateWindowDescFront<HousePickerWindow>(&_house_picker_desc, 0);
return;
}
new HousePickerWindow(&_house_picker_desc, parent);
} }
@@ -1820,8 +1876,7 @@ static void ShowSelectTownWindow(const TownList &towns, const CommandContainer &
new SelectTownWindow(&_select_town_desc, towns, cmd); new SelectTownWindow(&_select_town_desc, towns, cmd);
} }
static void PlaceProc_House(TileIndex tile)
void PlaceProc_House(TileIndex tile)
{ {
if (_town_pool.items == 0) { if (_town_pool.items == 0) {
ShowErrorMessage(STR_ERROR_CAN_T_BUILD_HOUSE_HERE, STR_ERROR_MUST_FOUND_TOWN_FIRST, WL_INFO); ShowErrorMessage(STR_ERROR_CAN_T_BUILD_HOUSE_HERE, STR_ERROR_MUST_FOUND_TOWN_FIRST, WL_INFO);

View File

@@ -12,11 +12,6 @@
#ifndef TOWN_GUI_H #ifndef TOWN_GUI_H
#define TOWN_GUI_H #define TOWN_GUI_H
#include "tile_type.h" void ShowBuildHousePicker();
struct Window;
void ShowBuildHousePicker(Window *parent);
void PlaceProc_House(TileIndex tile);
#endif /* TOWN_GUI_H */ #endif /* TOWN_GUI_H */