mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
remove hardcoded localisation from client
This commit is contained in:
parent
46cd112928
commit
a0ef3be9ac
@ -21,7 +21,7 @@ use common::{
|
||||
character::{CharacterId, CharacterItem},
|
||||
comp::{
|
||||
self,
|
||||
chat::{KillSource, KillType},
|
||||
chat::KillSource,
|
||||
controller::CraftEvent,
|
||||
group,
|
||||
inventory::item::{modular, tool, ItemKind},
|
||||
@ -56,9 +56,9 @@ use common_net::{
|
||||
msg::{
|
||||
self,
|
||||
world_msg::{EconomyInfo, PoiInfo, SiteId, SiteInfo},
|
||||
ClientGeneral, ClientMsg, ClientRegister, ClientType, DisconnectReason, InviteAnswer,
|
||||
Notification, PingMsg, PlayerInfo, PlayerListUpdate, PresenceKind, RegisterError,
|
||||
ServerGeneral, ServerInit, ServerRegisterAnswer,
|
||||
ChatTypeContext, ClientGeneral, ClientMsg, ClientRegister, ClientType, DisconnectReason,
|
||||
InviteAnswer, Notification, PingMsg, PlayerInfo, PlayerListUpdate, PresenceKind,
|
||||
RegisterError, ServerGeneral, ServerInit, ServerRegisterAnswer,
|
||||
},
|
||||
sync::WorldSyncExt,
|
||||
};
|
||||
@ -2641,11 +2641,11 @@ impl Client {
|
||||
}
|
||||
}
|
||||
|
||||
/// Format a message for the client (voxygen chat box or chat-cli)
|
||||
pub fn format_message(&self, msg: &comp::ChatMsg, character_name: bool) -> String {
|
||||
let comp::ChatMsg {
|
||||
chat_type, message, ..
|
||||
} = &msg;
|
||||
/// Get important information from client that is necessary for message
|
||||
/// localisation
|
||||
pub fn lockup_msg_context(&self, msg: &comp::ChatMsg) -> HashMap<&str, ChatTypeContext> {
|
||||
let mut result = HashMap::new();
|
||||
let comp::ChatMsg { chat_type, .. } = &msg;
|
||||
let name_of_uid = |uid| {
|
||||
let ecs = self.state.ecs();
|
||||
(
|
||||
@ -2658,190 +2658,59 @@ impl Client {
|
||||
};
|
||||
let alias_of_uid = |uid| {
|
||||
self.player_list.get(uid).map_or(
|
||||
name_of_uid(uid).unwrap_or_else(|| "<?>".to_string()),
|
||||
|player_info| {
|
||||
if player_info.is_moderator {
|
||||
format!(
|
||||
"MOD - {}",
|
||||
self.personalize_alias(*uid, player_info.player_alias.clone())
|
||||
)
|
||||
} else {
|
||||
self.personalize_alias(*uid, player_info.player_alias.clone())
|
||||
}
|
||||
ChatTypeContext::Raw(name_of_uid(uid).unwrap_or_else(|| "<?>".to_string())),
|
||||
|player_info| ChatTypeContext::PlayerAlias {
|
||||
you: self.uid().expect("Client doesn't have a Uid!!!") == *uid,
|
||||
info: player_info.clone(),
|
||||
},
|
||||
)
|
||||
};
|
||||
let message_format = |uid, message, group| {
|
||||
let alias = alias_of_uid(uid);
|
||||
let name = if character_name {
|
||||
name_of_uid(uid)
|
||||
} else {
|
||||
None
|
||||
};
|
||||
match (group, name) {
|
||||
(Some(group), None) => format!("({}) [{}]: {}", group, alias, message),
|
||||
(None, None) => format!("[{}]: {}", alias, message),
|
||||
(Some(group), Some(name)) => {
|
||||
format!("({}) [{}] {}: {}", group, alias, name, message)
|
||||
},
|
||||
(None, Some(name)) => format!("[{}] {}: {}", alias, name, message),
|
||||
}
|
||||
};
|
||||
match chat_type {
|
||||
// For ChatType::{Online, Offline, Kill} these message strings are localized
|
||||
// in voxygen/src/hud/chat.rs before being formatted here.
|
||||
// Kill messages are generated in server/src/events/entity_manipulation.rs
|
||||
// fn handle_destroy
|
||||
comp::ChatType::Online(uid) => {
|
||||
// Default message formats if no localized message string is set by hud
|
||||
// Needed for cli clients that don't set localization info
|
||||
if message.is_empty() {
|
||||
format!("[{}] came online", alias_of_uid(uid))
|
||||
} else {
|
||||
message.replace("{name}", &alias_of_uid(uid))
|
||||
}
|
||||
comp::ChatType::Online(uid) | comp::ChatType::Offline(uid) => {
|
||||
result.insert("player", alias_of_uid(uid));
|
||||
},
|
||||
comp::ChatType::Offline(uid) => {
|
||||
// Default message formats if no localized message string is set by hud
|
||||
// Needed for cli clients that don't set localization info
|
||||
if message.is_empty() {
|
||||
format!("[{}] went offline", alias_of_uid(uid))
|
||||
} else {
|
||||
message.replace("{name}", &alias_of_uid(uid))
|
||||
}
|
||||
},
|
||||
comp::ChatType::CommandError => message.to_string(),
|
||||
comp::ChatType::CommandInfo => message.to_string(),
|
||||
comp::ChatType::FactionMeta(_) => message.to_string(),
|
||||
comp::ChatType::GroupMeta(_) => message.to_string(),
|
||||
comp::ChatType::CommandError => (),
|
||||
comp::ChatType::CommandInfo => (),
|
||||
comp::ChatType::FactionMeta(_) => (),
|
||||
comp::ChatType::GroupMeta(_) => (),
|
||||
comp::ChatType::Kill(kill_source, victim) => {
|
||||
// Default message formats if no localized message string is set by hud
|
||||
// Needed for cli clients that don't set localization info
|
||||
if message.is_empty() {
|
||||
match kill_source {
|
||||
KillSource::Player(attacker_uid, KillType::Buff(buff_kind)) => format!(
|
||||
"[{}] died of {} caused by [{}]",
|
||||
alias_of_uid(victim),
|
||||
format!("{:?}", buff_kind).to_lowercase().as_str(),
|
||||
alias_of_uid(attacker_uid)
|
||||
),
|
||||
KillSource::Player(attacker_uid, KillType::Melee) => format!(
|
||||
"[{}] killed [{}]",
|
||||
alias_of_uid(attacker_uid),
|
||||
alias_of_uid(victim)
|
||||
),
|
||||
KillSource::Player(attacker_uid, KillType::Projectile) => format!(
|
||||
"[{}] shot [{}]",
|
||||
alias_of_uid(attacker_uid),
|
||||
alias_of_uid(victim)
|
||||
),
|
||||
KillSource::Player(attacker_uid, KillType::Explosion) => format!(
|
||||
"[{}] blew up [{}]",
|
||||
alias_of_uid(attacker_uid),
|
||||
alias_of_uid(victim)
|
||||
),
|
||||
KillSource::Player(attacker_uid, KillType::Energy) => format!(
|
||||
"[{}] used magic to kill [{}]",
|
||||
alias_of_uid(attacker_uid),
|
||||
alias_of_uid(victim)
|
||||
),
|
||||
KillSource::Player(attacker_uid, KillType::Other) => format!(
|
||||
"[{}] killed [{}]",
|
||||
alias_of_uid(attacker_uid),
|
||||
alias_of_uid(victim)
|
||||
),
|
||||
KillSource::NonExistent(KillType::Buff(buff_kind)) => format!(
|
||||
"[{}] died of {}",
|
||||
alias_of_uid(victim),
|
||||
format!("{:?}", buff_kind).to_lowercase().as_str()
|
||||
),
|
||||
KillSource::NonPlayer(attacker_name, KillType::Buff(buff_kind)) => format!(
|
||||
"[{}] died of {} caused by {}",
|
||||
alias_of_uid(victim),
|
||||
format!("{:?}", buff_kind).to_lowercase().as_str(),
|
||||
attacker_name
|
||||
),
|
||||
KillSource::NonPlayer(attacker_name, KillType::Melee) => {
|
||||
format!("{} killed [{}]", attacker_name, alias_of_uid(victim))
|
||||
},
|
||||
KillSource::NonPlayer(attacker_name, KillType::Projectile) => {
|
||||
format!("{} shot [{}]", attacker_name, alias_of_uid(victim))
|
||||
},
|
||||
KillSource::NonPlayer(attacker_name, KillType::Explosion) => {
|
||||
format!("{} blew up [{}]", attacker_name, alias_of_uid(victim))
|
||||
},
|
||||
KillSource::NonPlayer(attacker_name, KillType::Energy) => format!(
|
||||
"{} used magic to kill [{}]",
|
||||
attacker_name,
|
||||
alias_of_uid(victim)
|
||||
),
|
||||
KillSource::NonPlayer(attacker_name, KillType::Other) => {
|
||||
format!("{} killed [{}]", attacker_name, alias_of_uid(victim))
|
||||
},
|
||||
KillSource::Environment(environment) => {
|
||||
format!("[{}] died in {}", alias_of_uid(victim), environment)
|
||||
},
|
||||
KillSource::FallDamage => {
|
||||
format!("[{}] died from fall damage", alias_of_uid(victim))
|
||||
},
|
||||
KillSource::Suicide => {
|
||||
format!("[{}] died from self-inflicted wounds", alias_of_uid(victim))
|
||||
},
|
||||
KillSource::NonExistent(_) => format!("[{}] died", alias_of_uid(victim)),
|
||||
KillSource::Other => format!("[{}] died", alias_of_uid(victim)),
|
||||
}
|
||||
} else {
|
||||
match kill_source {
|
||||
KillSource::Player(attacker_uid, _) => message
|
||||
.replace("{attacker}", &alias_of_uid(attacker_uid))
|
||||
.replace("{victim}", &alias_of_uid(victim)),
|
||||
KillSource::NonExistent(KillType::Buff(_)) => {
|
||||
message.replace("{victim}", &alias_of_uid(victim))
|
||||
},
|
||||
KillSource::NonPlayer(attacker_name, _) => message
|
||||
.replace("{attacker}", attacker_name)
|
||||
.replace("{victim}", &alias_of_uid(victim)),
|
||||
KillSource::Environment(environment) => message
|
||||
.replace("{name}", &alias_of_uid(victim))
|
||||
.replace("{environment}", environment),
|
||||
KillSource::FallDamage => message.replace("{name}", &alias_of_uid(victim)),
|
||||
KillSource::Suicide => message.replace("{name}", &alias_of_uid(victim)),
|
||||
KillSource::NonExistent(_) => {
|
||||
message.replace("{name}", &alias_of_uid(victim))
|
||||
},
|
||||
KillSource::Other => message.replace("{name}", &alias_of_uid(victim)),
|
||||
}
|
||||
}
|
||||
result.insert("victim", alias_of_uid(victim));
|
||||
match kill_source {
|
||||
KillSource::Player(attacker_uid, _) => {
|
||||
result.insert("attacker", alias_of_uid(attacker_uid));
|
||||
},
|
||||
KillSource::NonPlayer(attacker_name, _) => {
|
||||
result.insert("attacker_name", ChatTypeContext::Raw(attacker_name.clone()));
|
||||
},
|
||||
KillSource::Environment(environment) => {
|
||||
result.insert("environment", ChatTypeContext::Raw(environment.clone()));
|
||||
},
|
||||
KillSource::FallDamage => (),
|
||||
KillSource::Suicide => (),
|
||||
KillSource::NonExistent(_) => (),
|
||||
KillSource::Other => (),
|
||||
};
|
||||
},
|
||||
comp::ChatType::Tell(from, to) => {
|
||||
let from_alias = alias_of_uid(from);
|
||||
let to_alias = alias_of_uid(to);
|
||||
if Some(*from) == self.uid() {
|
||||
format!("To [{}]: {}", to_alias, message)
|
||||
} else {
|
||||
format!("From [{}]: {}", from_alias, message)
|
||||
}
|
||||
comp::ChatType::Tell(from, to) | comp::ChatType::NpcTell(from, to, _) => {
|
||||
result.insert("from", alias_of_uid(from));
|
||||
result.insert("to", alias_of_uid(to));
|
||||
},
|
||||
comp::ChatType::Say(uid)
|
||||
| comp::ChatType::Region(uid)
|
||||
| comp::ChatType::World(uid)
|
||||
| comp::ChatType::NpcSay(uid, _) => {
|
||||
result.insert("from", alias_of_uid(uid));
|
||||
},
|
||||
comp::ChatType::Group(uid, s) | comp::ChatType::Faction(uid, s) => {
|
||||
result.insert("from", alias_of_uid(uid));
|
||||
result.insert("group_name", ChatTypeContext::Raw(s.clone()));
|
||||
},
|
||||
comp::ChatType::Say(uid) => message_format(uid, message, None),
|
||||
comp::ChatType::Group(uid, s) => message_format(uid, message, Some(s)),
|
||||
comp::ChatType::Faction(uid, s) => message_format(uid, message, Some(s)),
|
||||
comp::ChatType::Region(uid) => message_format(uid, message, None),
|
||||
comp::ChatType::World(uid) => message_format(uid, message, None),
|
||||
// NPCs can't talk. Should be filtered by hud/mod.rs for voxygen and should be filtered
|
||||
// by server (due to not having a Pos) for chat-cli
|
||||
comp::ChatType::Npc(_uid, _r) => "".to_string(),
|
||||
comp::ChatType::NpcSay(uid, _r) => message_format(uid, message, None),
|
||||
comp::ChatType::NpcTell(from, to, _r) => {
|
||||
let from_alias = alias_of_uid(from);
|
||||
let to_alias = alias_of_uid(to);
|
||||
if Some(*from) == self.uid() {
|
||||
format!("To [{}]: {}", to_alias, message)
|
||||
} else {
|
||||
format!("From [{}]: {}", from_alias, message)
|
||||
}
|
||||
},
|
||||
comp::ChatType::Meta => message.to_string(),
|
||||
}
|
||||
comp::ChatType::Npc(_uid, _r) => (),
|
||||
comp::ChatType::Meta => (),
|
||||
};
|
||||
result
|
||||
}
|
||||
|
||||
/// Execute a single client tick:
|
||||
|
@ -13,9 +13,9 @@ pub use self::{
|
||||
},
|
||||
ecs_packet::EcsCompPacket,
|
||||
server::{
|
||||
CharacterInfo, DisconnectReason, InviteAnswer, Notification, PlayerInfo, PlayerListUpdate,
|
||||
RegisterError, SerializedTerrainChunk, ServerGeneral, ServerInfo, ServerInit, ServerMsg,
|
||||
ServerRegisterAnswer,
|
||||
CharacterInfo, ChatTypeContext, DisconnectReason, InviteAnswer, Notification, PlayerInfo,
|
||||
PlayerListUpdate, RegisterError, SerializedTerrainChunk, ServerGeneral, ServerInfo,
|
||||
ServerInit, ServerMsg, ServerRegisterAnswer,
|
||||
},
|
||||
world_msg::WorldMapMsg,
|
||||
};
|
||||
|
@ -245,6 +245,13 @@ pub struct PlayerInfo {
|
||||
pub uuid: Uuid,
|
||||
}
|
||||
|
||||
/// used for localisation, filled by client and used by i18n code
|
||||
#[derive(Clone)]
|
||||
pub enum ChatTypeContext {
|
||||
PlayerAlias { you: bool, info: PlayerInfo },
|
||||
Raw(String),
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||
pub struct CharacterInfo {
|
||||
pub name: String,
|
||||
|
@ -9,6 +9,7 @@ use common::comp::{
|
||||
group::Role,
|
||||
BuffKind, ChatMode, ChatMsg, ChatType,
|
||||
};
|
||||
use common_net::msg::{ChatTypeContext, PlayerInfo};
|
||||
use conrod_core::{
|
||||
color,
|
||||
input::Key,
|
||||
@ -422,39 +423,12 @@ impl<'a> Widget for Chat<'a> {
|
||||
.messages
|
||||
.iter()
|
||||
.map(|m| {
|
||||
let mut message = m.clone();
|
||||
if let Some(template_key) = get_chat_template_key(&message.chat_type) {
|
||||
// FIXME (i18n death messages):
|
||||
// Death message is half localized in voxygen, half in client.
|
||||
// Make this not.
|
||||
message.message = self
|
||||
.localized_strings
|
||||
.get_msg_ctx(template_key, &i18n::fluent_args! {
|
||||
"attacker" => "{attacker}",
|
||||
"name" => "{name}",
|
||||
"died_of_buff" => "{died_of_buff}",
|
||||
"victim" => "{victim}",
|
||||
"environment" => "{environment}",
|
||||
})
|
||||
.into_owned();
|
||||
|
||||
if let ChatType::Kill(kill_source, _) = &message.chat_type {
|
||||
match kill_source {
|
||||
KillSource::Player(_, KillType::Buff(buffkind))
|
||||
| KillSource::NonExistent(KillType::Buff(buffkind))
|
||||
| KillSource::NonPlayer(_, KillType::Buff(buffkind)) => {
|
||||
message.message = insert_killing_buff(
|
||||
*buffkind,
|
||||
self.localized_strings,
|
||||
&message.message,
|
||||
);
|
||||
},
|
||||
_ => {},
|
||||
}
|
||||
}
|
||||
}
|
||||
message.message = self.client.format_message(&message, show_char_name);
|
||||
message
|
||||
internationalisate_chat_message(
|
||||
m.clone(),
|
||||
&self.client,
|
||||
&self.localized_strings,
|
||||
show_char_name,
|
||||
)
|
||||
})
|
||||
.filter(|m| {
|
||||
if let Some(chat_tab) = current_chat_tab {
|
||||
@ -688,6 +662,80 @@ impl<'a> Widget for Chat<'a> {
|
||||
}
|
||||
}
|
||||
|
||||
fn internationalisate_chat_message(
|
||||
mut msg: ChatMsg,
|
||||
client: &Client,
|
||||
localized_strings: &Localization,
|
||||
show_char_name: bool,
|
||||
) -> ChatMsg {
|
||||
if let Some(template_key) = get_chat_template_key(&msg.chat_type) {
|
||||
// FIXME (i18n death messages):
|
||||
// Death message is half localized in voxygen, half in client.
|
||||
// Make this not.
|
||||
msg.message = localized_strings
|
||||
.get_msg_ctx(template_key, &i18n::fluent_args! {
|
||||
"attacker" => "{attacker}",
|
||||
"name" => "{name}",
|
||||
"died_of_buff" => "{died_of_buff}",
|
||||
"victim" => "{victim}",
|
||||
"environment" => "{environment}",
|
||||
})
|
||||
.into_owned();
|
||||
|
||||
if let ChatType::Kill(kill_source, _) = &msg.chat_type {
|
||||
match kill_source {
|
||||
KillSource::Player(_, KillType::Buff(buffkind))
|
||||
| KillSource::NonExistent(KillType::Buff(buffkind))
|
||||
| KillSource::NonPlayer(_, KillType::Buff(buffkind)) => {
|
||||
msg.message = insert_killing_buff(*buffkind, localized_strings, &msg.message);
|
||||
},
|
||||
_ => {},
|
||||
}
|
||||
}
|
||||
}
|
||||
let info = client.lockup_msg_context(&msg);
|
||||
let gen_alias = |you, info: PlayerInfo| {
|
||||
let mod_str = if info.is_moderator { "MOD - " } else { "" };
|
||||
let you_str = if you { "You" } else { &info.player_alias };
|
||||
format!("{}{}", mod_str, you_str)
|
||||
};
|
||||
let message_format = |you, info: PlayerInfo, message: &str, group: Option<&String>| {
|
||||
let alias = gen_alias(you, info.clone());
|
||||
let name = if show_char_name {
|
||||
info.character.map(|c| c.name)
|
||||
} else {
|
||||
None
|
||||
};
|
||||
match (group, name) {
|
||||
(Some(group), None) => format!("({}) [{}]: {}", group, alias, message),
|
||||
(None, None) => format!("[{}]: {}", alias, message),
|
||||
(Some(group), Some(name)) => {
|
||||
format!("({}) [{}] {}: {}", group, alias, name, message)
|
||||
},
|
||||
(None, Some(name)) => format!("[{}] {}: {}", alias, name, message),
|
||||
}
|
||||
};
|
||||
if let Some(ChatTypeContext::PlayerAlias { you, info }) = info.get("from").cloned() {
|
||||
msg.message = match &msg.chat_type {
|
||||
ChatType::Say(_) => message_format(you, info, &msg.message, None),
|
||||
ChatType::Group(_, s) => message_format(you, info, &msg.message, Some(s)),
|
||||
ChatType::Faction(_, s) => message_format(you, info, &msg.message, Some(s)),
|
||||
ChatType::Region(_) => message_format(you, info, &msg.message, None),
|
||||
ChatType::World(_) => message_format(you, info, &msg.message, None),
|
||||
ChatType::NpcSay(_, _r) => message_format(you, info, &msg.message, None),
|
||||
_ => msg.message,
|
||||
};
|
||||
}
|
||||
for (name, datum) in info.into_iter() {
|
||||
let replacement = match datum {
|
||||
ChatTypeContext::PlayerAlias { you, info } => gen_alias(you, info),
|
||||
ChatTypeContext::Raw(text) => text,
|
||||
};
|
||||
msg.message = msg.message.replace(&format!("{{{}}}", name), &replacement);
|
||||
}
|
||||
msg
|
||||
}
|
||||
|
||||
fn do_tab_completion(cursor: usize, input: &str, word: &str) -> (String, usize) {
|
||||
let mut pre_ws = None;
|
||||
let mut post_ws = None;
|
||||
|
Loading…
Reference in New Issue
Block a user