Skip to content

Commit

Permalink
Make farm plots re-tillable in farming extension version 2 (#74344)
Browse files Browse the repository at this point in the history
* Make farm_action a method of basecamp class.

Preparation to infer plots for plowing from expansion data
so that #73761 can be fixed.

* Make farm_action use relative expansion coordinates.

Using dir instead of absolute overmap coordinates allows to access
available upgrades from basecamp expansions.
This is also more in line with other basecamp missions.

* Add mapgen update from expansions to farm_action.

Necessary to get dirtmound terrain from basecamp upgrades into the
reference map that farm_action compares to.
Fixes #73761.

* Apply suggestions from code review

Whitespace formatting corrected.

Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>

* Fixed debug message in case orientation flags fail.

* Use smallmap instead of tinymap for farm_action.

This will ensure that blueprints having multiple z-levels can be
applied correctly to the reference farm map.

* Update farming mission description.

Ensure that mission description is consistent with what happens in the
mission.

---------

Co-authored-by: silvadomi <[email protected]>
Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
  • Loading branch information
3 people authored Jun 15, 2024
1 parent 5a68b84 commit e3af8f0
Show file tree
Hide file tree
Showing 2 changed files with 59 additions and 25 deletions.
8 changes: 5 additions & 3 deletions src/basecamp.h
Original file line number Diff line number Diff line change
Expand Up @@ -336,7 +336,7 @@ class basecamp
std::string gathering_description();
/// Returns a string for the number of plants that are harvestable, plots ready to plant,
/// and ground that needs tilling
std::string farm_description( const tripoint_abs_omt &farm_pos, size_t &plots_count,
std::string farm_description( const point &dir, size_t &plots_count,
farm_ops operation );
/// Returns the description of a camp crafting options. converts fire charges to charcoal,
/// allows dark crafting
Expand Down Expand Up @@ -392,7 +392,7 @@ class basecamp
void start_salt_water_pipe( const mission_id &miss_id );
void continue_salt_water_pipe( const mission_id &miss_id );
void start_combat_mission( const mission_id &miss_id, float exertion_level );
void start_farm_op( const tripoint_abs_omt &omt_tgt, const mission_id &miss_id,
void start_farm_op( const point &dir, const mission_id &miss_id,
float exertion_level );
///Display items listed in @ref equipment to let the player pick what to give the departing
///NPC, loops until quit or empty.
Expand Down Expand Up @@ -442,7 +442,9 @@ class basecamp
* @param omt_tgt the overmap pos3 of the farm_ops
* @param op whether to plow, plant, or harvest
*/
bool farm_return( const mission_id &miss_id, const tripoint_abs_omt &omt_tgt );
bool farm_return( const mission_id &miss_id, const point &dir );
std::pair<size_t, std::string> farm_action( const point &dir, farm_ops op,
const npc_ptr &comp = nullptr );
void fortifications_return( const mission_id &miss_id );
bool salt_water_pipe_swamp_return( const mission_id &miss_id,
const comp_list &npc_list );
Expand Down
76 changes: 54 additions & 22 deletions src/faction_camp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -786,7 +786,6 @@ void basecamp::get_available_missions_by_dir( mission_data &mission_key, const p

const std::string dir_id = base_camps::all_directions.at( dir ).id;
const std::string dir_abbr = base_camps::all_directions.at( dir ).bracket_abbr.translated();
const tripoint_abs_omt omt_trg = omt_pos + dir;

{
// return legacy workers. How old is this legacy?...
Expand Down Expand Up @@ -1307,12 +1306,12 @@ void basecamp::get_available_missions_by_dir( mission_data &mission_key, const p
if( npc_list.empty() ) {
entry = _( "Notes:\n"
"Plow any spaces that have reverted to dirt or grass.\n\n" ) +
farm_description( omt_trg, plots, farm_ops::plow ) +
farm_description( dir, plots, farm_ops::plow ) +
_( "\n\n"
"Skill used: fabrication\n"
"Difficulty: N/A\n"
"Effects:\n"
"> Restores only the plots created in the last expansion upgrade.\n"
"> Restores farm plots created in previous expansion upgrades.\n"
"> Does not damage existing crops.\n\n"
"Risk: None\n"
"Intensity: Moderate\n"
Expand All @@ -1335,7 +1334,7 @@ void basecamp::get_available_missions_by_dir( mission_data &mission_key, const p
entry = _( "Notes:\n"
"Plant designated seeds in the spaces that have already been "
"tilled.\n\n" ) +
farm_description( omt_trg, plots, farm_ops::plant ) +
farm_description( dir, plots, farm_ops::plant ) +
_( "\n\n"
"Skill used: survival\n"
"Difficulty: N/A\n"
Expand All @@ -1349,7 +1348,7 @@ void basecamp::get_available_missions_by_dir( mission_data &mission_key, const p
"Positions: 0/1\n" );
mission_key.add_start( miss_id,
name_display_of( miss_id ), entry,
plots > 0 && warm_enough_to_plant( omt_trg ) );
plots > 0 && warm_enough_to_plant( omt_pos + dir ) );
} else {
entry = action_of( miss_id.id );
bool avail = update_time_left( entry, npc_list );
Expand All @@ -1364,7 +1363,7 @@ void basecamp::get_available_missions_by_dir( mission_data &mission_key, const p
if( npc_list.empty() ) {
entry = _( "Notes:\n"
"Harvest any plants that are ripe and bring the produce back.\n\n" ) +
farm_description( omt_trg, plots, farm_ops::harvest ) +
farm_description( dir, plots, farm_ops::harvest ) +
_( "\n\n"
"Skill used: survival\n"
"Difficulty: N/A\n"
Expand Down Expand Up @@ -1725,8 +1724,6 @@ bool basecamp::handle_mission( const ui_mission_id &miss_id )
const point &miss_dir = miss_id.id.dir.value();
// All missions should supply dir. Bug if they don't, so blow up during testing.

const tripoint_abs_omt omt_trg = omt_pos + miss_dir;

switch( miss_id.id.id ) {
case Camp_Distribute_Food:
distribute_food();
Expand Down Expand Up @@ -1950,9 +1947,9 @@ bool basecamp::handle_mission( const ui_mission_id &miss_id )
case Camp_Plant:
case Camp_Harvest:
if( miss_id.ret ) {
farm_return( miss_id.id, omt_trg );
farm_return( miss_id.id, miss_dir );
} else {
start_farm_op( omt_trg, miss_id.id, MODERATE_EXERCISE );
start_farm_op( miss_dir, miss_id.id, MODERATE_EXERCISE );
}
break;

Expand Down Expand Up @@ -3550,12 +3547,15 @@ static bool farm_valid_seed( const item &itm )
return itm.is_seed() && itm.typeId() != itype_marloss_seed && itm.typeId() != itype_fungal_seeds;
}

static std::pair<size_t, std::string> farm_action( const tripoint_abs_omt &omt_tgt, farm_ops op,
const npc_ptr &comp = nullptr )
std::pair<size_t, std::string> basecamp::farm_action( const point &dir, farm_ops op,
const npc_ptr &comp )
{
size_t plots_cnt = 0;
std::string crops;

const auto e_data = expansions.find( dir );
const tripoint_abs_omt omt_tgt = e_data->second.pos;

const auto is_dirtmound = []( const tripoint & pos, tinymap & bay1, tinymap & bay2 ) {
return ( bay1.ter( pos ) == ter_t_dirtmound ) && ( !bay2.has_furn( pos ) );
};
Expand All @@ -3571,10 +3571,10 @@ static std::pair<size_t, std::string> farm_action( const tripoint_abs_omt &omt_t
}

// farm_map is what the area actually looks like
tinymap farm_map;
smallmap farm_map;
farm_map.load( omt_tgt, false );
// farm_json is what the area should look like according to jsons (loaded on demand)
std::unique_ptr<fake_map> farm_json;
std::unique_ptr<small_fake_map> farm_json;
tripoint mapmin = tripoint( 0, 0, omt_tgt.z() );
tripoint mapmax = tripoint( 2 * SEEX - 1, 2 * SEEY - 1, omt_tgt.z() );
bool done_planting = false;
Expand All @@ -3587,12 +3587,44 @@ static std::pair<size_t, std::string> farm_action( const tripoint_abs_omt &omt_t
switch( op ) {
case farm_ops::plow: {
if( !farm_json ) {
farm_json = std::make_unique<fake_map>();
farm_json = std::make_unique<small_fake_map>();
mapgendata dat( omt_tgt, *farm_json->cast_to_map(), 0, calendar::turn, nullptr );
if( !run_mapgen_func( dat.terrain_type()->get_mapgen_id(), dat ) ) {
std::string omt_id = dat.terrain_type()->get_mapgen_id();
if( !run_mapgen_func( omt_id, dat ) ) {
debugmsg( "Failed to run mapgen for farm map" );
break;
}
// Add mapgen from expansion upgrades to fake_map
for( auto const &provide : e_data->second.provides ) {
if( !recipe_id( provide.first ).is_valid() ) {
continue;
}
const recipe &making = *recipe_id( provide.first );
const update_mapgen_id update_id = making.get_blueprint();
if( !has_update_mapgen_for( update_id ) ) {
continue;
}
bool mirror_horizontal;
bool mirror_vertical;
int rotation;
if( !extract_and_check_orientation_flags( making.ident(),
dir,
mirror_horizontal,
mirror_vertical,
rotation,
"%s failed to apply orientation flags to the %s upgrade",
"farm_action" ) ) {
continue;
}
farm_json->rotate( 4 - rotation );
farm_json->mirror( mirror_horizontal, mirror_vertical );
if( !run_mapgen_update_func( update_id, dat, false ) ) {
debugmsg( "farm_action failed to apply the %s map update to %s",
provide.first, omt_id );
}
farm_json->rotate( rotation );
farm_json->mirror( mirror_horizontal, mirror_vertical );
}
}
// Needs to be plowed to match json
if( is_dirtmound( pos, *farm_json, farm_map ) && is_unplowed( pos, farm_map ) ) {
Expand Down Expand Up @@ -3682,7 +3714,7 @@ static std::pair<size_t, std::string> farm_action( const tripoint_abs_omt &omt_t
return std::make_pair( plots_cnt, crops );
}

void basecamp::start_farm_op( const tripoint_abs_omt &omt_tgt, const mission_id &miss_id,
void basecamp::start_farm_op( const point &dir, const mission_id &miss_id,
float exertion_level )
{
farm_ops op = farm_ops::plow;
Expand All @@ -3697,7 +3729,7 @@ void basecamp::start_farm_op( const tripoint_abs_omt &omt_tgt, const mission_id
return;
}

std::pair<size_t, std::string> farm_data = farm_action( omt_tgt, op );
std::pair<size_t, std::string> farm_data = farm_action( dir, op );
size_t plots_cnt = farm_data.first;
if( !plots_cnt ) {
return;
Expand Down Expand Up @@ -4598,7 +4630,7 @@ bool basecamp::survey_return( const mission_id &miss_id )
return true;
}

bool basecamp::farm_return( const mission_id &miss_id, const tripoint_abs_omt &omt_tgt )
bool basecamp::farm_return( const mission_id &miss_id, const point &dir )
{
farm_ops op;
if( miss_id.id == Camp_Plow ) {
Expand All @@ -4619,7 +4651,7 @@ bool basecamp::farm_return( const mission_id &miss_id, const tripoint_abs_omt &o
return false;
}

farm_action( omt_tgt, op, comp );
farm_action( dir, op, comp );

Character &player_character = get_player_character();
//Give any seeds the NPC didn't use back to you.
Expand Down Expand Up @@ -5495,10 +5527,10 @@ std::string basecamp::gathering_description()
return output;
}

std::string basecamp::farm_description( const tripoint_abs_omt &farm_pos, size_t &plots_count,
std::string basecamp::farm_description( const point &dir, size_t &plots_count,
farm_ops operation )
{
std::pair<size_t, std::string> farm_data = farm_action( farm_pos, operation );
std::pair<size_t, std::string> farm_data = farm_action( dir, operation );
std::string entry;
plots_count = farm_data.first;
switch( operation ) {
Expand Down

0 comments on commit e3af8f0

Please sign in to comment.