Implement sub_48B244

This commit is contained in:
Ted John 2018-01-24 23:24:16 +00:00
parent 796a86962c
commit a0152c5158
11 changed files with 196 additions and 6 deletions

View File

@ -5,6 +5,11 @@
namespace openloco
{
using string_id = uint16_t;
namespace string_ids
{
constexpr string_id null = 0xFFFF;
}
}
namespace openloco::stringmgr

View File

@ -29,6 +29,7 @@
#include "platform/platform.h"
#include "progressbar.h"
#include "scenariomgr.h"
#include "stationmgr.h"
#include "things/thingmgr.h"
#include "tutorial.h"
#include "ui.h"
@ -578,7 +579,7 @@ namespace openloco
{
if (update_day_counter())
{
call(0x0048B244);
stationmgr::sub_48B244();
call(0x004B94CF);
call(0x00453487);
call(0x004284DB);

View File

@ -29,6 +29,8 @@
<ClCompile Include="things\thing.cpp" />
<ClCompile Include="things\thingmgr.cpp" />
<ClCompile Include="things\vehicle.cpp" />
<ClCompile Include="town.cpp" />
<ClCompile Include="townmgr.cpp" />
<ClCompile Include="utility\string.cpp" />
<ClCompile Include="viewportmgr.cpp" />
<ClCompile Include="window.cpp" />
@ -70,6 +72,8 @@
<ClInclude Include="things\thing.h" />
<ClInclude Include="things\thingmgr.h" />
<ClInclude Include="things\vehicle.h" />
<ClInclude Include="town.h" />
<ClInclude Include="townmgr.h" />
<ClInclude Include="tutorial.h" />
<ClInclude Include="utility\collection.hpp" />
<ClInclude Include="utility\numeric.hpp" />

View File

@ -22,6 +22,14 @@ namespace openloco
return (station_id_t)index;
}
// 0x0048F7D1
void station::sub_48F7D1()
{
registers regs;
regs.ebx = id();
call(0x0048F7D1, regs);
}
// 0x00492793
bool station::update_cargo()
{
@ -165,4 +173,12 @@ namespace openloco
regs.ebp = (int32_t)this;
call(0x004929DB, regs);
}
// 0x004CBA2D
void station::invalidate()
{
registers regs;
regs.esi = (int32_t)this;
call(0x004CBA2D, regs);
}
}

View File

@ -1,6 +1,7 @@
#pragma once
#include "localisation/stringmgr.h"
#include "town.h"
#include <cstdint>
#include <limits>
@ -42,18 +43,22 @@ namespace openloco
string_id name; // 0x00
uint8_t pad_02[0x28 - 0x02];
uint8_t var_28;
uint8_t pad_29[0x2A - 0x29];
uint8_t var_29;
uint16_t var_2A;
string_id town_name; // 0x2C
town_id_t town; // 0x2C
station_cargo_stats cargo_stats[32]; // 0x2E
uint8_t pad_1CE[0x3B0 - 0x1CE];
uint16_t var_1CE;
uint8_t pad_1D0[0x3B0 - 0x1D0];
uint8_t var_3B0;
uint8_t var_3B1;
uint8_t pad_3B2[0x3D2 - 0x3B2];
bool empty() const { return name == string_ids::null; }
station_id_t id();
void sub_48F7D1();
bool update_cargo();
int32_t calculate_cargo_rating(const station_cargo_stats& cargo) const;
void invalidate();
private:
void sub_4929DB();

View File

@ -1,11 +1,21 @@
#include "stationmgr.h"
#include "interop/interop.hpp"
#include "townmgr.h"
#include "window.h"
#include <array>
using namespace openloco::interop;
using namespace openloco::ui;
namespace openloco::stationmgr
{
static loco_global_array<station, 1024, 0x005E6EDC> _stations;
static loco_global_array<station, max_stations, 0x005E6EDC> _stations;
std::array<station, max_stations>& stations()
{
auto arr = (std::array<station, max_stations>*)_stations.get();
return *arr;
}
station* get(station_id_t id)
{
@ -16,4 +26,70 @@ namespace openloco::stationmgr
}
return nullptr;
}
// 0x00437F29
// arg0: ah
// arg1: al
static void sub_437F29(uint8_t arg0, uint8_t arg1)
{
constexpr uint8_t byte_4F9462[] = { 0, 31, 10, 7, 31, 10, 31, 31, 11 };
static loco_global_array<uint8_t, 9, 0x0053A334> byte_53A334;
byte_53A334[(arg0 * 36776) + arg1] = byte_4F9462[arg1];
}
// 0x0048B244
void sub_48B244()
{
for (auto& town : townmgr::towns())
{
if (!town.empty())
{
town.var_06 &= town_flags::flag_1;
}
}
for (auto& station : stations())
{
if (!station.empty())
{
if (station.var_1CE == 0)
{
station.var_29++;
if (station.var_29 != 5)
{
// clang-format off
if (station.var_28 == addr<0x00525E3C, uint8_t>() ||
station.var_28 == addr<0x00525E3D, uint8_t>())
// clang-format on
{
sub_437F29(station.var_28, 8);
}
}
if (station.var_29 >= 10)
{
call(0x0049E1F1);
station.invalidate();
station.sub_48F7D1();
}
}
else
{
station.var_29 = 0;
}
if (station.update_cargo())
{
auto town = townmgr::get(station.town);
if (town != nullptr && !(town->var_06 & town_flags::flag_1))
{
town->var_06 |= town_flags::flag_1;
town->var_58 |= (1 << station.var_28);
if (town->var_3A[station.var_28] < 1000)
{
town->var_3A[station.var_28]++;
}
}
}
}
}
}
}

View File

@ -1,9 +1,12 @@
#pragma once
#include "station.h"
#include <cstdint>
#include <cstddef>
namespace openloco::stationmgr
{
constexpr size_t max_stations = 1024;
station* get(station_id_t id);
void sub_48B244();
}

9
src/openloco/town.cpp Normal file
View File

@ -0,0 +1,9 @@
#include "town.h"
namespace openloco
{
bool town::empty() const
{
return var_00 != -1;
}
}

35
src/openloco/town.h Normal file
View File

@ -0,0 +1,35 @@
#pragma once
#include <cstdint>
#include <limits>
namespace openloco
{
using town_id_t = uint16_t;
namespace town_id
{
constexpr town_id_t null = std::numeric_limits<town_id_t>::max();
}
namespace town_flags
{
constexpr uint16_t flag_1 = 1 << 1;
}
#pragma pack(push, 1)
struct town
{
int16_t var_00;
uint8_t pad_02[0x06 - 0x02];
uint16_t var_06;
uint8_t pad_08[0x3A - 0x08];
int16_t var_3A[8]; // guess?
uint8_t pad_42[0x58 - 0x42];
uint16_t var_58;
uint8_t pad_5A[0x270 - 0x5A];
bool empty() const;
};
#pragma pack(pop)
}

24
src/openloco/townmgr.cpp Normal file
View File

@ -0,0 +1,24 @@
#include "townmgr.h"
#include "interop/interop.hpp"
using namespace openloco::interop;
namespace openloco::townmgr
{
static loco_global_array<town, 80, 0x005B825C> _towns;
std::array<town, max_towns> towns()
{
auto arr = (std::array<town, max_towns>*)_towns.get();
return *arr;
}
town* get(town_id_t id)
{
if (id >= _towns.size())
{
return nullptr;
}
return &_towns[id];
}
}

12
src/openloco/townmgr.h Normal file
View File

@ -0,0 +1,12 @@
#pragma once
#include "town.h"
#include <array>
namespace openloco::townmgr
{
constexpr size_t max_towns = 80;
std::array<town, max_towns> towns();
town* get(town_id_t id);
}