mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Implement MR!1043 changes suggested by Imbris
This commit is contained in:
parent
34acc4ddf3
commit
b7d7696d89
@ -1034,7 +1034,7 @@ impl Client {
|
||||
};
|
||||
let message_format = |uid, message, group| {
|
||||
if let Some(group) = group {
|
||||
format!("{{{}}} [{}]: {}", group, alias_of_uid(uid), message)
|
||||
format!("({}) [{}]: {}", group, alias_of_uid(uid), message)
|
||||
} else {
|
||||
format!("[{}]: {}", alias_of_uid(uid), message)
|
||||
}
|
||||
|
@ -96,10 +96,10 @@ impl ChatMsg {
|
||||
pub fn to_bubble(&self) -> Option<(SpeechBubble, Uid)> {
|
||||
let icon = self.icon();
|
||||
if let ChatType::Npc(from, r) = self.chat_type {
|
||||
Some((SpeechBubble::npc_new(self.message.clone(), r, icon), from))
|
||||
Some((SpeechBubble::npc_new(&self.message, r, icon), from))
|
||||
} else {
|
||||
self.uid()
|
||||
.map(|from| (SpeechBubble::player_new(self.message.clone(), icon), from))
|
||||
.map(|from| (SpeechBubble::player_new(&self.message, icon), from))
|
||||
}
|
||||
}
|
||||
|
||||
@ -194,8 +194,8 @@ impl SpeechBubble {
|
||||
/// Default duration in seconds of speech bubbles
|
||||
pub const DEFAULT_DURATION: f64 = 5.0;
|
||||
|
||||
pub fn npc_new(i18n_key: String, r: u16, icon: SpeechBubbleIcon) -> Self {
|
||||
let message = SpeechBubbleMessage::Localized(i18n_key, r);
|
||||
pub fn npc_new(i18n_key: &str, r: u16, icon: SpeechBubbleIcon) -> Self {
|
||||
let message = SpeechBubbleMessage::Localized(i18n_key.to_string(), r);
|
||||
let timeout = Instant::now() + Duration::from_secs_f64(SpeechBubble::DEFAULT_DURATION);
|
||||
Self {
|
||||
message,
|
||||
@ -204,8 +204,8 @@ impl SpeechBubble {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn player_new(message: String, icon: SpeechBubbleIcon) -> Self {
|
||||
let message = SpeechBubbleMessage::Plain(message);
|
||||
pub fn player_new(message: &str, icon: SpeechBubbleIcon) -> Self {
|
||||
let message = SpeechBubbleMessage::Plain(message.to_string());
|
||||
let timeout = Instant::now() + Duration::from_secs_f64(SpeechBubble::DEFAULT_DURATION);
|
||||
Self {
|
||||
message,
|
||||
@ -216,11 +216,11 @@ impl SpeechBubble {
|
||||
|
||||
pub fn message<F>(&self, i18n_variation: F) -> String
|
||||
where
|
||||
F: Fn(String, u16) -> String,
|
||||
F: Fn(&str, u16) -> String,
|
||||
{
|
||||
match &self.message {
|
||||
SpeechBubbleMessage::Plain(m) => m.to_string(),
|
||||
SpeechBubbleMessage::Localized(k, i) => i18n_variation(k.to_string(), *i).to_string(),
|
||||
SpeechBubbleMessage::Localized(k, i) => i18n_variation(&k, *i).to_string(),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -119,7 +119,7 @@ pub enum ServerEvent {
|
||||
ClientDisconnect(EcsEntity),
|
||||
ChunkRequest(EcsEntity, Vec2<i32>),
|
||||
ChatCmd(EcsEntity, String),
|
||||
/// Send a chat message from an npc to the player
|
||||
/// Send a chat message to the player from an npc or other player
|
||||
Chat(comp::ChatMsg),
|
||||
}
|
||||
|
||||
|
@ -392,12 +392,11 @@ fn handle_alias(
|
||||
action: &ChatCommand,
|
||||
) {
|
||||
if client != target {
|
||||
// Prevent people abusing /sudo
|
||||
// Notify target that an admin changed the alias due to /sudo
|
||||
server.notify_client(
|
||||
client,
|
||||
ServerMsg::private(String::from("Don't call people names. It's mean.")),
|
||||
target,
|
||||
ServerMsg::private(String::from("An admin changed your alias.")),
|
||||
);
|
||||
return;
|
||||
}
|
||||
if let Ok(alias) = scan_fmt!(&args, &action.arg_fmt(), String) {
|
||||
if !comp::Player::alias_is_valid(&alias) {
|
||||
@ -1284,7 +1283,7 @@ fn handle_join_group(
|
||||
// TODO notify group
|
||||
server.notify_client(
|
||||
client,
|
||||
ServerMsg::private(format!("Joined group {{{}}}", group)),
|
||||
ServerMsg::private(format!("Joined group ({})", group)),
|
||||
);
|
||||
} else {
|
||||
let mode = comp::ChatMode::default();
|
||||
@ -1293,7 +1292,7 @@ fn handle_join_group(
|
||||
// TODO notify group
|
||||
server.notify_client(
|
||||
client,
|
||||
ServerMsg::private(format!("Left group {{{}}}", group)),
|
||||
ServerMsg::private(format!("Left group ({})", group)),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -115,7 +115,6 @@ impl Server {
|
||||
state.ecs_mut().insert(sys::TerrainTimer::default());
|
||||
state.ecs_mut().insert(sys::WaypointTimer::default());
|
||||
state.ecs_mut().insert(sys::PersistenceTimer::default());
|
||||
//state.ecs_mut().insert(sys::StatsPersistenceTimer::default());
|
||||
|
||||
// System schedulers to control execution of systems
|
||||
state
|
||||
|
@ -244,13 +244,8 @@ impl StateExt for State {
|
||||
/// by location. Faction and group are limited by component.
|
||||
fn send_chat(&self, msg: comp::ChatMsg) {
|
||||
let ecs = self.ecs();
|
||||
let is_within = |target, a: &comp::Pos, b_opt: Option<&comp::Pos>| {
|
||||
if let Some(b) = b_opt {
|
||||
a.0.distance(b.0) < target
|
||||
} else {
|
||||
false
|
||||
}
|
||||
};
|
||||
let is_within =
|
||||
|target, a: &comp::Pos, b: &comp::Pos| a.0.distance_squared(b.0) < target * target;
|
||||
match &msg.chat_type {
|
||||
comp::ChatType::Broadcast
|
||||
| comp::ChatType::Kill
|
||||
@ -271,54 +266,39 @@ impl StateExt for State {
|
||||
}
|
||||
},
|
||||
|
||||
comp::ChatType::Say(_u) => {
|
||||
for (client, pos) in (
|
||||
&mut ecs.write_storage::<Client>(),
|
||||
&ecs.read_storage::<comp::Pos>(),
|
||||
)
|
||||
.join()
|
||||
{
|
||||
let entity_opt = msg.uid().and_then(|uid| {
|
||||
(*ecs.read_resource::<UidAllocator>()).retrieve_entity_internal(uid.0)
|
||||
});
|
||||
let positions = ecs.read_storage::<comp::Pos>();
|
||||
let pos_opt = entity_opt.and_then(|e| positions.get(e));
|
||||
if is_within(comp::ChatMsg::SAY_DISTANCE, pos, pos_opt) {
|
||||
client.notify(ServerMsg::ChatMsg(msg.clone()));
|
||||
comp::ChatType::Say(uid) => {
|
||||
let entity_opt =
|
||||
(*ecs.read_resource::<UidAllocator>()).retrieve_entity_internal(uid.0);
|
||||
let positions = ecs.read_storage::<comp::Pos>();
|
||||
if let Some(speaker_pos) = entity_opt.and_then(|e| positions.get(e)) {
|
||||
for (client, pos) in (&mut ecs.write_storage::<Client>(), &positions).join() {
|
||||
if is_within(comp::ChatMsg::SAY_DISTANCE, pos, speaker_pos) {
|
||||
client.notify(ServerMsg::ChatMsg(msg.clone()));
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
comp::ChatType::Region(_u) => {
|
||||
for (client, pos) in (
|
||||
&mut ecs.write_storage::<Client>(),
|
||||
&ecs.read_storage::<comp::Pos>(),
|
||||
)
|
||||
.join()
|
||||
{
|
||||
let entity_opt = msg.uid().and_then(|uid| {
|
||||
(*ecs.read_resource::<UidAllocator>()).retrieve_entity_internal(uid.0)
|
||||
});
|
||||
let positions = ecs.read_storage::<comp::Pos>();
|
||||
let pos_opt = entity_opt.and_then(|e| positions.get(e));
|
||||
if is_within(comp::ChatMsg::REGION_DISTANCE, pos, pos_opt) {
|
||||
client.notify(ServerMsg::ChatMsg(msg.clone()));
|
||||
comp::ChatType::Region(uid) => {
|
||||
let entity_opt =
|
||||
(*ecs.read_resource::<UidAllocator>()).retrieve_entity_internal(uid.0);
|
||||
let positions = ecs.read_storage::<comp::Pos>();
|
||||
if let Some(speaker_pos) = entity_opt.and_then(|e| positions.get(e)) {
|
||||
for (client, pos) in (&mut ecs.write_storage::<Client>(), &positions).join() {
|
||||
if is_within(comp::ChatMsg::REGION_DISTANCE, pos, speaker_pos) {
|
||||
client.notify(ServerMsg::ChatMsg(msg.clone()));
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
comp::ChatType::Npc(_u, _r) => {
|
||||
for (client, pos) in (
|
||||
&mut ecs.write_storage::<Client>(),
|
||||
&ecs.read_storage::<comp::Pos>(),
|
||||
)
|
||||
.join()
|
||||
{
|
||||
let entity_opt = msg.uid().and_then(|uid| {
|
||||
(*ecs.read_resource::<UidAllocator>()).retrieve_entity_internal(uid.0)
|
||||
});
|
||||
let positions = ecs.read_storage::<comp::Pos>();
|
||||
let pos_opt = entity_opt.and_then(|e| positions.get(e));
|
||||
if is_within(comp::ChatMsg::NPC_DISTANCE, pos, pos_opt) {
|
||||
client.notify(ServerMsg::ChatMsg(msg.clone()));
|
||||
comp::ChatType::Npc(uid, _r) => {
|
||||
let entity_opt =
|
||||
(*ecs.read_resource::<UidAllocator>()).retrieve_entity_internal(uid.0);
|
||||
let positions = ecs.read_storage::<comp::Pos>();
|
||||
if let Some(speaker_pos) = entity_opt.and_then(|e| positions.get(e)) {
|
||||
for (client, pos) in (&mut ecs.write_storage::<Client>(), &positions).join() {
|
||||
if is_within(comp::ChatMsg::NPC_DISTANCE, pos, speaker_pos) {
|
||||
client.notify(ServerMsg::ChatMsg(msg.clone()));
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
|
@ -337,10 +337,7 @@ impl<'a> System<'a> for Sys {
|
||||
| ClientState::Character => match validate_chat_msg(&message) {
|
||||
Ok(()) => {
|
||||
if let Some(from) = uids.get(entity) {
|
||||
let mode = chat_modes
|
||||
.get(entity)
|
||||
.map(Clone::clone)
|
||||
.unwrap_or(ChatMode::default());
|
||||
let mode = chat_modes.get(entity).cloned().unwrap_or_default();
|
||||
let msg = mode.new_message(*from, message);
|
||||
new_chat_msgs.push((Some(entity), msg));
|
||||
} else {
|
||||
|
@ -22,8 +22,6 @@ pub type TerrainSyncTimer = SysTimer<terrain_sync::Sys>;
|
||||
pub type WaypointTimer = SysTimer<waypoint::Sys>;
|
||||
pub type PersistenceTimer = SysTimer<persistence::Sys>;
|
||||
pub type PersistenceScheduler = SysScheduler<persistence::Sys>;
|
||||
//pub type StatsPersistenceTimer = SysTimer<persistence::stats::Sys>;
|
||||
//pub type StatsPersistenceScheduler = SysScheduler<persistence::stats::Sys>;
|
||||
|
||||
// System names
|
||||
// Note: commented names may be useful in the future
|
||||
@ -34,14 +32,11 @@ pub type PersistenceScheduler = SysScheduler<persistence::Sys>;
|
||||
const TERRAIN_SYS: &str = "server_terrain_sys";
|
||||
const WAYPOINT_SYS: &str = "waypoint_sys";
|
||||
const PERSISTENCE_SYS: &str = "persistence_sys";
|
||||
//const STATS_PERSISTENCE_SYS: &str = "stats_persistence_sys";
|
||||
|
||||
pub fn add_server_systems(dispatch_builder: &mut DispatcherBuilder) {
|
||||
dispatch_builder.add(terrain::Sys, TERRAIN_SYS, &[]);
|
||||
dispatch_builder.add(waypoint::Sys, WAYPOINT_SYS, &[]);
|
||||
dispatch_builder.add(persistence::Sys, PERSISTENCE_SYS, &[]);
|
||||
//dispatch_builder.add(persistence::stats::Sys, STATS_PERSISTENCE_SYS,
|
||||
// &[]);
|
||||
}
|
||||
|
||||
pub fn run_sync_systems(ecs: &mut specs::World) {
|
||||
|
@ -163,17 +163,7 @@ impl<'a> Widget for Chat<'a> {
|
||||
let transp = self.global_state.settings.gameplay.chat_transp;
|
||||
// Maintain scrolling.
|
||||
if !self.new_messages.is_empty() {
|
||||
state.update(|s| {
|
||||
s.messages.extend(
|
||||
self.new_messages
|
||||
.drain(..)
|
||||
.map(|msg| {
|
||||
// TODO format!([{}] {}, name, msg)
|
||||
msg
|
||||
})
|
||||
.collect::<Vec<_>>(),
|
||||
)
|
||||
});
|
||||
state.update(|s| s.messages.extend(self.new_messages.drain(..)));
|
||||
ui.scroll_widget(state.ids.message_box, [0.0, std::f64::MAX]);
|
||||
}
|
||||
|
||||
@ -354,8 +344,7 @@ impl<'a> Widget for Chat<'a> {
|
||||
Dimension::Absolute(y) => y + 2.0,
|
||||
_ => 0.0,
|
||||
};
|
||||
let widget = text.h(y);
|
||||
item.set(widget, ui);
|
||||
item.set(text.h(y), ui);
|
||||
let icon_id = state.ids.chat_icons[item.i];
|
||||
Image::new(icon)
|
||||
.w_h(16.0, 16.0)
|
||||
@ -365,11 +354,13 @@ impl<'a> Widget for Chat<'a> {
|
||||
} else {
|
||||
// Spacer at bottom of the last message so that it is not cut off.
|
||||
// Needs to be larger than the space above.
|
||||
let widget = Text::new("")
|
||||
.font_size(self.fonts.opensans.scale(6))
|
||||
.font_id(self.fonts.opensans.conrod_id)
|
||||
.w(CHAT_BOX_WIDTH);
|
||||
item.set(widget, ui);
|
||||
item.set(
|
||||
Text::new("")
|
||||
.font_size(self.fonts.opensans.scale(6))
|
||||
.font_id(self.fonts.opensans.conrod_id)
|
||||
.w(CHAT_BOX_WIDTH),
|
||||
ui,
|
||||
);
|
||||
};
|
||||
}
|
||||
|
||||
@ -432,7 +423,6 @@ fn do_tab_completion(cursor: usize, input: &str, word: &str) -> (String, usize)
|
||||
if char_i < cursor {
|
||||
pre_ws = Some(byte_i);
|
||||
} else {
|
||||
assert_eq!(post_ws, None); // TODO debug
|
||||
post_ws = Some(byte_i);
|
||||
break;
|
||||
}
|
||||
|
@ -940,8 +940,9 @@ impl Hud {
|
||||
}
|
||||
|
||||
// Pop speech bubbles
|
||||
let now = Instant::now();
|
||||
self.speech_bubbles
|
||||
.retain(|_uid, bubble| bubble.timeout > Instant::now());
|
||||
.retain(|_uid, bubble| bubble.timeout > now);
|
||||
|
||||
// Push speech bubbles
|
||||
for msg in self.new_messages.iter() {
|
||||
@ -1570,13 +1571,8 @@ impl Hud {
|
||||
}
|
||||
|
||||
// Don't put NPC messages in chat box.
|
||||
self.new_messages.retain(|m| {
|
||||
if let comp::ChatType::Npc(_, _) = m.chat_type {
|
||||
false
|
||||
} else {
|
||||
true
|
||||
}
|
||||
});
|
||||
self.new_messages
|
||||
.retain(|m| !matches!(m.chat_type, comp::ChatType::Npc(_, _)));
|
||||
|
||||
// Chat box
|
||||
match Chat::new(
|
||||
|
@ -148,7 +148,7 @@ impl<'a> Widget for Overhead<'a> {
|
||||
if let Some(bubble) = self.bubble {
|
||||
let dark_mode = self.settings.speech_bubble_dark_mode;
|
||||
let localizer =
|
||||
|s: String, i| -> String { self.voxygen_i18n.get_variation(&s, i).to_string() };
|
||||
|s: &str, i| -> String { self.voxygen_i18n.get_variation(&s, i).to_string() };
|
||||
let bubble_contents: String = bubble.message(localizer);
|
||||
|
||||
let mut text = Text::new(&bubble_contents)
|
||||
|
Loading…
Reference in New Issue
Block a user