New tweak: block-labors

Prevents labors that can't be used from being toggled

Suggested at http://www.bay12forums.com/smf/index.php?topic=121451.msg6719464#msg6719464
develop
lethosor 2016-01-08 19:27:11 -05:00
parent 974b427833
commit d670ee8ab4
6 changed files with 116 additions and 1 deletions

@ -58,6 +58,7 @@ New Features
- `tweak`:
- ``tweak block-labors``: Prevents labors that can't be used from being toggled
- ``tweak hide-priority``: Adds an option to hide designation priority indicators
- ``tweak title-start-rename``: Adds a safe rename option to the title screen "Start Playing" menu

@ -179,6 +179,7 @@ tweak farm-plot-select
tweak import-priority-category
# Misc. UI tweaks
tweak block-labors # Prevents labors that can't be used from being toggled
tweak civ-view-agreement
tweak fps-min
tweak hide-priority

@ -280,6 +280,7 @@ Subcommands that persist until disabled or DF quits:
in advmode. The issue is that the screen tries to force you to select
the contents separately from the container. This forcefully skips child
reagents.
:block-labors: Prevents labors that can't be used from being toggled
:civ-view-agreement: Fixes overlapping text on the "view agreement" screen
:craft-age-wear: Fixes the behavior of crafted items wearing out over time (:bug:`6003`).
With this tweak, items made from cloth and leather will gain a level of

@ -1 +1 @@
Subproject commit 9b14c45604fcd1ba5851d91d122d75f86936000b
Subproject commit d952e79b684f518b04eae5f973fa39679a2a4fa0

@ -79,6 +79,7 @@
#include "tweaks/adamantine-cloth-wear.h"
#include "tweaks/advmode-contained.h"
#include "tweaks/block-labors.h"
#include "tweaks/civ-agreement-ui.h"
#include "tweaks/craft-age-wear.h"
#include "tweaks/eggs-fertile.h"
@ -117,7 +118,9 @@ REQUIRE_GLOBAL(ui_area_map_width);
REQUIRE_GLOBAL(ui_build_selector);
REQUIRE_GLOBAL(ui_building_item_cursor);
REQUIRE_GLOBAL(ui_menu_width);
REQUIRE_GLOBAL(ui_look_cursor);
REQUIRE_GLOBAL(ui_sidebar_menus);
REQUIRE_GLOBAL(ui_unit_view_mode);
REQUIRE_GLOBAL(ui_workshop_in_add);
REQUIRE_GLOBAL(world);
@ -177,6 +180,8 @@ DFhackCExport command_result plugin_init (color_ostream &out, std::vector <Plugi
" Fixes custom reactions with container inputs in advmode. The issue is\n"
" that the screen tries to force you to select the contents separately\n"
" from the container. This forcefully skips child reagents.\n"
" tweak block-labors [disable]\n"
" Prevents labors that can't be used from being toggled.\n"
" tweak civ-view-agreement\n"
" Fixes overlapping text on the \"view agreement\" screen\n"
" tweak craft-age-wear [disable]\n"
@ -239,6 +244,9 @@ DFhackCExport command_result plugin_init (color_ostream &out, std::vector <Plugi
TWEAK_HOOK("advmode-contained", advmode_contained_hook, feed);
TWEAK_HOOK("block-labors", block_labors_hook, feed);
TWEAK_HOOK("block-labors", block_labors_hook, render);
TWEAK_HOOK("civ-view-agreement", civ_agreement_view_hook, render);
TWEAK_HOOK("craft-age-wear", craft_age_wear_hook, ageItem);

@ -0,0 +1,104 @@
#include "modules/Gui.h"
#include "modules/Screen.h"
#include "modules/Units.h"
#include "df/ui_unit_view_mode.h"
#include "df/unit_labor.h"
#include "df/viewscreen_dwarfmodest.h"
using namespace DFHack;
using df::global::ui;
using df::global::ui_look_cursor;
using df::global::ui_unit_view_mode;
struct block_labors_hook : df::viewscreen_dwarfmodest {
typedef df::viewscreen_dwarfmodest interpose_base;
inline bool valid_mode()
{
return ui->main.mode == df::ui_sidebar_mode::ViewUnits &&
ui_unit_view_mode->value == df::ui_unit_view_mode::T_value::PrefLabor;
}
inline bool forbidden_labor (df::unit *unit, df::unit_labor labor)
{
return is_valid_enum_item(labor) && !Units::isValidLabor(unit, labor);
}
inline bool all_labors_enabled (df::unit *unit, df::unit_labor_category cat)
{
FOR_ENUM_ITEMS(unit_labor, labor)
{
if (ENUM_ATTR(unit_labor, category, labor) == cat &&
!unit->status.labors[labor] &&
!forbidden_labor(unit, labor))
return false;
}
return true;
}
inline void recolor_line (int x1, int x2, int y, UIColor color)
{
for (int x = x1; x <= x2; x++)
{
auto tile = Screen::readTile(x, y);
tile.fg = color;
tile.bold = false;
Screen::paintTile(tile, x, y);
}
}
DEFINE_VMETHOD_INTERPOSE(void, render, ())
{
INTERPOSE_NEXT(render)();
auto dims = Gui::getDwarfmodeViewDims();
if (valid_mode())
{
df::unit *unit = Gui::getAnyUnit(this);
for (int y = 5, i = (*ui_look_cursor/13)*13;
y <= 17 && i < unit_labors_sidemenu.size();
++y, ++i)
{
df::unit_labor labor = unit_labors_sidemenu[i];
df::unit_labor_category cat = df::unit_labor_category(labor);
if (is_valid_enum_item(cat) && all_labors_enabled(unit, cat))
recolor_line(dims.menu_x1, dims.menu_x2, y, COLOR_WHITE);
if (forbidden_labor(unit, labor))
recolor_line(dims.menu_x1, dims.menu_x2, y, COLOR_RED +
(unit->status.labors[labor] ? 8 : 0));
}
}
}
DEFINE_VMETHOD_INTERPOSE(void, feed, (std::set<df::interface_key> *input))
{
using namespace df::enums::interface_key;
if (valid_mode())
{
df::unit *unit = Gui::getAnyUnit(this);
df::unit_labor labor = unit_labors_sidemenu[*ui_look_cursor];
df::unit_labor_category cat = df::unit_labor_category(labor);
if ((input->count(SELECT) || input->count(SELECT_ALL)) && forbidden_labor(unit, labor))
{
unit->status.labors[labor] = false;
return;
}
else if (input->count(SELECT_ALL) && is_valid_enum_item(cat))
{
bool new_state = !all_labors_enabled(unit, cat);
FOR_ENUM_ITEMS(unit_labor, labor)
{
if (ENUM_ATTR(unit_labor, category, labor) == cat)
unit->status.labors[labor] = (new_state && !forbidden_labor(unit, labor));
}
return;
}
}
INTERPOSE_NEXT(feed)(input);
}
};
IMPLEMENT_VMETHOD_INTERPOSE(block_labors_hook, feed);
IMPLEMENT_VMETHOD_INTERPOSE(block_labors_hook, render);