make merchants use tell, and general cleanup

This commit is contained in:
Isse 2023-04-01 14:09:41 +02:00 committed by Joshua Barretto
parent b022076a5c
commit d53b344c23
11 changed files with 90 additions and 117 deletions

View File

@ -64,7 +64,7 @@ impl NpcBuilder {
stats, stats,
skill_set: comp::SkillSet::default(), skill_set: comp::SkillSet::default(),
health: None, health: None,
poise: comp::Poise::new(body.clone()), poise: comp::Poise::new(body),
inventory: comp::Inventory::with_empty(), inventory: comp::Inventory::with_empty(),
body, body,
agent: None, agent: None,

View File

@ -389,7 +389,7 @@ impl SitePrices {
.as_ref() .as_ref()
.map(|ri| { .map(|ri| {
let item = ri.inventory.get(slot)?; let item = ri.inventory.get(slot)?;
if let Some(vec) = TradePricing::get_materials(&item.name.as_ref()) { let vec = TradePricing::get_materials(&item.name.as_ref())?;
Some( Some(
vec.iter() vec.iter()
.map(|(amount2, material)| { .map(|(amount2, material)| {
@ -400,9 +400,6 @@ impl SitePrices {
.sum::<f32>() .sum::<f32>()
* (*amount as f32), * (*amount as f32),
) )
} else {
None
}
}) })
.unwrap_or(Some(0.0)) .unwrap_or(Some(0.0))
}) })

View File

@ -469,7 +469,7 @@ impl<F: FnMut(&mut NpcCtx) -> Node<R> + Send + Sync + 'static, R: 'static> Actio
}; };
match prev.0.tick(ctx) { match prev.0.tick(ctx) {
ControlFlow::Continue(()) => return ControlFlow::Continue(()), ControlFlow::Continue(()) => ControlFlow::Continue(()),
ControlFlow::Break(r) => { ControlFlow::Break(r) => {
self.prev = None; self.prev = None;
ControlFlow::Break(r) ControlFlow::Break(r)

View File

@ -150,9 +150,7 @@ impl Data {
.with_personality(Personality::random_evil(&mut rng)) .with_personality(Personality::random_evil(&mut rng))
.with_faction(site.faction) .with_faction(site.faction)
.with_home(site_id) .with_home(site_id)
.with_profession(match rng.gen_range(0..20) { .with_profession(Profession::Cultist),
_ => Profession::Cultist,
}),
); );
} }
} }

View File

@ -136,9 +136,9 @@ impl RtState {
} }
pub fn emit<E: Event>(&mut self, e: E, world: &World, index: IndexRef) { pub fn emit<E: Event>(&mut self, e: E, world: &World, index: IndexRef) {
self.event_handlers if let Some(handlers) = self.event_handlers.get::<EventHandlersOf<E>>() {
.get::<EventHandlersOf<E>>() handlers.iter().for_each(|f| f(self, world, index, &e));
.map(|handlers| handlers.iter().for_each(|f| f(self, world, index, &e))); }
} }
pub fn tick( pub fn tick(

View File

@ -45,7 +45,7 @@ fn path_in_site(start: Vec2<i32>, end: Vec2<i32>, site: &site2::Site) -> PathRes
let mut astar = Astar::new( let mut astar = Astar::new(
1000, 1000,
start, start,
&heuristic, heuristic,
BuildHasherDefault::<FxHasher64>::default(), BuildHasherDefault::<FxHasher64>::default(),
); );
@ -76,12 +76,12 @@ fn path_in_site(start: Vec2<i32>, end: Vec2<i32>, site: &site2::Site) -> PathRes
let building = if a_tile.is_building() && b_tile.is_road() { let building = if a_tile.is_building() && b_tile.is_road() {
a_tile a_tile
.plot .plot
.and_then(|plot| is_door_tile(plot, *a).then(|| 1.0)) .and_then(|plot| is_door_tile(plot, *a).then_some(1.0))
.unwrap_or(10000.0) .unwrap_or(10000.0)
} else if b_tile.is_building() && a_tile.is_road() { } else if b_tile.is_building() && a_tile.is_road() {
b_tile b_tile
.plot .plot
.and_then(|plot| is_door_tile(plot, *b).then(|| 1.0)) .and_then(|plot| is_door_tile(plot, *b).then_some(1.0))
.unwrap_or(10000.0) .unwrap_or(10000.0)
} else if (a_tile.is_building() || b_tile.is_building()) && a_tile.plot != b_tile.plot { } else if (a_tile.is_building() || b_tile.is_building()) && a_tile.plot != b_tile.plot {
10000.0 10000.0
@ -493,7 +493,7 @@ fn adventure() -> impl Action {
casual(finish().boxed()) casual(finish().boxed())
} }
}) })
.debug(move || format!("adventure")) .debug(move || "adventure")
} }
fn villager(visiting_site: SiteId) -> impl Action { fn villager(visiting_site: SiteId) -> impl Action {
@ -513,9 +513,9 @@ fn villager(visiting_site: SiteId) -> impl Action {
// Travel to the site we're supposed to be in // Travel to the site we're supposed to be in
urgent(travel_to_site(visiting_site).debug(move || { urgent(travel_to_site(visiting_site).debug(move || {
if npc_home == Some(visiting_site) { if npc_home == Some(visiting_site) {
format!("travel home") "travel home".to_string()
} else { } else {
format!("travel to visiting site") "travel to visiting site".to_string()
} }
})) }))
} else if DayPeriod::from(ctx.time_of_day.0).is_dark() } else if DayPeriod::from(ctx.time_of_day.0).is_dark()

View File

@ -27,13 +27,11 @@ impl Rule for SimulateNpcs {
if let Some(vehicle) = data.npcs.vehicles.get_mut(ride.vehicle) { if let Some(vehicle) = data.npcs.vehicles.get_mut(ride.vehicle) {
let actor = crate::data::Actor::Npc(npc_id); let actor = crate::data::Actor::Npc(npc_id);
vehicle.riders.push(actor); vehicle.riders.push(actor);
if ride.steering { if ride.steering && vehicle.driver.replace(actor).is_some() {
if vehicle.driver.replace(actor).is_some() {
panic!("Replaced driver"); panic!("Replaced driver");
} }
} }
} }
}
if let Some(home) = npc.home.and_then(|home| data.sites.get_mut(home)) { if let Some(home) = npc.home.and_then(|home| data.sites.get_mut(home)) {
home.population.insert(npc_id); home.population.insert(npc_id);

View File

@ -1290,7 +1290,7 @@ fn handle_rtsim_purge(
); );
Ok(()) Ok(())
} else { } else {
return Err(action.help_string()); Err(action.help_string())
} }
} }

View File

@ -95,7 +95,7 @@ impl RtSim {
); );
} }
let data = Data::generate(settings, &world, index); let data = Data::generate(settings, world, index);
info!("Rtsim data generated."); info!("Rtsim data generated.");
data data
}; };

View File

@ -165,25 +165,7 @@ pub fn handle_inbox_talk(bdata: &mut BehaviorData) -> bool {
standard_response_msg() standard_response_msg()
}; };
agent_data.chat_npc(msg, event_emitter); agent_data.chat_npc(msg, event_emitter);
}
/*else if agent.behavior.can_trade(agent_data.alignment.copied(), by) {
if !agent.behavior.is(BehaviorState::TRADING) {
controller.push_initiate_invite(by, InviteKind::Trade);
agent_data.chat_npc(
"npc-speech-merchant_advertisement",
event_emitter,
);
} else { } else {
let default_msg = "npc-speech-merchant_busy";
let msg = if agent.rtsim_controller.personality.is(PersonalityTrait::Disagreeable) {
"npc-speech-merchant_busy_rude"
} else {
default_msg
};
agent_data.chat_npc(msg, event_emitter);
}
}*/
else {
let mut rng = thread_rng(); let mut rng = thread_rng();
if let Some(extreme_trait) = if let Some(extreme_trait) =
agent.rtsim_controller.personality.chat_trait(&mut rng) agent.rtsim_controller.personality.chat_trait(&mut rng)
@ -522,22 +504,36 @@ pub fn handle_inbox_update_pending_trade(bdata: &mut BehaviorData) -> bool {
let (tradeid, pending, prices, inventories) = *boxval; let (tradeid, pending, prices, inventories) = *boxval;
if agent.behavior.is(BehaviorState::TRADING) { if agent.behavior.is(BehaviorState::TRADING) {
let who = usize::from(!agent.behavior.is(BehaviorState::TRADING_ISSUER)); let who = usize::from(!agent.behavior.is(BehaviorState::TRADING_ISSUER));
let mut message = |msg| {
if let Some(with) = agent
.target
.as_ref()
.and_then(|tgt_data| read_data.uids.get(tgt_data.target))
{
event_emitter.emit(ServerEvent::Chat(UnresolvedChatMsg::npc_tell(
*agent_data.uid,
*with,
msg,
)));
} else {
event_emitter.emit(ServerEvent::Chat(UnresolvedChatMsg::npc_say(
*agent_data.uid,
msg,
)));
}
};
match agent.behavior.trading_behavior { match agent.behavior.trading_behavior {
TradingBehavior::RequireBalanced { .. } => { TradingBehavior::RequireBalanced { .. } => {
let balance0 = prices.balance(&pending.offers, &inventories, 1 - who, true); let balance0 = prices.balance(&pending.offers, &inventories, 1 - who, true);
let balance1 = prices.balance(&pending.offers, &inventories, who, false); let balance1 = prices.balance(&pending.offers, &inventories, who, false);
match (balance0, balance1) { match (balance0, balance1) {
(_, None) => { (_, None) => {
event_emitter.emit(ServerEvent::Chat(UnresolvedChatMsg::npc_say( let msg = "I'm not willing to sell that item".to_string();
*agent_data.uid, message(msg);
format!("I'm not willing to sell that item"),
)))
}, },
(None, _) => { (None, _) => {
event_emitter.emit(ServerEvent::Chat(UnresolvedChatMsg::npc_say( let msg = "I'm not willing to buy that item".to_string();
*agent_data.uid, message(msg);
format!("I'm not willing to buy that item"),
)))
}, },
(Some(balance0), Some(balance1)) => { (Some(balance0), Some(balance1)) => {
if balance0 >= balance1 { if balance0 >= balance1 {
@ -567,27 +563,7 @@ pub fn handle_inbox_update_pending_trade(bdata: &mut BehaviorData) -> bool {
"That only covers {:.0}% of my costs!", "That only covers {:.0}% of my costs!",
(balance0 / balance1 * 100.0).floor() (balance0 / balance1 * 100.0).floor()
); );
if let Some(tgt_data) = &agent.target { message(msg);
// If talking with someone in particular, "tell" it only to
// them
if let Some(with) = read_data.uids.get(tgt_data.target) {
event_emitter.emit(ServerEvent::Chat(
UnresolvedChatMsg::npc_tell(
*agent_data.uid,
*with,
msg,
),
));
} else {
event_emitter.emit(ServerEvent::Chat(
UnresolvedChatMsg::npc_say(*agent_data.uid, msg),
));
}
} else {
event_emitter.emit(ServerEvent::Chat(
UnresolvedChatMsg::npc_say(*agent_data.uid, msg),
));
}
} }
if pending.phase != TradePhase::Mutate { if pending.phase != TradePhase::Mutate {
// we got into the review phase but without balanced goods, // we got into the review phase but without balanced goods,

View File

@ -4035,16 +4035,19 @@ impl Hud {
remove, remove,
quantity: &mut u32| { quantity: &mut u32| {
if let Some(prices) = prices { if let Some(prices) = prices {
let balance0 = prices if let Some((balance0, balance1)) = prices
.balance(&trade.offers, &r_inventories, who, true) .balance(&trade.offers, &r_inventories, who, true)
.unwrap_or(0.0); // TODO: Don't default to 0 here? .zip(prices.balance(
let balance1 = prices &trade.offers,
.balance(&trade.offers, &r_inventories, 1 - who, false) &r_inventories,
.unwrap_or(0.0); // TODO: Don't default to 0 here? 1 - who,
if let Some(item) = inventory.get(slot) { false,
if let Some(materials) = ))
TradePricing::get_materials(&item.item_definition_id())
{ {
if let Some(item) = inventory.get(slot) {
if let Some(materials) = TradePricing::get_materials(
&item.item_definition_id(),
) {
let unit_price: f32 = materials let unit_price: f32 = materials
.iter() .iter()
.map(|e| { .map(|e| {
@ -4076,6 +4079,7 @@ impl Hud {
} }
} }
} }
}
}; };
match slot { match slot {
Inventory(i) => { Inventory(i) => {