Skip to content

Commit

Permalink
Added a report to autoclothing, as well as some changes to DFHack::Un…
Browse files Browse the repository at this point in the history
…its to enable it.
  • Loading branch information
RosaryMala committed Jan 14, 2023
1 parent 21d160c commit 0e021e3
Show file tree
Hide file tree
Showing 4 changed files with 121 additions and 1 deletion.
2 changes: 2 additions & 0 deletions library/include/modules/Units.h
Original file line number Diff line number Diff line change
Expand Up @@ -179,6 +179,8 @@ DFHACK_EXPORT std::string getRaceName(df::unit* unit);
DFHACK_EXPORT std::string getPhysicalDescription(df::unit* unit);
DFHACK_EXPORT std::string getRaceNamePluralById(int32_t race_id);
DFHACK_EXPORT std::string getRaceNamePlural(df::unit* unit);
DFHACK_EXPORT std::string getRaceReadableNameById(int32_t race_id);
DFHACK_EXPORT std::string getRaceReadableName(df::unit* unit);
DFHACK_EXPORT std::string getRaceBabyNameById(int32_t race_id);
DFHACK_EXPORT std::string getRaceBabyName(df::unit* unit);
DFHACK_EXPORT std::string getRaceChildNameById(int32_t race_id);
Expand Down
14 changes: 14 additions & 0 deletions library/modules/Units.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1036,6 +1036,20 @@ string Units::getRaceName(df::unit* unit)
return getRaceNameById(unit->race);
}

// get human-readable race name by id or unit pointer
string Units::getRaceReadableNameById(int32_t id)
{
df::creature_raw* raw = world->raws.creatures.all[id];
if (raw)
return raw->name[0];
return "";
}
string Units::getRaceReadableName(df::unit* unit)
{
CHECK_NULL_POINTER(unit);
return getRaceReadableNameById(unit->race);
}

void df_unit_get_physical_description(df::unit* unit, string* out_str)
{
static auto* const fn =
Expand Down
2 changes: 1 addition & 1 deletion plugins/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -77,7 +77,7 @@ set_source_files_properties( Brushes.h PROPERTIES HEADER_FILE_ONLY TRUE )
#dfhack_plugin(add-spatter add-spatter.cpp)
dfhack_plugin(autobutcher autobutcher.cpp LINK_LIBRARIES lua)
dfhack_plugin(autochop autochop.cpp LINK_LIBRARIES lua)
#dfhack_plugin(autoclothing autoclothing.cpp)
dfhack_plugin(autoclothing autoclothing.cpp)
#dfhack_plugin(autodump autodump.cpp)
dfhack_plugin(autofarm autofarm.cpp)
#dfhack_plugin(autogems autogems.cpp LINK_LIBRARIES jsoncpp_static)
Expand Down
104 changes: 104 additions & 0 deletions plugins/autoclothing.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
#include "modules/Materials.h"
#include "modules/Units.h"
#include "modules/World.h"
#include "modules/Translation.h"

#include "df/itemdef_armorst.h"
#include "df/itemdef_glovesst.h"
Expand Down Expand Up @@ -55,6 +56,7 @@ static void cleanup_state(color_ostream &out);
static void do_autoclothing();
static bool validateMaterialCategory(ClothingRequirement * requirement);
static bool setItem(std::string name, ClothingRequirement* requirement);
static void generate_report(color_ostream& out);

std::vector<ClothingRequirement>clothingOrders;

Expand Down Expand Up @@ -366,6 +368,12 @@ command_result autoclothing(color_ostream &out, std::vector <std::string> & para
}
return CR_OK;
}
else if (parameters.size() == 1 && parameters[0] == "report")
{
CoreSuspender suspend;
generate_report(out);
return CR_OK;
}
else if (parameters.size() < 2 || parameters.size() > 3)
{
out << "Wrong number of arguments." << endl;
Expand Down Expand Up @@ -663,3 +671,99 @@ static void save_state(color_ostream &out)
item.val() = clothingOrders[i].Serialize();
}
}

static void list_unit_counts(color_ostream& out, std::map<int, int>& unitList)
{
for (const auto& race : unitList)
{
if (race.second == 1)
out << " 1 " << Units::getRaceReadableNameById(race.first) << endl;
else
out << " " << race.second << " " << Units::getRaceNamePluralById(race.first) << endl;
}
}

static void generate_report(color_ostream& out)
{
std::map<int, int> fullUnitList;
std::map<int, int> missingArmor;
std::map<int, int> missingShoes;
std::map<int, int> missingHelms;
std::map<int, int> missingGloves;
std::map<int, int> missingPants;
for (df::unit* unit : world->units.active)
{
if (!Units::isCitizen(unit))
continue;
fullUnitList[unit->race]++;
int numArmor = 0, numShoes = 0, numHelms = 0, numGloves = 0, numPants = 0;
for (auto itemId : unit->owned_items)
{

auto item = Items::findItemByID(itemId);
if (item->getWear() >= 1)
continue;
switch (item->getType())
{
case df::item_type::ARMOR:
numArmor++;
break;
case df::item_type::SHOES:
numShoes++;
break;
case df::item_type::HELM:
numHelms++;
break;
case df::item_type::GLOVES:
numGloves++;
break;
case df::item_type::PANTS:
numPants++;
break;
default:
break;
}
}
if (numArmor == 0)
missingArmor[unit->race]++;
if (numShoes < 2)
missingShoes[unit->race]++;
if (numHelms == 0)
missingHelms[unit->race]++;
if (numGloves < 2)
missingGloves[unit->race]++;
if (numPants == 0)
missingPants[unit->race]++;
//out << Translation::TranslateName(Units::getVisibleName(unit)) << " has " << numArmor << " armor, " << numShoes << " shoes, " << numHelms << " helms, " << numGloves << " gloves, " << numPants << " pants" << endl;
}
if (missingArmor.size() + missingShoes.size() + missingHelms.size() + missingGloves.size() + missingPants.size() == 0)
{
out << "Everybody has a full set of clothes to wear, congrats!" << endl;
return;
}
if (missingArmor.size())
{
out << "Following units need new bodywear:" << endl;
list_unit_counts(out, missingArmor);
}
if (missingShoes.size())
{
out << "Following units need new shoes:" << endl;
list_unit_counts(out, missingShoes);
}
if (missingHelms.size())
{
out << "Following units need new headwear:" << endl;
list_unit_counts(out, missingHelms);
}
if (missingGloves.size())
{
out << "Following units need new handwear:" << endl;
list_unit_counts(out, missingGloves);
}
if (missingPants.size())
{
out << "Following units need new legwear:" << endl;
list_unit_counts(out, missingPants);
}
}

0 comments on commit 0e021e3

Please sign in to comment.