Remove separate explicit messages from all room broadcasts
This commit is contained in:
		
							parent
							
								
									b666165ecc
								
							
						
					
					
						commit
						a68955deab
					
				@ -118,11 +118,6 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    dir
 | 
			
		||||
                ),
 | 
			
		||||
                Some(&format!(
 | 
			
		||||
                    "{} closes the door to the {}.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                    dir
 | 
			
		||||
                )),
 | 
			
		||||
            )
 | 
			
		||||
            .await?;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -97,26 +97,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} prepares to cut {} from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &what_part,
 | 
			
		||||
            &corpse.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} prepares to cut {} from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &what_part,
 | 
			
		||||
            &corpse.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -234,12 +221,6 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                    possession_data.display,
 | 
			
		||||
                    corpse.display_for_sentence(true, 1, false)
 | 
			
		||||
                ),
 | 
			
		||||
                Some(&format!(
 | 
			
		||||
                    "{} tries to cut the {} from {}, but only leaves a mutilated mess.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    possession_data.display,
 | 
			
		||||
                    corpse.display_for_sentence(true, 1, false)
 | 
			
		||||
                )),
 | 
			
		||||
            )
 | 
			
		||||
            .await?;
 | 
			
		||||
        } else {
 | 
			
		||||
@ -258,12 +239,6 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                    possession_data.display,
 | 
			
		||||
                    corpse.display_for_sentence(true, 1, false)
 | 
			
		||||
                ),
 | 
			
		||||
                Some(&format!(
 | 
			
		||||
                    "{} expertly cuts the {} from {}.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    possession_data.display,
 | 
			
		||||
                    corpse.display_for_sentence(true, 1, false)
 | 
			
		||||
                )),
 | 
			
		||||
            )
 | 
			
		||||
            .await?;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -46,24 +46,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                item.display_for_sentence(ctx.explicit().await?, 1, false)
 | 
			
		||||
            ))?
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} prepares to drink from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} prepares to drink from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -136,24 +124,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
        };
 | 
			
		||||
        let how_many_drunk = how_many_to_fill.min(how_many_left.min(10000) as u16).max(1);
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} drinks from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} drinks from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        if let Some(urges) = ctx.item.urges.as_mut() {
 | 
			
		||||
            urges.hunger.last_value = urges.hunger.value;
 | 
			
		||||
 | 
			
		||||
@ -136,24 +136,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                ansi!("You're wearing it - try using <bold>remove<reset> first").to_owned(),
 | 
			
		||||
            )?;
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} prepares to drop {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} prepares to drop {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -209,24 +197,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            _ => (),
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} drops {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} drops {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        let mut item_mut = (*item).clone();
 | 
			
		||||
        item_mut.location = ctx.item.location.clone();
 | 
			
		||||
        consider_expire_job_for_item(ctx.trans, &item_mut).await?;
 | 
			
		||||
 | 
			
		||||
@ -44,24 +44,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                item.display_for_sentence(ctx.explicit().await?, 1, false)
 | 
			
		||||
            ))?
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} prepares to eat {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} prepares to eat {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -129,7 +117,7 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
        };
 | 
			
		||||
        let how_many_eaten = how_many_to_fill.min(how_many_left).max(1);
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} {} {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &(if how_many_eaten == how_many_left {
 | 
			
		||||
@ -143,24 +131,7 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            }),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} {} {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &(if how_many_eaten == how_many_left {
 | 
			
		||||
                "polishes off".to_owned()
 | 
			
		||||
            } else {
 | 
			
		||||
                format!("eats {} bites from", how_many_eaten)
 | 
			
		||||
            }),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        if let Some(urges) = ctx.item.urges.as_mut() {
 | 
			
		||||
            urges.hunger.last_value = urges.hunger.value;
 | 
			
		||||
 | 
			
		||||
@ -61,26 +61,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            ))?
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} prepares to fill {} from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &to_item.display_for_sentence(true, 1, false),
 | 
			
		||||
            &from_item.display_for_sentence(true, 1, false),
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} prepares to fill {} from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &to_item.display_for_sentence(false, 1, false),
 | 
			
		||||
            &from_item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -241,26 +228,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
        ctx.trans.save_item_model(&from_item_mut).await?;
 | 
			
		||||
        ctx.trans.save_item_model(&to_item_mut).await?;
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} fills {} from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &to_item.display_for_sentence(true, 1, false),
 | 
			
		||||
            &from_item.display_for_sentence(true, 1, false),
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} fills {} from {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &to_item.display_for_sentence(false, 1, false),
 | 
			
		||||
            &from_item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        Ok(())
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -41,24 +41,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        item.display_for_sentence(ctx.explicit().await?, 1, false)
 | 
			
		||||
                    ))?
 | 
			
		||||
                }
 | 
			
		||||
                let msg_exp = format!(
 | 
			
		||||
                let msg = format!(
 | 
			
		||||
                    "{} fumbles around trying to pick up {}\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(true, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                let msg_nonexp = format!(
 | 
			
		||||
                    "{} fumbles around trying to pick up {}\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(false, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                broadcast_to_room(
 | 
			
		||||
                    ctx.trans,
 | 
			
		||||
                    &ctx.item.location,
 | 
			
		||||
                    None,
 | 
			
		||||
                    &msg_exp,
 | 
			
		||||
                    Some(&msg_nonexp),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
            }
 | 
			
		||||
            QueueCommand::GetFromContainer {
 | 
			
		||||
                from_possession_id,
 | 
			
		||||
@ -90,26 +78,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        container.display_for_sentence(ctx.explicit().await?, 1, false),
 | 
			
		||||
                    ))?
 | 
			
		||||
                }
 | 
			
		||||
                let msg_exp = format!(
 | 
			
		||||
                let msg = format!(
 | 
			
		||||
                    "{} fumbles around trying to get {} from {}.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(true, 1, false),
 | 
			
		||||
                    &container.display_for_sentence(true, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                let msg_nonexp = format!(
 | 
			
		||||
                    "{} fumbles around trying to get {} from {}.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(false, 1, false),
 | 
			
		||||
                    &container.display_for_sentence(false, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                broadcast_to_room(
 | 
			
		||||
                    ctx.trans,
 | 
			
		||||
                    &ctx.item.location,
 | 
			
		||||
                    None,
 | 
			
		||||
                    &msg_exp,
 | 
			
		||||
                    Some(&msg_nonexp),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
            }
 | 
			
		||||
            _ => user_error("Unexpected command".to_owned())?,
 | 
			
		||||
        };
 | 
			
		||||
@ -140,24 +115,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                    ))?
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                let msg_exp = format!(
 | 
			
		||||
                let msg = format!(
 | 
			
		||||
                    "{} picks up {}\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(true, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                let msg_nonexp = format!(
 | 
			
		||||
                    "{} picks up {}\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(false, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                broadcast_to_room(
 | 
			
		||||
                    ctx.trans,
 | 
			
		||||
                    &ctx.item.location,
 | 
			
		||||
                    None,
 | 
			
		||||
                    &msg_exp,
 | 
			
		||||
                    Some(&msg_nonexp),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
                (item, None)
 | 
			
		||||
            }
 | 
			
		||||
            QueueCommand::GetFromContainer {
 | 
			
		||||
@ -190,26 +153,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        container.display_for_sentence(ctx.explicit().await?, 1, false),
 | 
			
		||||
                    ))?
 | 
			
		||||
                }
 | 
			
		||||
                let msg_exp = format!(
 | 
			
		||||
                let msg = format!(
 | 
			
		||||
                    "{} gets {} from {}.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(true, 1, false),
 | 
			
		||||
                    &container.display_for_sentence(true, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                let msg_nonexp = format!(
 | 
			
		||||
                    "{} gets {} from {}.\n",
 | 
			
		||||
                    &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                    &item.display_for_sentence(false, 1, false),
 | 
			
		||||
                    &container.display_for_sentence(false, 1, false)
 | 
			
		||||
                );
 | 
			
		||||
                broadcast_to_room(
 | 
			
		||||
                    ctx.trans,
 | 
			
		||||
                    &ctx.item.location,
 | 
			
		||||
                    None,
 | 
			
		||||
                    &msg_exp,
 | 
			
		||||
                    Some(&msg_nonexp),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
                (item, Some(container))
 | 
			
		||||
            }
 | 
			
		||||
            _ => user_error("Unexpected command".to_owned())?,
 | 
			
		||||
 | 
			
		||||
@ -69,12 +69,6 @@ impl QueueCommandHandler for WithQueueHandler {
 | 
			
		||||
                &ctx.item.pronouns.subject,
 | 
			
		||||
                &item.display_for_sentence(true, 1, false),
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} tries to work out what {} can make from {}.\n",
 | 
			
		||||
                &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                &ctx.item.pronouns.subject,
 | 
			
		||||
                &item.display_for_sentence(false, 1, false),
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
@ -261,12 +255,6 @@ impl QueueCommandHandler for FromQueueHandler {
 | 
			
		||||
                                &new_item.display_for_sentence(true, 1, false),
 | 
			
		||||
                                &ctx.item.pronouns.subject
 | 
			
		||||
                            ),
 | 
			
		||||
                            Some(&format!(
 | 
			
		||||
                                "{} proudly holds up the {} {} just made.\n",
 | 
			
		||||
                                &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                                &new_item.display_for_sentence(false, 1, false),
 | 
			
		||||
                                &ctx.item.pronouns.subject
 | 
			
		||||
                            )),
 | 
			
		||||
                        )
 | 
			
		||||
                        .await?;
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
@ -113,14 +113,6 @@ impl UserVerb for Verb {
 | 
			
		||||
                    sep,
 | 
			
		||||
                    &npc.pronouns.intensive
 | 
			
		||||
                ),
 | 
			
		||||
                Some(&format!(
 | 
			
		||||
                    "{} {}s {} {} {}\n",
 | 
			
		||||
                    &npc.display_for_sentence(false, 1, true),
 | 
			
		||||
                    verb,
 | 
			
		||||
                    &item.display_for_sentence(false, 1, false),
 | 
			
		||||
                    sep,
 | 
			
		||||
                    &npc.pronouns.intensive
 | 
			
		||||
                )),
 | 
			
		||||
            )
 | 
			
		||||
            .await?;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@ -98,39 +98,23 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            )?;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let mut msg_exp = format!(
 | 
			
		||||
        let mut msg = format!(
 | 
			
		||||
            "{} starts fiddling around trying to make something",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true)
 | 
			
		||||
        );
 | 
			
		||||
        let mut msg_nonexp = format!(
 | 
			
		||||
            "{} starts fiddling around trying to make something",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true)
 | 
			
		||||
        );
 | 
			
		||||
 | 
			
		||||
        match bench_opt {
 | 
			
		||||
            None => {}
 | 
			
		||||
            Some(bench) => {
 | 
			
		||||
                msg_exp.push_str(&format!(
 | 
			
		||||
                msg.push_str(&format!(
 | 
			
		||||
                    " on {}",
 | 
			
		||||
                    bench.display_for_sentence(true, 1, false)
 | 
			
		||||
                ));
 | 
			
		||||
                msg_nonexp.push_str(&format!(
 | 
			
		||||
                    " on {}",
 | 
			
		||||
                    bench.display_for_sentence(false, 1, false)
 | 
			
		||||
                ));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        msg_exp.push_str(".\n");
 | 
			
		||||
        msg_nonexp.push_str(".\n");
 | 
			
		||||
        msg.push_str(".\n");
 | 
			
		||||
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            &ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(&ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
@ -199,12 +183,9 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let (on_what_exp, on_what_nonexp) = match bench_opt {
 | 
			
		||||
            None => ("".to_owned(), "".to_owned()),
 | 
			
		||||
            Some(bench) => (
 | 
			
		||||
                format!(" on {}", bench.display_for_sentence(true, 1, false)),
 | 
			
		||||
                format!(" on {}", bench.display_for_sentence(false, 1, false)),
 | 
			
		||||
            ),
 | 
			
		||||
        let on_what = match bench_opt {
 | 
			
		||||
            None => "".to_owned(),
 | 
			
		||||
            Some(bench) => format!(" on {}", bench.display_for_sentence(true, 1, false)),
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        let craft_data = get_craft_data_for_instructions(&instructions)
 | 
			
		||||
@ -258,14 +239,8 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        "{} makes a {}{}.\n",
 | 
			
		||||
                        &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                        &new_item.display_for_sentence(true, 1, false),
 | 
			
		||||
                        &on_what_exp
 | 
			
		||||
                        &on_what
 | 
			
		||||
                    ),
 | 
			
		||||
                    Some(&format!(
 | 
			
		||||
                        "{} makes a {}{}.\n",
 | 
			
		||||
                        &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                        &new_item.display_for_sentence(false, 1, false),
 | 
			
		||||
                        &on_what_nonexp
 | 
			
		||||
                    )),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -49,47 +49,29 @@ pub async fn announce_move(
 | 
			
		||||
    leaving: &Item,
 | 
			
		||||
    arriving: &Item,
 | 
			
		||||
) -> DResult<()> {
 | 
			
		||||
    let msg_leaving_exp = format!(
 | 
			
		||||
    let msg_leaving = format!(
 | 
			
		||||
        "{} departs towards {}\n",
 | 
			
		||||
        &character.display_for_sentence(true, 1, true),
 | 
			
		||||
        &arriving.display
 | 
			
		||||
    );
 | 
			
		||||
    let msg_leaving_nonexp = format!(
 | 
			
		||||
        "{} departs towards {}\n",
 | 
			
		||||
        character.display_for_sentence(true, 1, false),
 | 
			
		||||
        arriving
 | 
			
		||||
            .display_less_explicit
 | 
			
		||||
            .as_ref()
 | 
			
		||||
            .unwrap_or(&arriving.display)
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(
 | 
			
		||||
        trans,
 | 
			
		||||
        &format!("{}/{}", &leaving.item_type, &leaving.item_code),
 | 
			
		||||
        None,
 | 
			
		||||
        &msg_leaving_exp,
 | 
			
		||||
        Some(&msg_leaving_nonexp),
 | 
			
		||||
        &msg_leaving,
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
 | 
			
		||||
    let msg_arriving_exp = format!(
 | 
			
		||||
    let msg_arriving = format!(
 | 
			
		||||
        "{} arrives from {}\n",
 | 
			
		||||
        &character.display_for_sentence(true, 1, true),
 | 
			
		||||
        &leaving.display
 | 
			
		||||
    );
 | 
			
		||||
    let msg_arriving_nonexp = format!(
 | 
			
		||||
        "{} arrives from {}\n",
 | 
			
		||||
        character.display_for_sentence(true, 1, false),
 | 
			
		||||
        leaving
 | 
			
		||||
            .display_less_explicit
 | 
			
		||||
            .as_ref()
 | 
			
		||||
            .unwrap_or(&leaving.display)
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(
 | 
			
		||||
        trans,
 | 
			
		||||
        &format!("{}/{}", &arriving.item_type, &arriving.item_code),
 | 
			
		||||
        None,
 | 
			
		||||
        &msg_arriving_exp,
 | 
			
		||||
        Some(&msg_arriving_nonexp),
 | 
			
		||||
        &msg_arriving,
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
    Ok(())
 | 
			
		||||
@ -321,7 +303,7 @@ pub async fn handle_fall(trans: &DBTrans, faller: &mut Item, fall_dist: u64) ->
 | 
			
		||||
        * Normal::new(1.0, 0.3)?.sample(&mut rand::thread_rng())) as i64;
 | 
			
		||||
 | 
			
		||||
    if damage > 0 {
 | 
			
		||||
        change_health(trans, -damage, faller, "You fell", "You fell").await?;
 | 
			
		||||
        change_health(trans, -damage, faller, "You fell").await?;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    let descriptor = if damage >= 30 {
 | 
			
		||||
@ -477,22 +459,15 @@ async fn attempt_move_immediate(
 | 
			
		||||
                };
 | 
			
		||||
                ctx.item.active_climb = None;
 | 
			
		||||
                let descriptor = handle_fall(&ctx.trans, ctx.item, fall_dist).await?;
 | 
			
		||||
                let msg_exp = format!(
 | 
			
		||||
                let msg = format!(
 | 
			
		||||
                    "{} loses {} grip from {} metres up and {}!\n",
 | 
			
		||||
                    ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                    ctx.item.pronouns.possessive,
 | 
			
		||||
                    fall_dist,
 | 
			
		||||
                    &descriptor
 | 
			
		||||
                );
 | 
			
		||||
                let msg_nonexp = format!(
 | 
			
		||||
                    "{} loses {} grip from {} metres up and {}!\n",
 | 
			
		||||
                    ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                    &ctx.item.pronouns.possessive,
 | 
			
		||||
                    fall_dist,
 | 
			
		||||
                    &descriptor
 | 
			
		||||
                );
 | 
			
		||||
                broadcast_to_room(ctx.trans, &from_room, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &to_room, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &from_room, None, &msg).await?;
 | 
			
		||||
                broadcast_to_room(ctx.trans, &to_room, None, &msg).await?;
 | 
			
		||||
                ctx.item.queue.truncate(0);
 | 
			
		||||
                return Ok(got_there);
 | 
			
		||||
            } else if skills <= 0.0 {
 | 
			
		||||
@ -566,17 +541,12 @@ async fn attempt_move_immediate(
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            let msg_exp = format!(
 | 
			
		||||
            let msg = format!(
 | 
			
		||||
                "{} starts climbing {}\n",
 | 
			
		||||
                &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                &direction.describe_climb(if climb.height > 0 { "up" } else { "down" })
 | 
			
		||||
            );
 | 
			
		||||
            let msg_nonexp = format!(
 | 
			
		||||
                "{} starts climbing {}\n",
 | 
			
		||||
                &ctx.item.display_for_sentence(true, 1, false),
 | 
			
		||||
                &direction.describe_climb(if climb.height > 0 { "up" } else { "down" })
 | 
			
		||||
            );
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &use_location, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &use_location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
            ctx.item.active_climb = Some(ActiveClimb {
 | 
			
		||||
                ..Default::default()
 | 
			
		||||
 | 
			
		||||
@ -76,7 +76,7 @@ impl TaskHandler for SwingShutHandler {
 | 
			
		||||
            "The door to the {} swings shut with a click.\n",
 | 
			
		||||
            &direction.describe()
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(&ctx.trans, &room_str, None, &msg, Some(&msg)).await?;
 | 
			
		||||
        broadcast_to_room(&ctx.trans, &room_str, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        if let Ok(Some(other_room)) = direction_to_item(&ctx.trans, &room_str, &direction).await {
 | 
			
		||||
            let msg = format!(
 | 
			
		||||
@ -86,7 +86,7 @@ impl TaskHandler for SwingShutHandler {
 | 
			
		||||
                    .map(|d| d.describe())
 | 
			
		||||
                    .unwrap_or_else(|| "outside".to_owned())
 | 
			
		||||
            );
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &other_room.refstr(), None, &msg, Some(&msg)).await?;
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &other_room.refstr(), None, &msg).await?;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        Ok(None)
 | 
			
		||||
@ -182,11 +182,6 @@ pub async fn attempt_open_immediate(
 | 
			
		||||
                &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                dir
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} opens the door to the {}.\n",
 | 
			
		||||
                &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                dir
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -58,26 +58,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                container.display_for_sentence(ctx.explicit().await?, 1, false),
 | 
			
		||||
            ))?
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} fumbles around trying to put {} in {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false),
 | 
			
		||||
            &container.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} fumbles around trying to put {} in {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false),
 | 
			
		||||
            &container.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -139,26 +126,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            })?;
 | 
			
		||||
        container_data.checker.check_place(&container, &item)?;
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} puts {} in {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false),
 | 
			
		||||
            &container.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} puts {} in {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false),
 | 
			
		||||
            &container.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        let possession_data = match item
 | 
			
		||||
            .possession_type
 | 
			
		||||
 | 
			
		||||
@ -107,8 +107,8 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            }
 | 
			
		||||
            _ => {}
 | 
			
		||||
        }
 | 
			
		||||
        let (item, desc_exp, desc_nonexp) = match item_ref {
 | 
			
		||||
            None => (None, "the floor".to_owned(), "the floor".to_owned()),
 | 
			
		||||
        let (item, desc) = match item_ref {
 | 
			
		||||
            None => (None, "the floor".to_owned()),
 | 
			
		||||
            Some(item_ref) => {
 | 
			
		||||
                let (item_type, item_code) = match item_ref.split_once("/") {
 | 
			
		||||
                    None => user_error("Invalid item ref in Sit command".to_owned())?,
 | 
			
		||||
@ -130,30 +130,17 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        (
 | 
			
		||||
                            Some(item.clone()),
 | 
			
		||||
                            item.display_for_sentence(true, 1, false),
 | 
			
		||||
                            item.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} reclines on {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &desc_exp
 | 
			
		||||
            &desc
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} reclines on {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &desc_nonexp
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        ctx.item.action_type = LocationActionType::Reclining(item.map(|it| it.refstr()));
 | 
			
		||||
        recalculate_urge_growth(&ctx.trans, &mut ctx.item).await?;
 | 
			
		||||
 | 
			
		||||
@ -101,24 +101,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
 | 
			
		||||
        check_removeable(ctx, &item).await?;
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} fumbles around trying to take off {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} fumbles around trying to take off {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -144,24 +132,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
 | 
			
		||||
        check_removeable(ctx, &item).await?;
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} removes {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} removes {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        let mut item_mut = (*item).clone();
 | 
			
		||||
        item_mut.action_type = LocationActionType::Normal;
 | 
			
		||||
        item_mut.action_type_started = None;
 | 
			
		||||
 | 
			
		||||
@ -1,6 +1,5 @@
 | 
			
		||||
use super::{
 | 
			
		||||
    get_player_item_or_fail, is_likely_explicit, user_error, UResult, UserError, UserVerb,
 | 
			
		||||
    UserVerbRef, VerbContext,
 | 
			
		||||
    get_player_item_or_fail, user_error, UResult, UserError, UserVerb, UserVerbRef, VerbContext,
 | 
			
		||||
};
 | 
			
		||||
#[double]
 | 
			
		||||
use crate::db::DBTrans;
 | 
			
		||||
@ -17,7 +16,6 @@ pub async fn say_to_room<'l>(
 | 
			
		||||
    from_item: &Item,
 | 
			
		||||
    location: &str,
 | 
			
		||||
    say_what: &str,
 | 
			
		||||
    is_explicit: bool,
 | 
			
		||||
) -> UResult<()> {
 | 
			
		||||
    let (loc_type, loc_code) = location
 | 
			
		||||
        .split_once("/")
 | 
			
		||||
@ -33,29 +31,13 @@ pub async fn say_to_room<'l>(
 | 
			
		||||
                .to_owned(),
 | 
			
		||||
        )?
 | 
			
		||||
    }
 | 
			
		||||
    let msg_exp = format!(
 | 
			
		||||
    let msg = format!(
 | 
			
		||||
        ansi!("<yellow>{} says: <reset><bold>\"{}\"<reset>\n"),
 | 
			
		||||
        from_item.display_for_sentence(true, 1, true),
 | 
			
		||||
        say_what
 | 
			
		||||
    );
 | 
			
		||||
    let msg_lessexp = format!(
 | 
			
		||||
        ansi!("<yellow>{} says: <reset><bold>\"{}\"<reset>\n"),
 | 
			
		||||
        from_item.display_for_sentence(false, 1, true),
 | 
			
		||||
        say_what
 | 
			
		||||
    );
 | 
			
		||||
 | 
			
		||||
    broadcast_to_room(
 | 
			
		||||
        trans,
 | 
			
		||||
        location,
 | 
			
		||||
        Some(from_item),
 | 
			
		||||
        &msg_exp,
 | 
			
		||||
        if is_explicit {
 | 
			
		||||
            None
 | 
			
		||||
        } else {
 | 
			
		||||
            Some(&msg_lessexp)
 | 
			
		||||
        },
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
    broadcast_to_room(trans, location, Some(from_item), &msg).await?;
 | 
			
		||||
    Ok(())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -76,14 +58,7 @@ impl UserVerb for Verb {
 | 
			
		||||
        if player_item.death_data.is_some() {
 | 
			
		||||
            user_error("Shush, the dead can't talk!".to_string())?;
 | 
			
		||||
        }
 | 
			
		||||
        say_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &player_item,
 | 
			
		||||
            &player_item.location,
 | 
			
		||||
            &say_what,
 | 
			
		||||
            is_likely_explicit(&say_what),
 | 
			
		||||
        )
 | 
			
		||||
        .await
 | 
			
		||||
        say_to_room(ctx.trans, &player_item, &player_item.location, &say_what).await
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
static VERB_INT: Verb = Verb;
 | 
			
		||||
 | 
			
		||||
@ -34,10 +34,6 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                ansi!("<blue>{} starts methodically searching the area.<reset>\n"),
 | 
			
		||||
                ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                ansi!("<blue>{} starts methodically searching the area.<reset>\n"),
 | 
			
		||||
                ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(3))
 | 
			
		||||
@ -97,10 +93,6 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                            ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                            found.display_for_sentence(true, 1, false),
 | 
			
		||||
                    ),
 | 
			
		||||
                    Some(&format!(
 | 
			
		||||
                        "{} seems to have found {} - but can't carry it so drops it on the ground.\n",
 | 
			
		||||
                        ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                        found.display_for_sentence(false, 1, false),)),
 | 
			
		||||
                ).await?;
 | 
			
		||||
            }
 | 
			
		||||
            _ => {
 | 
			
		||||
@ -113,11 +105,6 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
                        found.display_for_sentence(true, 1, false),
 | 
			
		||||
                    ),
 | 
			
		||||
                    Some(&format!(
 | 
			
		||||
                        "{} seems to have found {}.\n",
 | 
			
		||||
                        ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
                        found.display_for_sentence(false, 1, false),
 | 
			
		||||
                    )),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
                found.location = ctx.item.refstr();
 | 
			
		||||
 | 
			
		||||
@ -99,8 +99,8 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            LocationActionType::Sitting { .. } => user_error("You're already sitting.".to_owned())?,
 | 
			
		||||
            _ => {}
 | 
			
		||||
        }
 | 
			
		||||
        let (item, desc_exp, desc_nonexp) = match item_ref {
 | 
			
		||||
            None => (None, "the floor".to_owned(), "the floor".to_owned()),
 | 
			
		||||
        let (item, desc) = match item_ref {
 | 
			
		||||
            None => (None, "the floor".to_owned()),
 | 
			
		||||
            Some(item_ref) => {
 | 
			
		||||
                let (item_type, item_code) = match item_ref.split_once("/") {
 | 
			
		||||
                    None => user_error("Invalid item ref in Sit command".to_owned())?,
 | 
			
		||||
@ -122,30 +122,17 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                        (
 | 
			
		||||
                            Some(item.clone()),
 | 
			
		||||
                            item.display_for_sentence(true, 1, false),
 | 
			
		||||
                            item.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} sits on {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &desc_exp
 | 
			
		||||
            &desc
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} sits on {}.\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &desc_nonexp
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        ctx.item.action_type = LocationActionType::Sitting(item.map(|it| it.refstr()));
 | 
			
		||||
        recalculate_urge_growth(&ctx.trans, &mut ctx.item).await?;
 | 
			
		||||
 | 
			
		||||
@ -17,9 +17,8 @@ pub async fn stand_if_needed(trans: &DBTrans, who: &mut Item) -> UResult<()> {
 | 
			
		||||
        LocationActionType::Sitting { .. } | LocationActionType::Reclining { .. } => {}
 | 
			
		||||
        _ => return Ok(()),
 | 
			
		||||
    }
 | 
			
		||||
    let msg_exp = format!("{} stands up.\n", &who.display_for_sentence(true, 1, true),);
 | 
			
		||||
    let msg_nonexp = format!("{} stands up.\n", &who.display_for_sentence(false, 1, true),);
 | 
			
		||||
    broadcast_to_room(trans, &who.location, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
    let msg = format!("{} stands up.\n", &who.display_for_sentence(true, 1, true));
 | 
			
		||||
    broadcast_to_room(trans, &who.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    who.action_type = LocationActionType::Normal;
 | 
			
		||||
    recalculate_urge_growth(trans, who).await?;
 | 
			
		||||
 | 
			
		||||
@ -80,7 +80,7 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                target_name
 | 
			
		||||
            ))?
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} prepares to use {} {} on {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &ctx.item.pronouns.possessive,
 | 
			
		||||
@ -91,25 +91,7 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
                target.display_for_sentence(true, 1, false)
 | 
			
		||||
            }
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} prepares to use {} {} on {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &ctx.item.pronouns.possessive,
 | 
			
		||||
            &item.display_for_sentence(false, 0, false),
 | 
			
		||||
            &if is_self_use {
 | 
			
		||||
                ctx.item.pronouns.intensive.clone()
 | 
			
		||||
            } else {
 | 
			
		||||
                target.display_for_sentence(true, 1, false)
 | 
			
		||||
            }
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        let mut draw_level: f64 = *ctx
 | 
			
		||||
            .item
 | 
			
		||||
            .total_skills
 | 
			
		||||
 | 
			
		||||
@ -60,24 +60,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            .as_ref()
 | 
			
		||||
            .ok_or_else(|| UserError("You can't wear that!".to_owned()))?;
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} fumbles around trying to put on {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} fumbles around trying to put on {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        Ok(time::Duration::from_secs(1))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -152,24 +140,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} wears {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} wears {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        let mut item_mut = (*item).clone();
 | 
			
		||||
        item_mut.action_type = LocationActionType::Worn;
 | 
			
		||||
        item_mut.action_type_started = Some(Utc::now());
 | 
			
		||||
 | 
			
		||||
@ -37,26 +37,13 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
        if item.location != format!("player/{}", ctx.item.item_code) {
 | 
			
		||||
            user_error("You try to wield it but realise you no longer have it".to_owned())?
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} fumbles around with {} {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &ctx.item.pronouns.possessive,
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} fumbles around with {} {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &ctx.item.pronouns.possessive,
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        let mut draw_level: f64 = ctx
 | 
			
		||||
            .item
 | 
			
		||||
            .total_skills
 | 
			
		||||
@ -105,24 +92,12 @@ impl QueueCommandHandler for QueueHandler {
 | 
			
		||||
        if item.location != format!("player/{}", ctx.item.item_code) {
 | 
			
		||||
            user_error("You try to wield it but realise you no longer have it".to_owned())?
 | 
			
		||||
        }
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} wields {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(true, 1, true),
 | 
			
		||||
            &item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} wields {}\n",
 | 
			
		||||
            &ctx.item.display_for_sentence(false, 1, true),
 | 
			
		||||
            &item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &ctx.item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &ctx.item.location, None, &msg).await?;
 | 
			
		||||
        ctx.trans
 | 
			
		||||
            .set_exclusive_action_type_to(
 | 
			
		||||
                &item,
 | 
			
		||||
 | 
			
		||||
@ -15,10 +15,10 @@ pub struct EffectSet {
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
pub enum Effect {
 | 
			
		||||
    // messagef takes player, causative item, target as the 3 parameters. Returns (explicit, non explicit) message.
 | 
			
		||||
    // messagef takes player, causative item, target as the 3 parameters. Returns message.
 | 
			
		||||
    BroadcastMessage {
 | 
			
		||||
        delay_secs: u64,
 | 
			
		||||
        messagef: Box<dyn Fn(&Item, &Item, &Item) -> (String, String) + Sync + Send>,
 | 
			
		||||
        messagef: Box<dyn Fn(&Item, &Item, &Item) -> String + Sync + Send>,
 | 
			
		||||
    },
 | 
			
		||||
    // skill_multiplier is always positive - sign flipped for crit fails.
 | 
			
		||||
    ChangeTargetHealth {
 | 
			
		||||
@ -26,6 +26,6 @@ pub enum Effect {
 | 
			
		||||
        base_effect: i64,
 | 
			
		||||
        skill_multiplier: f64,
 | 
			
		||||
        max_effect: i64,
 | 
			
		||||
        message: Box<dyn Fn(&Item) -> (String, String) + Sync + Send>,
 | 
			
		||||
        message: Box<dyn Fn(&Item) -> String + Sync + Send>,
 | 
			
		||||
    },
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -138,22 +138,11 @@ async fn start_next_attack(
 | 
			
		||||
    victim_item: &Item,
 | 
			
		||||
    weapon: &WeaponData,
 | 
			
		||||
) -> DResult<()> {
 | 
			
		||||
    let msg_exp = &(weapon
 | 
			
		||||
    let msg = &(weapon
 | 
			
		||||
        .normal_attack
 | 
			
		||||
        .start_message(&attacker_item, victim_item, true)
 | 
			
		||||
        + ".\n");
 | 
			
		||||
    let msg_nonexp = &(weapon
 | 
			
		||||
        .normal_attack
 | 
			
		||||
        .start_message(&attacker_item, victim_item, false)
 | 
			
		||||
        + ".\n");
 | 
			
		||||
    broadcast_to_room(
 | 
			
		||||
        ctx.trans,
 | 
			
		||||
        &attacker_item.location,
 | 
			
		||||
        None,
 | 
			
		||||
        msg_exp,
 | 
			
		||||
        Some(msg_nonexp),
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
    broadcast_to_room(ctx.trans, &attacker_item.location, None, msg).await?;
 | 
			
		||||
    Ok(())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -172,26 +161,13 @@ async fn process_attack(
 | 
			
		||||
        .unwrap_or(0)
 | 
			
		||||
        > 8000
 | 
			
		||||
    {
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} looks like {} wanted to attack {}, but was too tired and stressed to do it.\n",
 | 
			
		||||
            attacker_item.display_for_sentence(true, 1, true),
 | 
			
		||||
            attacker_item.pronouns.subject,
 | 
			
		||||
            victim_item.display_for_sentence(true, 1, false),
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} looks like {} wanted to attack {}, but was too tired and stressed to do it.\n",
 | 
			
		||||
            attacker_item.display_for_sentence(false, 1, true),
 | 
			
		||||
            attacker_item.pronouns.subject,
 | 
			
		||||
            victim_item.display_for_sentence(false, 1, false),
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &attacker_item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &attacker_item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        match attacker_item.active_combat.as_mut() {
 | 
			
		||||
            Some(ac) if ac.attack_mode != AttackMode::NORMAL => {
 | 
			
		||||
@ -240,24 +216,12 @@ async fn process_attack(
 | 
			
		||||
    change_stress_considering_cool(&ctx.trans, attacker_item, 100).await?;
 | 
			
		||||
 | 
			
		||||
    if dodge_result > attack_result {
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} dodges out of the way of {}'s attack.\n",
 | 
			
		||||
            victim_item.display_for_sentence(true, 1, true),
 | 
			
		||||
            attacker_item.display_for_sentence(true, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} dodges out of the way of {}'s attack.\n",
 | 
			
		||||
            victim_item.display_for_sentence(false, 1, true),
 | 
			
		||||
            attacker_item.display_for_sentence(false, 1, false)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &attacker_item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &attacker_item.location, None, &msg).await?;
 | 
			
		||||
        match attacker_item.active_combat.as_mut() {
 | 
			
		||||
            Some(ac) => ac.attack_mode = AttackMode::NORMAL,
 | 
			
		||||
            None => {}
 | 
			
		||||
@ -298,38 +262,16 @@ async fn process_attack(
 | 
			
		||||
            &part,
 | 
			
		||||
        )
 | 
			
		||||
        .await? as i64;
 | 
			
		||||
        let msg_exp = attack.success_message(&attacker_item, victim_item, &part, true);
 | 
			
		||||
        let msg_nonexp = attack.success_message(&attacker_item, victim_item, &part, false);
 | 
			
		||||
        let msg = attack.success_message(&attacker_item, victim_item, &part, true);
 | 
			
		||||
        if actual_damage == 0 {
 | 
			
		||||
            let msg_exp = format!(
 | 
			
		||||
            let msg = format!(
 | 
			
		||||
                "{}'s attack bounces off {}'s {}.\n",
 | 
			
		||||
                &attacker_item.display_for_sentence(true, 1, true),
 | 
			
		||||
                &victim_item.display_for_sentence(true, 1, false),
 | 
			
		||||
                &part.display(victim_item.sex.clone())
 | 
			
		||||
            );
 | 
			
		||||
            let msg_nonexp = format!(
 | 
			
		||||
                "{}'s attack bounces off {}'s {}.\n",
 | 
			
		||||
                attacker_item.display_for_sentence(false, 1, true),
 | 
			
		||||
                victim_item.display_for_sentence(false, 1, false),
 | 
			
		||||
                &part.display(None)
 | 
			
		||||
            );
 | 
			
		||||
            broadcast_to_room(
 | 
			
		||||
                &ctx.trans,
 | 
			
		||||
                &victim_item.location,
 | 
			
		||||
                None,
 | 
			
		||||
                &msg_exp,
 | 
			
		||||
                Some(&msg_nonexp),
 | 
			
		||||
            )
 | 
			
		||||
            .await?;
 | 
			
		||||
        } else if change_health(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            -actual_damage,
 | 
			
		||||
            victim_item,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            &msg_nonexp,
 | 
			
		||||
        )
 | 
			
		||||
        .await?
 | 
			
		||||
        {
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &victim_item.location, None, &msg).await?;
 | 
			
		||||
        } else if change_health(ctx.trans, -actual_damage, victim_item, &msg).await? {
 | 
			
		||||
            ctx.trans.save_item_model(victim_item).await?;
 | 
			
		||||
            return Ok(true);
 | 
			
		||||
        }
 | 
			
		||||
@ -375,26 +317,13 @@ async fn process_feint(
 | 
			
		||||
        .unwrap_or(0)
 | 
			
		||||
        > 8000
 | 
			
		||||
    {
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} looks like {} wanted to feint {}, but was too tired and stressed to do it.\n",
 | 
			
		||||
            attacker_item.display_for_sentence(true, 1, true),
 | 
			
		||||
            attacker_item.pronouns.subject,
 | 
			
		||||
            victim_item.display_for_sentence(true, 1, false),
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} looks like {} wanted to feint {}, but was too tired and stressed to do it.\n",
 | 
			
		||||
            attacker_item.display_for_sentence(false, 1, true),
 | 
			
		||||
            attacker_item.pronouns.subject,
 | 
			
		||||
            victim_item.display_for_sentence(false, 1, false),
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &attacker_item.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &attacker_item.location, None, &msg).await?;
 | 
			
		||||
        match attacker_item.active_combat.as_mut() {
 | 
			
		||||
            Some(ac) => {
 | 
			
		||||
                ac.attack_mode = AttackMode::NORMAL;
 | 
			
		||||
@ -426,12 +355,6 @@ async fn process_feint(
 | 
			
		||||
                &attacker_item.pronouns.object,
 | 
			
		||||
                &attacker_item.pronouns.intensive,
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} seems to have pulled off the feint so poorly {} confused {}!\n",
 | 
			
		||||
                &attacker_item.display_for_sentence(false, 1, true),
 | 
			
		||||
                &attacker_item.pronouns.object,
 | 
			
		||||
                &attacker_item.pronouns.intensive,
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        run_effects(
 | 
			
		||||
@ -460,11 +383,6 @@ async fn process_feint(
 | 
			
		||||
                &victim_item.display_for_sentence(true, 1, true),
 | 
			
		||||
                &attacker_item.display_for_sentence(true, 1, false),
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} is confused by {}'s antics!\n",
 | 
			
		||||
                &victim_item.display_for_sentence(false, 1, true),
 | 
			
		||||
                &attacker_item.display_for_sentence(false, 1, false),
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        run_effects(
 | 
			
		||||
@ -488,11 +406,6 @@ async fn process_feint(
 | 
			
		||||
                &victim_item.display_for_sentence(true, 1, true),
 | 
			
		||||
                &attacker_item.display_for_sentence(true, 1, false)
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} doesn't seem to have fallen for {}'s unenlightened attempt at a feint.\n",
 | 
			
		||||
                &victim_item.display_for_sentence(false, 1, true),
 | 
			
		||||
                &attacker_item.display_for_sentence(false, 1, false)
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        return Ok(false);
 | 
			
		||||
@ -608,8 +521,7 @@ pub async fn change_health(
 | 
			
		||||
    trans: &DBTrans,
 | 
			
		||||
    change: i64,
 | 
			
		||||
    victim: &mut Item,
 | 
			
		||||
    reason_exp: &str,
 | 
			
		||||
    reason_nonexp: &str,
 | 
			
		||||
    reason: &str,
 | 
			
		||||
) -> DResult<bool> {
 | 
			
		||||
    let maxh = max_health(victim);
 | 
			
		||||
    let new_health = ((victim.health as i64 + change).max(0) as u64).min(maxh);
 | 
			
		||||
@ -621,19 +533,15 @@ pub async fn change_health(
 | 
			
		||||
    } else {
 | 
			
		||||
        ansi!("<red>")
 | 
			
		||||
    };
 | 
			
		||||
    let msg_exp = format!(
 | 
			
		||||
    let msg = format!(
 | 
			
		||||
        ansi!("[ {}{}<reset> <bold>{}/{}<reset> ] {}.\n"),
 | 
			
		||||
        colour,
 | 
			
		||||
        change,
 | 
			
		||||
        new_health,
 | 
			
		||||
        max_health(&victim),
 | 
			
		||||
        reason_exp
 | 
			
		||||
        reason
 | 
			
		||||
    );
 | 
			
		||||
    let msg_nonexp = format!(
 | 
			
		||||
        ansi!("[ {}{}<reset> <bold>{}/{}<reset> ] {}.\n"),
 | 
			
		||||
        colour, change, new_health, maxh, reason_nonexp
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(trans, &victim.location, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
    broadcast_to_room(trans, &victim.location, None, &msg).await?;
 | 
			
		||||
    victim.health = new_health;
 | 
			
		||||
    if new_health == 0 {
 | 
			
		||||
        handle_death(trans, victim).await?;
 | 
			
		||||
@ -739,15 +647,11 @@ pub async fn consider_reward_for(
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
pub async fn handle_death(trans: &DBTrans, whom: &mut Item) -> DResult<()> {
 | 
			
		||||
    let msg_exp = format!(
 | 
			
		||||
    let msg = format!(
 | 
			
		||||
        ansi!("<red>{} stiffens and collapses dead.<reset>\n"),
 | 
			
		||||
        &whom.display_for_sentence(true, 1, true)
 | 
			
		||||
    );
 | 
			
		||||
    let msg_nonexp = format!(
 | 
			
		||||
        ansi!("<red>{} stiffens and collapses dead.<reset>\n"),
 | 
			
		||||
        &whom.display_for_sentence(false, 1, true)
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(trans, &whom.location, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
    broadcast_to_room(trans, &whom.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    whom.death_data = Some(DeathData {
 | 
			
		||||
        parts_remaining: species_info_map()
 | 
			
		||||
@ -1002,8 +906,7 @@ pub async fn start_attack_mut(
 | 
			
		||||
    by_whom: &mut Item,
 | 
			
		||||
    to_whom: &mut Item,
 | 
			
		||||
) -> UResult<()> {
 | 
			
		||||
    let mut msg_exp = String::new();
 | 
			
		||||
    let mut msg_nonexp = String::new();
 | 
			
		||||
    let mut msg = String::new();
 | 
			
		||||
    let mut verb: String = "attacks".to_string();
 | 
			
		||||
    match by_whom.action_type {
 | 
			
		||||
        LocationActionType::Sitting { .. } | LocationActionType::Reclining { .. } => {
 | 
			
		||||
@ -1037,31 +940,17 @@ pub async fn start_attack_mut(
 | 
			
		||||
        _ => {}
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    msg_exp.push_str(&format!(
 | 
			
		||||
    msg.push_str(&format!(
 | 
			
		||||
        ansi!("<red>{} {} {}.<reset>\n"),
 | 
			
		||||
        &by_whom.display_for_sentence(true, 1, true),
 | 
			
		||||
        verb,
 | 
			
		||||
        &to_whom.display_for_sentence(true, 1, false)
 | 
			
		||||
    ));
 | 
			
		||||
    msg_nonexp.push_str(&format!(
 | 
			
		||||
        ansi!("<red>{} {} {}.<reset>\n"),
 | 
			
		||||
        &by_whom.display_for_sentence(false, 1, true),
 | 
			
		||||
        verb,
 | 
			
		||||
        &to_whom.display_for_sentence(false, 1, false)
 | 
			
		||||
    ));
 | 
			
		||||
 | 
			
		||||
    let (_, wielded) = what_wielded(trans, &Arc::new(by_whom.clone())).await?;
 | 
			
		||||
    msg_exp.push_str(&(wielded.normal_attack.start_message(by_whom, to_whom, true) + ".\n"));
 | 
			
		||||
    msg_nonexp.push_str(&(wielded.normal_attack.start_message(by_whom, to_whom, false) + ".\n"));
 | 
			
		||||
    msg.push_str(&(wielded.normal_attack.start_message(by_whom, to_whom, true) + ".\n"));
 | 
			
		||||
 | 
			
		||||
    broadcast_to_room(
 | 
			
		||||
        trans,
 | 
			
		||||
        &by_whom.location,
 | 
			
		||||
        None::<&Item>,
 | 
			
		||||
        &msg_exp,
 | 
			
		||||
        Some(msg_nonexp.as_str()),
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
    broadcast_to_room(trans, &by_whom.location, None::<&Item>, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    let ac = by_whom
 | 
			
		||||
        .active_combat
 | 
			
		||||
@ -1164,9 +1053,8 @@ pub async fn switch_to_power_attack(ctx: &VerbContext<'_>, who: &Arc<Item>) -> U
 | 
			
		||||
        None => user_error("They seem to be gone!".to_owned())?,
 | 
			
		||||
        Some(v) => v,
 | 
			
		||||
    };
 | 
			
		||||
    let msg_exp = pow_att.start_message(who, &to_whom, true) + ".\n";
 | 
			
		||||
    let msg_nonexp = pow_att.start_message(who, &to_whom, false) + ".\n";
 | 
			
		||||
    broadcast_to_room(ctx.trans, &who.location, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
    let msg = pow_att.start_message(who, &to_whom, true) + ".\n";
 | 
			
		||||
    broadcast_to_room(ctx.trans, &who.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    let mut who_mut = (**who).clone();
 | 
			
		||||
    who_mut.active_combat.as_mut().map(|ac| {
 | 
			
		||||
@ -1259,15 +1147,11 @@ pub async fn switch_to_feint(ctx: &VerbContext<'_>, who: &Arc<Item>) -> UResult<
 | 
			
		||||
        },
 | 
			
		||||
    ];
 | 
			
		||||
    let feint = feints.iter().choose(&mut thread_rng()).unwrap();
 | 
			
		||||
    let msg_exp = feint(
 | 
			
		||||
    let msg = feint(
 | 
			
		||||
        &who.display_for_sentence(true, 1, true),
 | 
			
		||||
        &to_whom.display_for_sentence(true, 1, false),
 | 
			
		||||
    );
 | 
			
		||||
    let msg_nonexp = feint(
 | 
			
		||||
        &who.display_for_sentence(false, 1, true),
 | 
			
		||||
        &to_whom.display_for_sentence(false, 1, false),
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(ctx.trans, &who.location, None, &msg_exp, Some(&msg_nonexp)).await?;
 | 
			
		||||
    broadcast_to_room(ctx.trans, &who.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    let mut who_mut = (**who).clone();
 | 
			
		||||
    who_mut.active_combat.as_mut().map(|ac| {
 | 
			
		||||
@ -1339,22 +1223,11 @@ impl TaskHandler for RotCorpseTaskHandler {
 | 
			
		||||
        };
 | 
			
		||||
        destroy_container(ctx.trans, &corpse).await?;
 | 
			
		||||
 | 
			
		||||
        let msg_exp = format!(
 | 
			
		||||
        let msg = format!(
 | 
			
		||||
            "{} rots away to nothing.\n",
 | 
			
		||||
            corpse.display_for_sentence(true, 1, true)
 | 
			
		||||
        );
 | 
			
		||||
        let msg_nonexp = format!(
 | 
			
		||||
            "{} rots away to nothing.\n",
 | 
			
		||||
            corpse.display_for_sentence(false, 1, true)
 | 
			
		||||
        );
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &corpse.location,
 | 
			
		||||
            None,
 | 
			
		||||
            &msg_exp,
 | 
			
		||||
            Some(&msg_nonexp),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(ctx.trans, &corpse.location, None, &msg).await?;
 | 
			
		||||
        Ok(None)
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -7,26 +7,21 @@ pub async fn broadcast_to_room(
 | 
			
		||||
    trans: &DBTrans,
 | 
			
		||||
    location: &str,
 | 
			
		||||
    from_item: Option<&Item>,
 | 
			
		||||
    message_explicit_ok: &str,
 | 
			
		||||
    message_nonexplicit: Option<&str>,
 | 
			
		||||
    message: &str,
 | 
			
		||||
) -> DResult<()> {
 | 
			
		||||
    for item in trans.find_items_by_location(location).await? {
 | 
			
		||||
        if item.item_type != "player" || item.death_data.is_some() {
 | 
			
		||||
            continue;
 | 
			
		||||
        }
 | 
			
		||||
        if let Some((session, session_dat)) = trans.find_session_for_player(&item.item_code).await?
 | 
			
		||||
        {
 | 
			
		||||
            if session_dat.less_explicit_mode
 | 
			
		||||
                && Some(&item.item_code) != from_item.map(|i| &i.item_code)
 | 
			
		||||
            {
 | 
			
		||||
                if let Some(msg) = message_nonexplicit {
 | 
			
		||||
                    trans.queue_for_session(&session, Some(msg)).await?;
 | 
			
		||||
                }
 | 
			
		||||
                return Ok(());
 | 
			
		||||
        if let Some(exclude) = from_item {
 | 
			
		||||
            if exclude.item_code == item.item_code && exclude.item_type == item.item_type {
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            trans
 | 
			
		||||
                .queue_for_session(&session, Some(message_explicit_ok))
 | 
			
		||||
                .await?;
 | 
			
		||||
        }
 | 
			
		||||
        if let Some((session, _session_dat)) =
 | 
			
		||||
            trans.find_session_for_player(&item.item_code).await?
 | 
			
		||||
        {
 | 
			
		||||
            trans.queue_for_session(&session, Some(message)).await?;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
    Ok(())
 | 
			
		||||
 | 
			
		||||
@ -26,14 +26,12 @@ pub struct DelayedHealthEffect {
 | 
			
		||||
    magnitude: i64,
 | 
			
		||||
    delay: u64,
 | 
			
		||||
    message: String,
 | 
			
		||||
    message_nonexp: String,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[derive(Serialize, Deserialize, Clone, Debug, Eq, PartialEq, Ord, PartialOrd)]
 | 
			
		||||
pub struct DelayedMessageEffect {
 | 
			
		||||
    delay: u64,
 | 
			
		||||
    message: String,
 | 
			
		||||
    message_nonexp: String,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
pub struct DelayedHealthTaskHandler;
 | 
			
		||||
@ -73,20 +71,10 @@ impl TaskHandler for DelayedHealthTaskHandler {
 | 
			
		||||
        match item_effect_series.1.pop_front() {
 | 
			
		||||
            None => Ok(None),
 | 
			
		||||
            Some(DelayedHealthEffect {
 | 
			
		||||
                magnitude,
 | 
			
		||||
                message,
 | 
			
		||||
                message_nonexp,
 | 
			
		||||
                ..
 | 
			
		||||
                magnitude, message, ..
 | 
			
		||||
            }) => {
 | 
			
		||||
                let mut item_mut = (*item).clone();
 | 
			
		||||
                change_health(
 | 
			
		||||
                    ctx.trans,
 | 
			
		||||
                    magnitude,
 | 
			
		||||
                    &mut item_mut,
 | 
			
		||||
                    &message,
 | 
			
		||||
                    &message_nonexp,
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
                change_health(ctx.trans, magnitude, &mut item_mut, &message).await?;
 | 
			
		||||
                ctx.trans.save_item_model(&item_mut).await?;
 | 
			
		||||
                Ok(item_effect_series
 | 
			
		||||
                    .1
 | 
			
		||||
@ -135,19 +123,8 @@ impl TaskHandler for DelayedMessageTaskHandler {
 | 
			
		||||
        }
 | 
			
		||||
        match item_effect_series.1.pop_front() {
 | 
			
		||||
            None => Ok(None),
 | 
			
		||||
            Some(DelayedMessageEffect {
 | 
			
		||||
                message,
 | 
			
		||||
                message_nonexp,
 | 
			
		||||
                ..
 | 
			
		||||
            }) => {
 | 
			
		||||
                broadcast_to_room(
 | 
			
		||||
                    &ctx.trans,
 | 
			
		||||
                    &item.location,
 | 
			
		||||
                    None,
 | 
			
		||||
                    &message,
 | 
			
		||||
                    Some(&message_nonexp),
 | 
			
		||||
                )
 | 
			
		||||
                .await?;
 | 
			
		||||
            Some(DelayedMessageEffect { message, .. }) => {
 | 
			
		||||
                broadcast_to_room(&ctx.trans, &item.location, None, &message).await?;
 | 
			
		||||
                Ok(item_effect_series
 | 
			
		||||
                    .1
 | 
			
		||||
                    .front()
 | 
			
		||||
@ -214,20 +191,18 @@ pub async fn run_effects(
 | 
			
		||||
                delay_secs,
 | 
			
		||||
                messagef,
 | 
			
		||||
            } => {
 | 
			
		||||
                let (msg_exp, msg_nonexp) = messagef(
 | 
			
		||||
                let msg = messagef(
 | 
			
		||||
                    player,
 | 
			
		||||
                    item,
 | 
			
		||||
                    target.as_ref().map(|t| &**t).unwrap_or(player),
 | 
			
		||||
                );
 | 
			
		||||
                if *delay_secs == 0 {
 | 
			
		||||
                    broadcast_to_room(trans, &player.location, None, &msg_exp, Some(&msg_nonexp))
 | 
			
		||||
                        .await?;
 | 
			
		||||
                    broadcast_to_room(trans, &player.location, None, &msg).await?;
 | 
			
		||||
                } else {
 | 
			
		||||
                    dispel_time_secs = dispel_time_secs.max(*delay_secs);
 | 
			
		||||
                    let fx = DelayedMessageEffect {
 | 
			
		||||
                        delay: *delay_secs,
 | 
			
		||||
                        message: msg_exp,
 | 
			
		||||
                        message_nonexp: msg_nonexp,
 | 
			
		||||
                        message: msg,
 | 
			
		||||
                    };
 | 
			
		||||
                    let actual_target: &mut Item = *target.as_mut().unwrap_or(&mut player);
 | 
			
		||||
                    target_message_series
 | 
			
		||||
@ -248,14 +223,13 @@ pub async fn run_effects(
 | 
			
		||||
            } => {
 | 
			
		||||
                let health_impact =
 | 
			
		||||
                    (*base_effect + ((skill_multiplier * level) as i64)).min(*max_effect) as i64;
 | 
			
		||||
                let (msg, msg_nonexp) = message(target.as_ref().map(|t| &**t).unwrap_or(player));
 | 
			
		||||
                let msg = message(target.as_ref().map(|t| &**t).unwrap_or(player));
 | 
			
		||||
                if *delay_secs == 0 {
 | 
			
		||||
                    change_health(
 | 
			
		||||
                        trans,
 | 
			
		||||
                        health_impact,
 | 
			
		||||
                        *target.as_mut().unwrap_or(&mut player),
 | 
			
		||||
                        &msg,
 | 
			
		||||
                        &msg_nonexp,
 | 
			
		||||
                    )
 | 
			
		||||
                    .await?;
 | 
			
		||||
                } else {
 | 
			
		||||
@ -265,7 +239,6 @@ pub async fn run_effects(
 | 
			
		||||
                        magnitude: health_impact,
 | 
			
		||||
                        delay: *delay_secs,
 | 
			
		||||
                        message: msg,
 | 
			
		||||
                        message_nonexp: msg_nonexp,
 | 
			
		||||
                    };
 | 
			
		||||
                    target_health_series
 | 
			
		||||
                        .entry(format!("{}/{}", target_it.item_type, target_it.item_code))
 | 
			
		||||
@ -376,105 +349,84 @@ pub fn default_effects_for_type() -> &'static BTreeMap<EffectType, EffectSet> {
 | 
			
		||||
                effects: vec![
 | 
			
		||||
                    Effect::BroadcastMessage {
 | 
			
		||||
                        delay_secs: 0,
 | 
			
		||||
                        messagef: Box::new(|_player, _item, target| (
 | 
			
		||||
                        messagef: Box::new(|_player, _item, target|
 | 
			
		||||
                            format!(ansi!("<red>You notice that {} has a fresh gaping wound that looks like it's about to {}!<reset>\n"),
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "leak coolant" } else { "bleed" }
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!(ansi!("<red>You notice that {} has a fresh gaping wound that looks like it's about to {}!<reset>\n"),
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "leak coolant" } else { "bleed" }
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 10,
 | 
			
		||||
                        base_effect: -12,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: -12,
 | 
			
		||||
                        message: Box::new(|target| (
 | 
			
		||||
                        message: Box::new(|target|
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 20,
 | 
			
		||||
                        base_effect: -10,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: -10,
 | 
			
		||||
                        message: Box::new(|target| (
 | 
			
		||||
                        message: Box::new(|target|
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 30,
 | 
			
		||||
                        base_effect: -8,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: -8,
 | 
			
		||||
                        message: Box::new(|target| (
 | 
			
		||||
                        message: Box::new(|target|
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 40,
 | 
			
		||||
                        base_effect: -6,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: -6,
 | 
			
		||||
                        message: Box::new(|target| (
 | 
			
		||||
                        message: Box::new(|target|
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 50,
 | 
			
		||||
                        base_effect: -4,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: -4,
 | 
			
		||||
                        message: Box::new(|target| (
 | 
			
		||||
                        message: Box::new(|target|
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!("{} pulses from {}'s wound",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "Coolant" } else { "Blood" },
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 60,
 | 
			
		||||
                        base_effect: -2,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: -2,
 | 
			
		||||
                        message: Box::new(|target| (
 | 
			
		||||
                        message: Box::new(|target|
 | 
			
		||||
                            format!("A final tiny drop of {} oozes from {}'s wound as it heals",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "coolant" } else { "blood" },
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!("A final tiny drop of {} oozes from {}'s wound as it clots",
 | 
			
		||||
                                    if target.species == SpeciesType::Robot { "coolant" } else { "blood" },
 | 
			
		||||
                                    target.display_for_sentence(false, 1, false),
 | 
			
		||||
                        )))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                ],
 | 
			
		||||
            },
 | 
			
		||||
@ -483,26 +435,20 @@ pub fn default_effects_for_type() -> &'static BTreeMap<EffectType, EffectSet> {
 | 
			
		||||
                effects: vec![
 | 
			
		||||
                    Effect::BroadcastMessage {
 | 
			
		||||
                        delay_secs: 0,
 | 
			
		||||
                        messagef: Box::new(|_player, _item, target| (
 | 
			
		||||
                        messagef: Box::new(|_player, _item, target|
 | 
			
		||||
                            format!(ansi!("<blue>{} is stunned!<reset>\n"),
 | 
			
		||||
                                    target.display_for_sentence(true, 1, true),
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!(ansi!("<blue>{} is stunned!<reset>\n"),
 | 
			
		||||
                                         target.display_for_sentence(false, 1, true))
 | 
			
		||||
                        ))
 | 
			
		||||
                            )
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::BroadcastMessage {
 | 
			
		||||
                        delay_secs: 30,
 | 
			
		||||
                        messagef: Box::new(|_player, _item, target| (
 | 
			
		||||
                        messagef: Box::new(|_player, _item, target|
 | 
			
		||||
                            format!(ansi!("<blue>{} seems to have returned to {} senses!<reset>\n"),
 | 
			
		||||
                                    target.display_for_sentence(true, 1, true),
 | 
			
		||||
                                    &target.pronouns.object,
 | 
			
		||||
                            ),
 | 
			
		||||
                            format!(ansi!("<blue>{} seems to have returned to {} senses!<reset>\n"),
 | 
			
		||||
                                    target.display_for_sentence(false, 1, true),
 | 
			
		||||
                                    &target.pronouns.object,
 | 
			
		||||
                            )
 | 
			
		||||
                        ))
 | 
			
		||||
                        )
 | 
			
		||||
                    },
 | 
			
		||||
                ]
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
@ -265,7 +265,7 @@ impl TaskHandler for ShareTaskHandler {
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
        let msg = format!(ansi!("<magenta>{}<reset>\n"), &msg);
 | 
			
		||||
        broadcast_to_room(&ctx.trans, &p1.location, None, &msg, Some(&msg)).await?;
 | 
			
		||||
        broadcast_to_room(&ctx.trans, &p1.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
        let mut p1_mut = (*p1).clone();
 | 
			
		||||
        let mut p2_mut = (*p2).clone();
 | 
			
		||||
@ -638,7 +638,6 @@ pub async fn start_conversation(
 | 
			
		||||
            &acceptor.display_for_sentence(false, 1, true),
 | 
			
		||||
            &acceptor.pronouns.subject
 | 
			
		||||
        ),
 | 
			
		||||
        None,
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
 | 
			
		||||
@ -708,7 +707,6 @@ pub async fn stop_conversation_mut(
 | 
			
		||||
            leave_description,
 | 
			
		||||
            &partner_mut.display_for_sentence(true, 1, false)
 | 
			
		||||
        ),
 | 
			
		||||
        None,
 | 
			
		||||
    )
 | 
			
		||||
    .await?;
 | 
			
		||||
 | 
			
		||||
@ -1078,7 +1076,7 @@ pub async fn change_conversational_style(
 | 
			
		||||
        topic.display_readable(),
 | 
			
		||||
        &alt_topics_str
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(&ctx.trans, &player_item.location, None, &msg, Some(&msg)).await?;
 | 
			
		||||
    broadcast_to_room(&ctx.trans, &player_item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    Ok(())
 | 
			
		||||
}
 | 
			
		||||
@ -1128,7 +1126,7 @@ pub async fn change_conversation_topic(
 | 
			
		||||
        other_player.display_for_sentence(true, 1, false),
 | 
			
		||||
        topic.display_readable(),
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(&ctx.trans, &player_item.location, None, &msg, Some(&msg)).await?;
 | 
			
		||||
    broadcast_to_room(&ctx.trans, &player_item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    Ok(())
 | 
			
		||||
}
 | 
			
		||||
@ -1170,7 +1168,7 @@ pub async fn change_conversation_intensity(
 | 
			
		||||
        other_player.display_for_sentence(true, 1, false),
 | 
			
		||||
        intensity.display_readable(),
 | 
			
		||||
    );
 | 
			
		||||
    broadcast_to_room(&ctx.trans, &player_item.location, None, &msg, Some(&msg)).await?;
 | 
			
		||||
    broadcast_to_room(&ctx.trans, &player_item.location, None, &msg).await?;
 | 
			
		||||
 | 
			
		||||
    Ok(())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -473,6 +473,6 @@ pub async fn crit_fail_penalty_for_skill(
 | 
			
		||||
        .floor()
 | 
			
		||||
        .max(1.0);
 | 
			
		||||
    let final_damage = soak_damage(trans, &dist, who, actual_damage_presoak, &part).await?;
 | 
			
		||||
    change_health(trans, -final_damage as i64, who, &msg, &msg).await?;
 | 
			
		||||
    change_health(trans, -final_damage as i64, who, &msg).await?;
 | 
			
		||||
    Ok(())
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -101,7 +101,7 @@ pub async fn hunger_changed(trans: &DBTrans, who: &Item) -> DResult<()> {
 | 
			
		||||
        }
 | 
			
		||||
    } else {
 | 
			
		||||
        if who.species == SpeciesType::Human {
 | 
			
		||||
            match say_to_room(&trans, who, &who.location, msg, false).await {
 | 
			
		||||
            match say_to_room(&trans, who, &who.location, msg).await {
 | 
			
		||||
                Ok(_) => Ok(()),
 | 
			
		||||
                Err(SystemError(e)) => Err(e),
 | 
			
		||||
                Err(UserError(_)) => Ok(()),
 | 
			
		||||
@ -183,7 +183,7 @@ pub async fn thirst_changed(trans: &DBTrans, who: &Item) -> DResult<()> {
 | 
			
		||||
                .await?;
 | 
			
		||||
        }
 | 
			
		||||
    } else {
 | 
			
		||||
        match say_to_room(&trans, who, &who.location, msg, false).await {
 | 
			
		||||
        match say_to_room(&trans, who, &who.location, msg).await {
 | 
			
		||||
            Ok(_) => Ok(()),
 | 
			
		||||
            Err(SystemError(e)) => Err(e),
 | 
			
		||||
            Err(UserError(_)) => Ok(()),
 | 
			
		||||
 | 
			
		||||
@ -53,8 +53,7 @@ pub trait NPCMessageHandler {
 | 
			
		||||
 | 
			
		||||
#[derive(Clone, Debug)]
 | 
			
		||||
pub enum NPCSayType {
 | 
			
		||||
    // Bool is true if it should be filtered for less-explicit.
 | 
			
		||||
    FromFixedList(Vec<(bool, &'static str)>),
 | 
			
		||||
    FromFixedList(Vec<&'static str>),
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#[derive(Clone, Debug)]
 | 
			
		||||
@ -393,7 +392,7 @@ impl TaskHandler for NPCSayTaskHandler {
 | 
			
		||||
            return Ok(None);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let (is_explicit, say_what) = match &say_info.talk_type {
 | 
			
		||||
        let say_what = match &say_info.talk_type {
 | 
			
		||||
            NPCSayType::FromFixedList(l) => {
 | 
			
		||||
                let mut rng = thread_rng();
 | 
			
		||||
                match l[..].choose(&mut rng) {
 | 
			
		||||
@ -404,20 +403,12 @@ impl TaskHandler for NPCSayTaskHandler {
 | 
			
		||||
                        );
 | 
			
		||||
                        return Ok(None);
 | 
			
		||||
                    }
 | 
			
		||||
                    Some(r) => r.clone(),
 | 
			
		||||
                    Some(r) => r,
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        match say_to_room(
 | 
			
		||||
            ctx.trans,
 | 
			
		||||
            &npc_item,
 | 
			
		||||
            &npc_item.location,
 | 
			
		||||
            say_what,
 | 
			
		||||
            is_explicit,
 | 
			
		||||
        )
 | 
			
		||||
        .await
 | 
			
		||||
        {
 | 
			
		||||
        match say_to_room(ctx.trans, &npc_item, &npc_item.location, say_what).await {
 | 
			
		||||
            Ok(()) => {}
 | 
			
		||||
            Err(CommandHandlingError::UserError(e)) => {
 | 
			
		||||
                info!(
 | 
			
		||||
 | 
			
		||||
@ -260,7 +260,7 @@ impl NPCMessageHandler for DoorbotMsgHandler {
 | 
			
		||||
                             again, ready for the next candidate for the club - so I suggest you enter \
 | 
			
		||||
                             before it closes.\"<reset>. As if by magic, the puzzle resets back to \
 | 
			
		||||
                             its starting state, and the door swings open with a creak.\n");
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &target.location, None, msg, Some(msg)).await?;
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &target.location, None, msg).await?;
 | 
			
		||||
            ctx.trans
 | 
			
		||||
                .upsert_task(&Task {
 | 
			
		||||
                    meta: TaskMeta {
 | 
			
		||||
@ -286,7 +286,7 @@ impl NPCMessageHandler for DoorbotMsgHandler {
 | 
			
		||||
                "Doorbot moves a disc to tower {}. The screen now shows: {}.\n",
 | 
			
		||||
                to, &descr
 | 
			
		||||
            );
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &target.location, None, &msg, Some(&msg)).await?;
 | 
			
		||||
            broadcast_to_room(&ctx.trans, &target.location, None, &msg).await?;
 | 
			
		||||
            room_item.details_dyn_suffix = Some(descr);
 | 
			
		||||
            ctx.trans.save_item_model(&room_item).await?;
 | 
			
		||||
 | 
			
		||||
@ -375,22 +375,22 @@ pub fn npc_list() -> Vec<NPC> {
 | 
			
		||||
        say_code: "babble",
 | 
			
		||||
        frequency_secs: 120,
 | 
			
		||||
        talk_type: FromFixedList(vec!(
 | 
			
		||||
            (false, "I wish I could get into the secret hackers club - I heard they have a machine that hacks your wristpad to make you a super smart dork."),
 | 
			
		||||
            (false, "The basement here is pretty dangerous with all those robots."),
 | 
			
		||||
            (false, "I overhead a real dork bragging about how he managed to get all four rings onto the rightmost virtual peg. No idea what that was about!"),
 | 
			
		||||
            (false, "Why is it that all the dorks around here keep whispering stuff to each other about Towers of Hanoi?"),
 | 
			
		||||
            ("I wish I could get into the secret hackers club - I heard they have a machine that hacks your wristpad to make you a super smart dork."),
 | 
			
		||||
            ("The basement here is pretty dangerous with all those robots."),
 | 
			
		||||
            ("I overhead a real dork bragging about how he managed to get all four rings onto the rightmost virtual peg. No idea what that was about!"),
 | 
			
		||||
            ("Why is it that all the dorks around here keep whispering stuff to each other about Towers of Hanoi?"),
 | 
			
		||||
        ))
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    let killbot_stdsay = NPCSayInfo {
 | 
			
		||||
        say_code: "babble",
 | 
			
		||||
        frequency_secs: 20,
 | 
			
		||||
        talk_type: FromFixedList(vec!(
 | 
			
		||||
            (false, "My mission is to EXTERMINATE"),
 | 
			
		||||
            (false, "Intruder kill mode active"),
 | 
			
		||||
            (false, "Recoverable Error: Preset Kill Limit not set. Treating as unlimited"),
 | 
			
		||||
            (false, "404 action module STUN not found. Falling back to action KILL underscore WITH underscore EXTREME underscore PREJUDICE"),
 | 
			
		||||
        ))
 | 
			
		||||
        talk_type: FromFixedList(vec![
 | 
			
		||||
            "My mission is to EXTERMINATE",
 | 
			
		||||
            "Intruder kill mode active",
 | 
			
		||||
            "Recoverable Error: Preset Kill Limit not set. Treating as unlimited",
 | 
			
		||||
            "404 action module STUN not found. Falling back to action KILL underscore WITH underscore EXTREME underscore PREJUDICE",
 | 
			
		||||
        ])
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    fn geek_gender_word(pronouns: &NPCPronounType) -> &'static str {
 | 
			
		||||
 | 
			
		||||
@ -19,16 +19,16 @@ pub fn npc_list() -> Vec<NPC> {
 | 
			
		||||
    let melbs_citizen_stdsay = NPCSayInfo {
 | 
			
		||||
        say_code: "babble",
 | 
			
		||||
        frequency_secs: 120,
 | 
			
		||||
        talk_type: FromFixedList(vec!(
 | 
			
		||||
            (false, "I'm so sick of being cloned."),
 | 
			
		||||
            (false, "I hope I don't die again today."),
 | 
			
		||||
            (false, "I wish the so-called king would do something about the damned zombies everywhere."),
 | 
			
		||||
            (true, "I earn so many credits making babies for the body factory - it literally pays my bills."),
 | 
			
		||||
            (false, "I know people hated the empire, but I kind of wish it was still intact - it was a lot better than what we have now."),
 | 
			
		||||
            (false, "I wish there wasn't so much radiation outside of Melbs CBD."),
 | 
			
		||||
            (false, "I heard about a guy who went to a special place somewhere around here, and there was a machine that enhanced his wristpad and gave him basically superpowers."),
 | 
			
		||||
            (false, "The damn vampire movement... they are all so sneaky, and I never know when they are going to come for my blood."),
 | 
			
		||||
        ))
 | 
			
		||||
        talk_type: FromFixedList(vec![
 | 
			
		||||
            "I'm so sick of being cloned.",
 | 
			
		||||
            "I hope I don't die again today.",
 | 
			
		||||
            "I wish the so-called king would do something about the damned zombies everywhere.",
 | 
			
		||||
            "I heard in the olden days before the empire babies grew up naturally instead of being taken away to the body factory.",
 | 
			
		||||
            "I know people hated the empire, but I kind of wish it was still intact - it was a lot better than what we have now.",
 | 
			
		||||
            "I wish there wasn't so much radiation outside of Melbs CBD.",
 | 
			
		||||
            "I heard about a guy who went to a special place somewhere around here, and there was a machine that enhanced his wristpad and gave him basically superpowers.",
 | 
			
		||||
            "The damn vampire movement... they are all so sneaky, and I never know when they are going to come for my blood.",
 | 
			
		||||
        ])
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    from_yaml_str::<Vec<Citizen>>(include_str!("melbs_citizen.yaml"))
 | 
			
		||||
 | 
			
		||||
@ -50,34 +50,23 @@ impl HireHandler for RoboporterHandler {
 | 
			
		||||
        } else {
 | 
			
		||||
            50 - stats.total_count
 | 
			
		||||
        };
 | 
			
		||||
        let mut msg_exp = String::new();
 | 
			
		||||
        let mut msg_nonexp = String::new();
 | 
			
		||||
        let desc_exp = target.display_for_sentence(true, 1, true);
 | 
			
		||||
        let desc_nonexp = target.display_for_sentence(false, 1, true);
 | 
			
		||||
        let mut msg = String::new();
 | 
			
		||||
        let desc = target.display_for_sentence(true, 1, true);
 | 
			
		||||
        for item in trans.find_items_by_location(&target.refstr()).await? {
 | 
			
		||||
            if remaining_space > 0 {
 | 
			
		||||
                msg_exp.push_str(&format!(
 | 
			
		||||
                msg.push_str(&format!(
 | 
			
		||||
                    "{} unloads {} from {}\n",
 | 
			
		||||
                    &desc_exp,
 | 
			
		||||
                    &desc,
 | 
			
		||||
                    &item.display_for_sentence(true, 1, false),
 | 
			
		||||
                    &target.pronouns.intensive
 | 
			
		||||
                ));
 | 
			
		||||
                msg_nonexp.push_str(&format!(
 | 
			
		||||
                    "{} unloads {} from {}\n",
 | 
			
		||||
                    &desc_nonexp,
 | 
			
		||||
                    &item.display_for_sentence(false, 1, false),
 | 
			
		||||
                    &target.pronouns.intensive
 | 
			
		||||
                ));
 | 
			
		||||
                let mut item_mut = (*item).clone();
 | 
			
		||||
                item_mut.location = target.location.clone();
 | 
			
		||||
                trans.save_item_model(&item_mut).await?;
 | 
			
		||||
                remaining_space -= 1;
 | 
			
		||||
            } else {
 | 
			
		||||
                msg_exp.push_str(&format!("{} unloads {} - but since there isn't enough space to put it down, flicks it into the Roboporter's onboard furnace compartment!\n",
 | 
			
		||||
                                          &desc_exp, &item.display_for_sentence(true, 1, false),
 | 
			
		||||
                ));
 | 
			
		||||
                msg_nonexp.push_str(&format!("{} unloads {} - but since there isn't enough space to put it down, flicks it into the Roboporter's onboard furnace compartment!\n",
 | 
			
		||||
                                          &desc_exp, &item.display_for_sentence(false, 1, false),
 | 
			
		||||
                msg.push_str(&format!("{} unloads {} - but since there isn't enough space to put it down, flicks it into the Roboporter's onboard furnace compartment!\n",
 | 
			
		||||
                                          &desc, &item.display_for_sentence(true, 1, false),
 | 
			
		||||
                ));
 | 
			
		||||
                recursively_destroy_or_move_item(trans, &item).await?;
 | 
			
		||||
            }
 | 
			
		||||
@ -89,22 +78,12 @@ impl HireHandler for RoboporterHandler {
 | 
			
		||||
        {
 | 
			
		||||
            if return_to != &target.location {
 | 
			
		||||
                target.location = return_to.to_owned();
 | 
			
		||||
                msg_exp.push_str(
 | 
			
		||||
                msg.push_str(
 | 
			
		||||
                        &format!("By some marvel of modern engineering, {} disappears in a puff of smoke and is gone.\n",
 | 
			
		||||
                                 desc_exp));
 | 
			
		||||
                msg_nonexp.push_str(
 | 
			
		||||
                        &format!("By some marvel of modern engineering, {} disappears in a puff of smoke and is gone.\n",
 | 
			
		||||
                                 desc_nonexp));
 | 
			
		||||
                                 desc));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        broadcast_to_room(
 | 
			
		||||
            trans,
 | 
			
		||||
            &old_location,
 | 
			
		||||
            None,
 | 
			
		||||
            msg_exp.as_str(),
 | 
			
		||||
            Some(msg_nonexp.as_str()),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        broadcast_to_room(trans, &old_location, None, msg.as_str()).await?;
 | 
			
		||||
        Ok(())
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
@ -101,11 +101,6 @@ impl ArglessHandler for CorpLicenceHandler {
 | 
			
		||||
                &player.display_for_sentence(true, 1, true),
 | 
			
		||||
                name
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} signs a contract establishing {} as a corp\n",
 | 
			
		||||
                &player.display_for_sentence(false, 1, true),
 | 
			
		||||
                name
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        let corp_id = ctx
 | 
			
		||||
 | 
			
		||||
@ -91,12 +91,6 @@ impl InstallHandler for ScanLockInstall {
 | 
			
		||||
                &direction.describe(),
 | 
			
		||||
                &what.display_for_sentence(true, 1, false)
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} bangs the door to the {} as he installs {} on it.\n",
 | 
			
		||||
                &player.display_for_sentence(false, 1, true),
 | 
			
		||||
                &direction.describe(),
 | 
			
		||||
                &what.display_for_sentence(false, 1, false)
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        Ok(())
 | 
			
		||||
@ -140,13 +134,6 @@ impl InstallHandler for ScanLockInstall {
 | 
			
		||||
                &what.display_for_sentence(true, 1, false),
 | 
			
		||||
                extra_text
 | 
			
		||||
            ),
 | 
			
		||||
            Some(&format!(
 | 
			
		||||
                "{} bangs the door to the {} as he uninstalls {} from it{}.\n",
 | 
			
		||||
                &player.display_for_sentence(false, 1, true),
 | 
			
		||||
                &direction.describe(),
 | 
			
		||||
                &what.display_for_sentence(false, 1, false),
 | 
			
		||||
                extra_text
 | 
			
		||||
            )),
 | 
			
		||||
        )
 | 
			
		||||
        .await?;
 | 
			
		||||
        Ok(())
 | 
			
		||||
 | 
			
		||||
@ -30,7 +30,7 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                     effects: vec!(
 | 
			
		||||
                         Effect::BroadcastMessage {
 | 
			
		||||
                             delay_secs: 0,
 | 
			
		||||
                             messagef: Box::new(|player, _item, target| (
 | 
			
		||||
                             messagef: Box::new(|player, _item, target|
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "{} attempts to heal {} with a trauma kit, but fucks it up badly\n",
 | 
			
		||||
                                     &player.display_for_sentence(true, 1, true),
 | 
			
		||||
@ -40,28 +40,17 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                                         target.display_for_sentence(true, 1, false)
 | 
			
		||||
                                     }
 | 
			
		||||
                                 ),
 | 
			
		||||
                                 format!("{} attempts to heal {} with a trauma kit, but messes it up badly\n",
 | 
			
		||||
                                         &player.display_for_sentence(false, 1, true),
 | 
			
		||||
                                         &if target.item_type == player.item_type && target.item_code == player.item_code {
 | 
			
		||||
                                             player.pronouns.intensive.clone()
 | 
			
		||||
                                         } else {
 | 
			
		||||
                                             target.display_for_sentence(false, 1, false)
 | 
			
		||||
                                         }
 | 
			
		||||
                                 )))
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
                             delay_secs: 0, base_effect: -2, skill_multiplier: -3.0,
 | 
			
		||||
                             max_effect: -5,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "Fuck! The trauma kit makes {}'s condition worse",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false)),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "The trauma kit makes {}'s condition worse",
 | 
			
		||||
                                      target.display_for_sentence(false, 1, false)
 | 
			
		||||
                                  )
 | 
			
		||||
                                 ))
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false))
 | 
			
		||||
                             )
 | 
			
		||||
                         }
 | 
			
		||||
                     )
 | 
			
		||||
                 }),
 | 
			
		||||
@ -70,7 +59,7 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                     effects: vec!(
 | 
			
		||||
                         Effect::BroadcastMessage {
 | 
			
		||||
                             delay_secs: 0,
 | 
			
		||||
                             messagef: Box::new(|player, _item, target| (
 | 
			
		||||
                             messagef: Box::new(|player, _item, target|
 | 
			
		||||
                               format!(
 | 
			
		||||
                                   "{} attempts unsuccessfully to heal {} with a trauma kit\n",
 | 
			
		||||
                                   &player.display_for_sentence(true, 1, true),
 | 
			
		||||
@ -79,15 +68,8 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                                   } else {
 | 
			
		||||
                                       target.display_for_sentence(true, 1, false)
 | 
			
		||||
                                   }
 | 
			
		||||
                               ),
 | 
			
		||||
                               format!("{} attempts unsuccessfully to heal {} with a trauma kit\n",
 | 
			
		||||
                                       &player.display_for_sentence(false, 1, true),
 | 
			
		||||
                                       &if target.item_type == player.item_type && target.item_code == player.item_code {
 | 
			
		||||
                                           player.pronouns.intensive.clone()
 | 
			
		||||
                                       } else {
 | 
			
		||||
                                           target.display_for_sentence(false, 1, false)
 | 
			
		||||
                                       }
 | 
			
		||||
                               )))
 | 
			
		||||
                               )
 | 
			
		||||
                             )
 | 
			
		||||
                       },
 | 
			
		||||
                     )
 | 
			
		||||
                 }),
 | 
			
		||||
@ -96,7 +78,7 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                     effects: vec!(
 | 
			
		||||
                         Effect::BroadcastMessage {
 | 
			
		||||
                             delay_secs: 0,
 | 
			
		||||
                             messagef: Box::new(|player, _item, target| (
 | 
			
		||||
                             messagef: Box::new(|player, _item, target|
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "{} expertly heals {} with a trauma kit\n",
 | 
			
		||||
                                     &player.display_for_sentence(true, 1, true),
 | 
			
		||||
@ -105,31 +87,19 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                                     } else {
 | 
			
		||||
                                         target.display_for_sentence(true, 1, false)
 | 
			
		||||
                                     }
 | 
			
		||||
                                 ),
 | 
			
		||||
                                 format!("{} expertly heals {} with a trauma kit\n",
 | 
			
		||||
                                         &player.display_for_sentence(false, 1, true),
 | 
			
		||||
                                         &if target.item_type == player.item_type && target.item_code == player.item_code {
 | 
			
		||||
                                             player.pronouns.intensive.clone()
 | 
			
		||||
                                         } else {
 | 
			
		||||
                                             target.display_for_sentence(false, 1, false)
 | 
			
		||||
                                         }
 | 
			
		||||
                                 )))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
                             delay_secs: 0, base_effect: 2, skill_multiplier: 8.0,
 | 
			
		||||
                             max_effect: 10,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                               |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "FUUUCK! It hurts {}, but also starts to soothe {}",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                     &target.pronouns.object
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                    "It hurts {}, but also starts to soothe {}",
 | 
			
		||||
                                    target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                    &target.pronouns.object
 | 
			
		||||
                                ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
@ -137,16 +107,11 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                             max_effect: 9,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "FUUUCK! It hurts {}, but also starts to soothe {}",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                     &target.pronouns.object
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "It hurts {}, but also starts to soothe {}",
 | 
			
		||||
                                      target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                      &target.pronouns.object
 | 
			
		||||
                                  ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
@ -154,14 +119,10 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                             max_effect: 7,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages soothe {}'s wounds",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "The bandages soothe {}'s wounds",
 | 
			
		||||
                                      target.display_for_sentence(false, 1, false),
 | 
			
		||||
                                  ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
@ -169,14 +130,10 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                             max_effect: 6,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages soothe {}'s wounds",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "The bandages soothe {}'s wounds",
 | 
			
		||||
                                      target.display_for_sentence(false, 1, false),
 | 
			
		||||
                                  ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
@ -184,14 +141,10 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                             max_effect: 4,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages soothe {}'s wounds",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "The bandages soothe {}'s wounds",
 | 
			
		||||
                                      target.display_for_sentence(false, 1, false),
 | 
			
		||||
                                  ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
@ -199,14 +152,10 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                             max_effect: 3,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages soothe {}'s wounds",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "The bandages soothe {}'s wounds",
 | 
			
		||||
                                      target.display_for_sentence(false, 1, false),
 | 
			
		||||
                                  ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::ChangeTargetHealth {
 | 
			
		||||
@ -214,27 +163,20 @@ pub fn data() -> &'static Vec<(PossessionType, PossessionData)> {
 | 
			
		||||
                             max_effect: 2,
 | 
			
		||||
                             message: Box::new(
 | 
			
		||||
                                 |target|
 | 
			
		||||
                                 (format!(
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages soothe {}'s wounds",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false),
 | 
			
		||||
                                 ),
 | 
			
		||||
                                  format!(
 | 
			
		||||
                                      "The bandages soothe {}'s wounds",
 | 
			
		||||
                                      target.display_for_sentence(false, 1, false),
 | 
			
		||||
                                  ))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         },
 | 
			
		||||
                         Effect::BroadcastMessage {
 | 
			
		||||
                             delay_secs: 60,
 | 
			
		||||
                             messagef: Box::new(|_player, _item, target| (
 | 
			
		||||
                             messagef: Box::new(|_player, _item, target|
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages wrapping {} crumble and fall away, their healing capabilities fully expended.\n",
 | 
			
		||||
                                     target.display_for_sentence(true, 1, false)
 | 
			
		||||
                                 ),
 | 
			
		||||
                                 format!(
 | 
			
		||||
                                     "The bandages wrapping {} crumble and fall away, their healing capabilities fully expended.\n",
 | 
			
		||||
                                     target.display_for_sentence(false, 1, false)
 | 
			
		||||
                                 )))
 | 
			
		||||
                                 )
 | 
			
		||||
                             )
 | 
			
		||||
                         }
 | 
			
		||||
                     ),
 | 
			
		||||
                 }),
 | 
			
		||||
 | 
			
		||||
@ -121,48 +121,28 @@ impl TaskHandler for SeePatientTaskHandler {
 | 
			
		||||
                        base_effect: 10,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: 10,
 | 
			
		||||
                        message: Box::new(|_item| {
 | 
			
		||||
                            (
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                            )
 | 
			
		||||
                        }),
 | 
			
		||||
                        message: Box::new(|_item| "That feels better".to_owned()),
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 10,
 | 
			
		||||
                        base_effect: 9,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: 10,
 | 
			
		||||
                        message: Box::new(|_item| {
 | 
			
		||||
                            (
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                            )
 | 
			
		||||
                        }),
 | 
			
		||||
                        message: Box::new(|_item| "That feels better".to_owned()),
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 20,
 | 
			
		||||
                        base_effect: 8,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: 10,
 | 
			
		||||
                        message: Box::new(|_item| {
 | 
			
		||||
                            (
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                            )
 | 
			
		||||
                        }),
 | 
			
		||||
                        message: Box::new(|_item| "That feels better".to_owned()),
 | 
			
		||||
                    },
 | 
			
		||||
                    Effect::ChangeTargetHealth {
 | 
			
		||||
                        delay_secs: 30,
 | 
			
		||||
                        base_effect: 7,
 | 
			
		||||
                        skill_multiplier: 0.0,
 | 
			
		||||
                        max_effect: 10,
 | 
			
		||||
                        message: Box::new(|_item| {
 | 
			
		||||
                            (
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                                "That feels better".to_owned(),
 | 
			
		||||
                            )
 | 
			
		||||
                        }),
 | 
			
		||||
                        message: Box::new(|_item| "That feels better".to_owned()),
 | 
			
		||||
                    },
 | 
			
		||||
                ],
 | 
			
		||||
            },
 | 
			
		||||
 | 
			
		||||
		Loading…
	
		Reference in New Issue
	
	Block a user