mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Addressed further review.
This commit is contained in:
parent
dfcb8c8519
commit
a288f9ee43
@ -15,7 +15,7 @@ sum_type! {
|
|||||||
CanBuild(comp::CanBuild),
|
CanBuild(comp::CanBuild),
|
||||||
Stats(comp::Stats),
|
Stats(comp::Stats),
|
||||||
SkillSet(comp::SkillSet),
|
SkillSet(comp::SkillSet),
|
||||||
AbilityPool(comp::AbilityPool),
|
ActiveAbilities(comp::ActiveAbilities),
|
||||||
Buffs(comp::Buffs),
|
Buffs(comp::Buffs),
|
||||||
Auras(comp::Auras),
|
Auras(comp::Auras),
|
||||||
Energy(comp::Energy),
|
Energy(comp::Energy),
|
||||||
@ -51,7 +51,7 @@ sum_type! {
|
|||||||
CanBuild(PhantomData<comp::CanBuild>),
|
CanBuild(PhantomData<comp::CanBuild>),
|
||||||
Stats(PhantomData<comp::Stats>),
|
Stats(PhantomData<comp::Stats>),
|
||||||
SkillSet(PhantomData<comp::SkillSet>),
|
SkillSet(PhantomData<comp::SkillSet>),
|
||||||
AbilityPool(PhantomData<comp::AbilityPool>),
|
ActiveAbilities(PhantomData<comp::ActiveAbilities>),
|
||||||
Buffs(PhantomData<comp::Buffs>),
|
Buffs(PhantomData<comp::Buffs>),
|
||||||
Auras(PhantomData<comp::Auras>),
|
Auras(PhantomData<comp::Auras>),
|
||||||
Energy(PhantomData<comp::Energy>),
|
Energy(PhantomData<comp::Energy>),
|
||||||
@ -87,7 +87,7 @@ impl sync::CompPacket for EcsCompPacket {
|
|||||||
EcsCompPacket::CanBuild(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::CanBuild(comp) => sync::handle_insert(comp, entity, world),
|
||||||
EcsCompPacket::Stats(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::Stats(comp) => sync::handle_insert(comp, entity, world),
|
||||||
EcsCompPacket::SkillSet(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::SkillSet(comp) => sync::handle_insert(comp, entity, world),
|
||||||
EcsCompPacket::AbilityPool(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::ActiveAbilities(comp) => sync::handle_insert(comp, entity, world),
|
||||||
EcsCompPacket::Buffs(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::Buffs(comp) => sync::handle_insert(comp, entity, world),
|
||||||
EcsCompPacket::Auras(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::Auras(comp) => sync::handle_insert(comp, entity, world),
|
||||||
EcsCompPacket::Energy(comp) => sync::handle_insert(comp, entity, world),
|
EcsCompPacket::Energy(comp) => sync::handle_insert(comp, entity, world),
|
||||||
@ -127,7 +127,7 @@ impl sync::CompPacket for EcsCompPacket {
|
|||||||
EcsCompPacket::CanBuild(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::CanBuild(comp) => sync::handle_modify(comp, entity, world),
|
||||||
EcsCompPacket::Stats(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::Stats(comp) => sync::handle_modify(comp, entity, world),
|
||||||
EcsCompPacket::SkillSet(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::SkillSet(comp) => sync::handle_modify(comp, entity, world),
|
||||||
EcsCompPacket::AbilityPool(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::ActiveAbilities(comp) => sync::handle_modify(comp, entity, world),
|
||||||
EcsCompPacket::Buffs(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::Buffs(comp) => sync::handle_modify(comp, entity, world),
|
||||||
EcsCompPacket::Auras(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::Auras(comp) => sync::handle_modify(comp, entity, world),
|
||||||
EcsCompPacket::Energy(comp) => sync::handle_modify(comp, entity, world),
|
EcsCompPacket::Energy(comp) => sync::handle_modify(comp, entity, world),
|
||||||
@ -167,8 +167,8 @@ impl sync::CompPacket for EcsCompPacket {
|
|||||||
EcsCompPhantom::CanBuild(_) => sync::handle_remove::<comp::CanBuild>(entity, world),
|
EcsCompPhantom::CanBuild(_) => sync::handle_remove::<comp::CanBuild>(entity, world),
|
||||||
EcsCompPhantom::Stats(_) => sync::handle_remove::<comp::Stats>(entity, world),
|
EcsCompPhantom::Stats(_) => sync::handle_remove::<comp::Stats>(entity, world),
|
||||||
EcsCompPhantom::SkillSet(_) => sync::handle_remove::<comp::SkillSet>(entity, world),
|
EcsCompPhantom::SkillSet(_) => sync::handle_remove::<comp::SkillSet>(entity, world),
|
||||||
EcsCompPhantom::AbilityPool(_) => {
|
EcsCompPhantom::ActiveAbilities(_) => {
|
||||||
sync::handle_remove::<comp::AbilityPool>(entity, world)
|
sync::handle_remove::<comp::ActiveAbilities>(entity, world)
|
||||||
},
|
},
|
||||||
EcsCompPhantom::Buffs(_) => sync::handle_remove::<comp::Buffs>(entity, world),
|
EcsCompPhantom::Buffs(_) => sync::handle_remove::<comp::Buffs>(entity, world),
|
||||||
EcsCompPhantom::Auras(_) => sync::handle_remove::<comp::Auras>(entity, world),
|
EcsCompPhantom::Auras(_) => sync::handle_remove::<comp::Auras>(entity, world),
|
||||||
|
@ -5,7 +5,7 @@ use crate::{
|
|||||||
self, aura, beam, buff,
|
self, aura, beam, buff,
|
||||||
inventory::{
|
inventory::{
|
||||||
item::{
|
item::{
|
||||||
tool::{Stats, ToolKind},
|
tool::{AbilityItem, Stats, ToolKind},
|
||||||
ItemKind,
|
ItemKind,
|
||||||
},
|
},
|
||||||
slot::EquipSlot,
|
slot::EquipSlot,
|
||||||
@ -34,18 +34,18 @@ pub const MAX_ABILITIES: usize = 5;
|
|||||||
// set of weapons. Consider after UI is set up and people weigh in on memory
|
// set of weapons. Consider after UI is set up and people weigh in on memory
|
||||||
// considerations.
|
// considerations.
|
||||||
#[derive(Serialize, Deserialize, Debug, Clone)]
|
#[derive(Serialize, Deserialize, Debug, Clone)]
|
||||||
pub struct AbilityPool {
|
pub struct ActiveAbilities {
|
||||||
pub primary: PrimaryAbility,
|
pub primary: PrimaryAbility,
|
||||||
pub secondary: SecondaryAbility,
|
pub secondary: SecondaryAbility,
|
||||||
pub movement: MovementAbility,
|
pub movement: MovementAbility,
|
||||||
pub abilities: [AuxiliaryAbility; MAX_ABILITIES],
|
pub abilities: [AuxiliaryAbility; MAX_ABILITIES],
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Component for AbilityPool {
|
impl Component for ActiveAbilities {
|
||||||
type Storage = DerefFlaggedStorage<Self, IdvStorage<Self>>;
|
type Storage = DerefFlaggedStorage<Self, IdvStorage<Self>>;
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for AbilityPool {
|
impl Default for ActiveAbilities {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
Self {
|
Self {
|
||||||
primary: PrimaryAbility::Tool,
|
primary: PrimaryAbility::Tool,
|
||||||
@ -56,7 +56,7 @@ impl Default for AbilityPool {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AbilityPool {
|
impl ActiveAbilities {
|
||||||
pub fn new(inv: Option<&Inventory>, skill_set: Option<&SkillSet>) -> Self {
|
pub fn new(inv: Option<&Inventory>, skill_set: Option<&SkillSet>) -> Self {
|
||||||
let mut pool = Self::default();
|
let mut pool = Self::default();
|
||||||
pool.auto_update(inv, skill_set);
|
pool.auto_update(inv, skill_set);
|
||||||
@ -90,7 +90,7 @@ impl AbilityPool {
|
|||||||
input: AbilityInput,
|
input: AbilityInput,
|
||||||
inv: Option<&Inventory>,
|
inv: Option<&Inventory>,
|
||||||
skill_set: &SkillSet,
|
skill_set: &SkillSet,
|
||||||
body: &Body,
|
body: Option<&Body>,
|
||||||
// bool is from_offhand
|
// bool is from_offhand
|
||||||
) -> Option<(CharacterAbility, bool)> {
|
) -> Option<(CharacterAbility, bool)> {
|
||||||
let ability = self.get_ability(input);
|
let ability = self.get_ability(input);
|
||||||
@ -110,6 +110,10 @@ impl AbilityPool {
|
|||||||
ability.adjusted_by_skills(skill_set, tool_kind)
|
ability.adjusted_by_skills(skill_set, tool_kind)
|
||||||
};
|
};
|
||||||
|
|
||||||
|
let unwrap_ability = |(skill_req, ability): &(Option<Skill>, AbilityItem)| {
|
||||||
|
(*skill_req, ability.ability.clone())
|
||||||
|
};
|
||||||
|
|
||||||
let unlocked = |(s, a): (Option<Skill>, CharacterAbility)| {
|
let unlocked = |(s, a): (Option<Skill>, CharacterAbility)| {
|
||||||
// If there is a skill requirement and the skillset does not contain the
|
// If there is a skill requirement and the skillset does not contain the
|
||||||
// required skill, return None
|
// required skill, return None
|
||||||
@ -118,25 +122,25 @@ impl AbilityPool {
|
|||||||
|
|
||||||
match ability {
|
match ability {
|
||||||
Ability::ToolPrimary => ability_set(EquipSlot::ActiveMainhand)
|
Ability::ToolPrimary => ability_set(EquipSlot::ActiveMainhand)
|
||||||
.map(|abilities| abilities.primary.clone())
|
.map(|abilities| abilities.primary.ability.clone())
|
||||||
.map(|ability| (scale_ability(ability, EquipSlot::ActiveMainhand), false)),
|
.map(|ability| (scale_ability(ability, EquipSlot::ActiveMainhand), false)),
|
||||||
Ability::ToolSecondary => ability_set(EquipSlot::ActiveOffhand)
|
Ability::ToolSecondary => ability_set(EquipSlot::ActiveOffhand)
|
||||||
.map(|abilities| abilities.secondary.clone())
|
.map(|abilities| abilities.secondary.ability.clone())
|
||||||
.map(|ability| (scale_ability(ability, EquipSlot::ActiveOffhand), true))
|
.map(|ability| (scale_ability(ability, EquipSlot::ActiveOffhand), true))
|
||||||
.or_else(|| {
|
.or_else(|| {
|
||||||
ability_set(EquipSlot::ActiveMainhand)
|
ability_set(EquipSlot::ActiveMainhand)
|
||||||
.map(|abilities| abilities.secondary.clone())
|
.map(|abilities| abilities.secondary.ability.clone())
|
||||||
.map(|ability| (scale_ability(ability, EquipSlot::ActiveMainhand), false))
|
.map(|ability| (scale_ability(ability, EquipSlot::ActiveMainhand), false))
|
||||||
}),
|
}),
|
||||||
Ability::SpeciesMovement => matches!(body, Body::Humanoid(_))
|
Ability::SpeciesMovement => matches!(body, Some(Body::Humanoid(_)))
|
||||||
.then(|| CharacterAbility::default_roll)
|
.then(CharacterAbility::default_roll)
|
||||||
.map(|ability| (ability().adjusted_by_skills(skill_set, None), false)),
|
.map(|ability| (ability.adjusted_by_skills(skill_set, None), false)),
|
||||||
Ability::MainWeaponAux(index) => ability_set(EquipSlot::ActiveMainhand)
|
Ability::MainWeaponAux(index) => ability_set(EquipSlot::ActiveMainhand)
|
||||||
.and_then(|abilities| abilities.abilities.get(index).cloned())
|
.and_then(|abilities| abilities.abilities.get(index).map(unwrap_ability))
|
||||||
.and_then(unlocked)
|
.and_then(unlocked)
|
||||||
.map(|ability| (scale_ability(ability, EquipSlot::ActiveMainhand), false)),
|
.map(|ability| (scale_ability(ability, EquipSlot::ActiveMainhand), false)),
|
||||||
Ability::OffWeaponAux(index) => ability_set(EquipSlot::ActiveOffhand)
|
Ability::OffWeaponAux(index) => ability_set(EquipSlot::ActiveOffhand)
|
||||||
.and_then(|abilities| abilities.abilities.get(index).cloned())
|
.and_then(|abilities| abilities.abilities.get(index).map(unwrap_ability))
|
||||||
.and_then(unlocked)
|
.and_then(unlocked)
|
||||||
.map(|ability| (scale_ability(ability, EquipSlot::ActiveOffhand), true)),
|
.map(|ability| (scale_ability(ability, EquipSlot::ActiveOffhand), true)),
|
||||||
Ability::Empty => None,
|
Ability::Empty => None,
|
||||||
@ -149,19 +153,13 @@ impl AbilityPool {
|
|||||||
inv: Option<&Inventory>,
|
inv: Option<&Inventory>,
|
||||||
skill_set: Option<&SkillSet>,
|
skill_set: Option<&SkillSet>,
|
||||||
equip_slot: EquipSlot,
|
equip_slot: EquipSlot,
|
||||||
) -> Vec<AuxiliaryAbility> {
|
) -> Vec<usize> {
|
||||||
let ability_from_slot = move |i| match equip_slot {
|
|
||||||
EquipSlot::ActiveMainhand => AuxiliaryAbility::MainWeapon(i),
|
|
||||||
EquipSlot::ActiveOffhand => AuxiliaryAbility::OffWeapon(i),
|
|
||||||
_ => AuxiliaryAbility::Empty,
|
|
||||||
};
|
|
||||||
|
|
||||||
inv
|
inv
|
||||||
.and_then(|inv| inv.equipped(equip_slot))
|
.and_then(|inv| inv.equipped(equip_slot))
|
||||||
.iter()
|
.iter()
|
||||||
.flat_map(|i| &i.item_config_expect().abilities.abilities)
|
.flat_map(|i| &i.item_config_expect().abilities.abilities)
|
||||||
.enumerate()
|
.enumerate()
|
||||||
.filter_map(move |(i, (skill, _))| skill.map_or(true, |s| skill_set.map_or(false, |ss| ss.has_skill(s))).then_some(ability_from_slot(i)))
|
.filter_map(move |(i, (skill, _))| skill.map_or(true, |s| skill_set.map_or(false, |ss| ss.has_skill(s))).then_some(i))
|
||||||
// TODO: Let someone smarter than borrow checker remove collect
|
// TODO: Let someone smarter than borrow checker remove collect
|
||||||
.collect()
|
.collect()
|
||||||
}
|
}
|
||||||
@ -170,9 +168,18 @@ impl AbilityPool {
|
|||||||
let off_abilities = iter_unlocked_abilities(inv, skill_set, EquipSlot::ActiveOffhand);
|
let off_abilities = iter_unlocked_abilities(inv, skill_set, EquipSlot::ActiveOffhand);
|
||||||
|
|
||||||
(0..MAX_ABILITIES)
|
(0..MAX_ABILITIES)
|
||||||
.zip(main_abilities.iter().chain(off_abilities.iter()))
|
.zip(
|
||||||
|
main_abilities
|
||||||
|
.iter()
|
||||||
|
.map(|a| AuxiliaryAbility::MainWeapon(*a))
|
||||||
|
.chain(
|
||||||
|
off_abilities
|
||||||
|
.iter()
|
||||||
|
.map(|a| AuxiliaryAbility::OffWeapon(*a)),
|
||||||
|
),
|
||||||
|
)
|
||||||
.for_each(|(i, ability)| {
|
.for_each(|(i, ability)| {
|
||||||
self.change_ability(i, *ability);
|
self.change_ability(i, ability);
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -198,25 +205,37 @@ pub enum Ability {
|
|||||||
|
|
||||||
impl Ability {
|
impl Ability {
|
||||||
pub fn ability_id(self, inv: Option<&Inventory>) -> Option<&str> {
|
pub fn ability_id(self, inv: Option<&Inventory>) -> Option<&str> {
|
||||||
let ability_id_set = |equip_slot| {
|
let ability_set = |equip_slot| {
|
||||||
inv.and_then(|inv| inv.equipped(equip_slot))
|
inv.and_then(|inv| inv.equipped(equip_slot))
|
||||||
.map(|i| &i.item_config_expect().ability_ids)
|
.map(|i| &i.item_config_expect().abilities)
|
||||||
};
|
};
|
||||||
|
|
||||||
match self {
|
match self {
|
||||||
Ability::ToolPrimary => {
|
Ability::ToolPrimary => ability_set(EquipSlot::ActiveMainhand)
|
||||||
ability_id_set(EquipSlot::ActiveMainhand).map(|ids| ids.primary.as_str())
|
.map(|abilities| abilities.primary.id.as_str()),
|
||||||
},
|
Ability::ToolSecondary => ability_set(EquipSlot::ActiveOffhand)
|
||||||
Ability::ToolSecondary => ability_id_set(EquipSlot::ActiveOffhand)
|
.map(|abilities| abilities.secondary.id.as_str())
|
||||||
.map(|ids| ids.secondary.as_str())
|
|
||||||
.or_else(|| {
|
.or_else(|| {
|
||||||
ability_id_set(EquipSlot::ActiveMainhand).map(|ids| ids.secondary.as_str())
|
ability_set(EquipSlot::ActiveMainhand)
|
||||||
|
.map(|abilities| abilities.secondary.id.as_str())
|
||||||
}),
|
}),
|
||||||
Ability::SpeciesMovement => None, // TODO: Make not None
|
Ability::SpeciesMovement => None, // TODO: Make not None
|
||||||
Ability::MainWeaponAux(index) => ability_id_set(EquipSlot::ActiveMainhand)
|
Ability::MainWeaponAux(index) => {
|
||||||
.and_then(|ids| ids.abilities.get(index).map(|(_, id)| id.as_str())),
|
ability_set(EquipSlot::ActiveMainhand).and_then(|abilities| {
|
||||||
Ability::OffWeaponAux(index) => ability_id_set(EquipSlot::ActiveOffhand)
|
abilities
|
||||||
.and_then(|ids| ids.abilities.get(index).map(|(_, id)| id.as_str())),
|
.abilities
|
||||||
|
.get(index)
|
||||||
|
.map(|(_, ability)| ability.id.as_str())
|
||||||
|
})
|
||||||
|
},
|
||||||
|
Ability::OffWeaponAux(index) => {
|
||||||
|
ability_set(EquipSlot::ActiveOffhand).and_then(|abilities| {
|
||||||
|
abilities
|
||||||
|
.abilities
|
||||||
|
.get(index)
|
||||||
|
.map(|(_, ability)| ability.id.as_str())
|
||||||
|
})
|
||||||
|
},
|
||||||
Ability::Empty => None,
|
Ability::Empty => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -8,10 +8,7 @@ pub use tool::{AbilitySet, AbilitySpec, Hands, MaterialStatManifest, Tool, ToolK
|
|||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
assets::{self, AssetExt, Error},
|
assets::{self, AssetExt, Error},
|
||||||
comp::{
|
comp::inventory::{item::tool::AbilityMap, InvSlot},
|
||||||
inventory::{item::tool::AbilityMap, InvSlot},
|
|
||||||
CharacterAbility,
|
|
||||||
},
|
|
||||||
effect::Effect,
|
effect::Effect,
|
||||||
recipe::RecipeInput,
|
recipe::RecipeInput,
|
||||||
terrain::Block,
|
terrain::Block,
|
||||||
@ -433,8 +430,7 @@ impl PartialEq for ItemDef {
|
|||||||
// TODO: Look into removing ItemConfig and just using AbilitySet
|
// TODO: Look into removing ItemConfig and just using AbilitySet
|
||||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||||
pub struct ItemConfig {
|
pub struct ItemConfig {
|
||||||
pub abilities: AbilitySet<CharacterAbility>,
|
pub abilities: AbilitySet<tool::AbilityItem>,
|
||||||
pub ability_ids: AbilitySet<String>,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
@ -449,56 +445,33 @@ impl TryFrom<(&Item, &AbilityMap, &MaterialStatManifest)> for ItemConfig {
|
|||||||
(item, ability_map, msm): (&Item, &AbilityMap, &MaterialStatManifest),
|
(item, ability_map, msm): (&Item, &AbilityMap, &MaterialStatManifest),
|
||||||
) -> Result<Self, Self::Error> {
|
) -> Result<Self, Self::Error> {
|
||||||
if let ItemKind::Tool(tool) = &item.kind {
|
if let ItemKind::Tool(tool) = &item.kind {
|
||||||
// TODO: Maybe try to make an ecs resource?
|
|
||||||
let ability_ids_map =
|
|
||||||
AbilityMap::<String>::load_expect("common.abilities.ability_set_manifest").read();
|
|
||||||
|
|
||||||
// If no custom ability set is specified, fall back to abilityset of tool kind.
|
// If no custom ability set is specified, fall back to abilityset of tool kind.
|
||||||
let tool_default = |tool_kind| {
|
let tool_default = |tool_kind| {
|
||||||
let key = &AbilitySpec::Tool(tool_kind);
|
let key = &AbilitySpec::Tool(tool_kind);
|
||||||
(
|
ability_map.get_ability_set(key)
|
||||||
ability_map.get_ability_set(key),
|
|
||||||
ability_ids_map.get_ability_set(key),
|
|
||||||
)
|
|
||||||
};
|
};
|
||||||
let (abilities, ability_ids) = if let Some(set_key) = item.ability_spec() {
|
let abilities = if let Some(set_key) = item.ability_spec() {
|
||||||
if let (Some(set), Some(ids)) = (
|
if let Some(set) = ability_map.get_ability_set(set_key) {
|
||||||
ability_map.get_ability_set(set_key),
|
set.clone().modified_by_tool(tool, msm, &item.components)
|
||||||
ability_ids_map.get_ability_set(set_key),
|
|
||||||
) {
|
|
||||||
(
|
|
||||||
set.clone().modified_by_tool(tool, msm, &item.components),
|
|
||||||
ids.clone(),
|
|
||||||
)
|
|
||||||
} else {
|
} else {
|
||||||
error!(
|
error!(
|
||||||
"Custom ability set: {:?} references non-existent set, falling back to \
|
"Custom ability set: {:?} references non-existent set, falling back to \
|
||||||
default ability set.",
|
default ability set.",
|
||||||
set_key
|
set_key
|
||||||
);
|
);
|
||||||
let (abilities, ids) = tool_default(tool.kind);
|
tool_default(tool.kind).cloned().unwrap_or_default()
|
||||||
(
|
|
||||||
abilities.cloned().unwrap_or_default(),
|
|
||||||
ids.cloned().unwrap_or_default(),
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
} else if let (Some(set), Some(ids)) = tool_default(tool.kind) {
|
} else if let Some(set) = tool_default(tool.kind) {
|
||||||
(
|
set.clone().modified_by_tool(tool, msm, &item.components)
|
||||||
set.clone().modified_by_tool(tool, msm, &item.components),
|
|
||||||
ids.clone(),
|
|
||||||
)
|
|
||||||
} else {
|
} else {
|
||||||
error!(
|
error!(
|
||||||
"No ability set defined for tool: {:?}, falling back to default ability set.",
|
"No ability set defined for tool: {:?}, falling back to default ability set.",
|
||||||
tool.kind
|
tool.kind
|
||||||
);
|
);
|
||||||
(Default::default(), Default::default())
|
Default::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
Ok(ItemConfig {
|
Ok(ItemConfig { abilities })
|
||||||
abilities,
|
|
||||||
ability_ids,
|
|
||||||
})
|
|
||||||
} else {
|
} else {
|
||||||
Err(ItemConfigError::BadItemKind)
|
Err(ItemConfigError::BadItemKind)
|
||||||
}
|
}
|
||||||
|
@ -345,7 +345,7 @@ pub struct AbilitySet<T> {
|
|||||||
pub abilities: Vec<(Option<Skill>, T)>,
|
pub abilities: Vec<(Option<Skill>, T)>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl AbilitySet<CharacterAbility> {
|
impl AbilitySet<AbilityItem> {
|
||||||
pub fn modified_by_tool(
|
pub fn modified_by_tool(
|
||||||
self,
|
self,
|
||||||
tool: &Tool,
|
tool: &Tool,
|
||||||
@ -353,7 +353,10 @@ impl AbilitySet<CharacterAbility> {
|
|||||||
components: &[Item],
|
components: &[Item],
|
||||||
) -> Self {
|
) -> Self {
|
||||||
let stats = Stats::from((msm, components, tool));
|
let stats = Stats::from((msm, components, tool));
|
||||||
self.map(|a| a.adjusted_by_stats(stats))
|
self.map(|a| AbilityItem {
|
||||||
|
id: a.id,
|
||||||
|
ability: a.ability.adjusted_by_stats(stats),
|
||||||
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -376,22 +379,17 @@ impl<T> AbilitySet<T> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[allow(clippy::derivable_impls)]
|
#[allow(clippy::derivable_impls)]
|
||||||
impl Default for AbilitySet<CharacterAbility> {
|
impl Default for AbilitySet<AbilityItem> {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
AbilitySet {
|
AbilitySet {
|
||||||
primary: CharacterAbility::default(),
|
primary: AbilityItem {
|
||||||
secondary: CharacterAbility::default(),
|
id: String::new(),
|
||||||
abilities: Vec::new(),
|
ability: CharacterAbility::default(),
|
||||||
}
|
},
|
||||||
}
|
secondary: AbilityItem {
|
||||||
}
|
id: String::new(),
|
||||||
|
ability: CharacterAbility::default(),
|
||||||
#[allow(clippy::derivable_impls)]
|
},
|
||||||
impl Default for AbilitySet<String> {
|
|
||||||
fn default() -> Self {
|
|
||||||
AbilitySet {
|
|
||||||
primary: String::new(),
|
|
||||||
secondary: String::new(),
|
|
||||||
abilities: Vec::new(),
|
abilities: Vec::new(),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -404,7 +402,13 @@ pub enum AbilitySpec {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Debug, Serialize, Deserialize)]
|
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||||
pub struct AbilityMap<T = CharacterAbility>(HashMap<AbilitySpec, AbilitySet<T>>);
|
pub struct AbilityItem {
|
||||||
|
pub id: String,
|
||||||
|
pub ability: CharacterAbility,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Debug, Serialize, Deserialize)]
|
||||||
|
pub struct AbilityMap<T = AbilityItem>(HashMap<AbilitySpec, AbilitySet<T>>);
|
||||||
|
|
||||||
impl Default for AbilityMap {
|
impl Default for AbilityMap {
|
||||||
fn default() -> Self {
|
fn default() -> Self {
|
||||||
@ -445,7 +449,10 @@ impl assets::Compound for AbilityMap {
|
|||||||
kind.clone(),
|
kind.clone(),
|
||||||
// expect cannot fail because CharacterAbility always
|
// expect cannot fail because CharacterAbility always
|
||||||
// provides a default value in case of failure
|
// provides a default value in case of failure
|
||||||
set.map_ref(|s| cache.load_expect(s).cloned()),
|
set.map_ref(|s| AbilityItem {
|
||||||
|
id: s.clone(),
|
||||||
|
ability: cache.load_expect(s).cloned(),
|
||||||
|
}),
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
.collect(),
|
.collect(),
|
||||||
|
@ -48,7 +48,7 @@ pub mod visual;
|
|||||||
// Reexports
|
// Reexports
|
||||||
#[cfg(not(target_arch = "wasm32"))]
|
#[cfg(not(target_arch = "wasm32"))]
|
||||||
pub use self::{
|
pub use self::{
|
||||||
ability::{Ability, AbilityPool, CharacterAbility, CharacterAbilityType},
|
ability::{Ability, AbilityInput, ActiveAbilities, CharacterAbility, CharacterAbilityType},
|
||||||
admin::{Admin, AdminRole},
|
admin::{Admin, AdminRole},
|
||||||
agent::{Agent, Alignment, Behavior, BehaviorCapability, BehaviorState, PidController},
|
agent::{Agent, Alignment, Behavior, BehaviorCapability, BehaviorState, PidController},
|
||||||
anchor::Anchor,
|
anchor::Anchor,
|
||||||
@ -78,7 +78,11 @@ pub use self::{
|
|||||||
group::Group,
|
group::Group,
|
||||||
inputs::CanBuild,
|
inputs::CanBuild,
|
||||||
inventory::{
|
inventory::{
|
||||||
item::{self, tool, Item, ItemConfig, ItemDrop},
|
item::{
|
||||||
|
self,
|
||||||
|
tool::{self, AbilityItem},
|
||||||
|
Item, ItemConfig, ItemDrop,
|
||||||
|
},
|
||||||
slot, Inventory, InventoryUpdate, InventoryUpdateEvent,
|
slot, Inventory, InventoryUpdate, InventoryUpdateEvent,
|
||||||
},
|
},
|
||||||
last::Last,
|
last::Last,
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use crate::{
|
use crate::{
|
||||||
comp::{
|
comp::{
|
||||||
self, character_state::OutputEvents, item::MaterialStatManifest, AbilityPool, Beam, Body,
|
self, character_state::OutputEvents, item::MaterialStatManifest, ActiveAbilities, Beam,
|
||||||
CharacterState, Combo, ControlAction, Controller, ControllerInputs, Density, Energy,
|
Body, CharacterState, Combo, ControlAction, Controller, ControllerInputs, Density, Energy,
|
||||||
Health, InputAttr, InputKind, Inventory, InventoryAction, Mass, Melee, Ori, PhysicsState,
|
Health, InputAttr, InputKind, Inventory, InventoryAction, Mass, Melee, Ori, PhysicsState,
|
||||||
Pos, SkillSet, StateUpdate, Stats, Vel,
|
Pos, SkillSet, StateUpdate, Stats, Vel,
|
||||||
},
|
},
|
||||||
@ -124,7 +124,7 @@ pub struct JoinData<'a> {
|
|||||||
pub updater: &'a LazyUpdate,
|
pub updater: &'a LazyUpdate,
|
||||||
pub stats: &'a Stats,
|
pub stats: &'a Stats,
|
||||||
pub skill_set: &'a SkillSet,
|
pub skill_set: &'a SkillSet,
|
||||||
pub ability_pool: &'a AbilityPool,
|
pub active_abilities: &'a ActiveAbilities,
|
||||||
pub msm: &'a MaterialStatManifest,
|
pub msm: &'a MaterialStatManifest,
|
||||||
pub combo: &'a Combo,
|
pub combo: &'a Combo,
|
||||||
pub alignment: Option<&'a comp::Alignment>,
|
pub alignment: Option<&'a comp::Alignment>,
|
||||||
@ -150,7 +150,7 @@ pub struct JoinStruct<'a> {
|
|||||||
pub beam: Option<&'a Beam>,
|
pub beam: Option<&'a Beam>,
|
||||||
pub stat: &'a Stats,
|
pub stat: &'a Stats,
|
||||||
pub skill_set: &'a SkillSet,
|
pub skill_set: &'a SkillSet,
|
||||||
pub ability_pool: &'a AbilityPool,
|
pub active_abilities: &'a ActiveAbilities,
|
||||||
pub combo: &'a Combo,
|
pub combo: &'a Combo,
|
||||||
pub alignment: Option<&'a comp::Alignment>,
|
pub alignment: Option<&'a comp::Alignment>,
|
||||||
pub terrain: &'a TerrainGrid,
|
pub terrain: &'a TerrainGrid,
|
||||||
@ -188,7 +188,7 @@ impl<'a> JoinData<'a> {
|
|||||||
combo: j.combo,
|
combo: j.combo,
|
||||||
alignment: j.alignment,
|
alignment: j.alignment,
|
||||||
terrain: j.terrain,
|
terrain: j.terrain,
|
||||||
ability_pool: j.ability_pool,
|
active_abilities: j.active_abilities,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -823,8 +823,13 @@ pub fn handle_jump(
|
|||||||
fn handle_ability(data: &JoinData<'_>, update: &mut StateUpdate, input: InputKind) {
|
fn handle_ability(data: &JoinData<'_>, update: &mut StateUpdate, input: InputKind) {
|
||||||
if let Some(ability_input) = input.into() {
|
if let Some(ability_input) = input.into() {
|
||||||
if let Some((ability, from_offhand)) = data
|
if let Some((ability, from_offhand)) = data
|
||||||
.ability_pool
|
.active_abilities
|
||||||
.activate_ability(ability_input, data.inventory, data.skill_set, data.body)
|
.activate_ability(
|
||||||
|
ability_input,
|
||||||
|
data.inventory,
|
||||||
|
data.skill_set,
|
||||||
|
Some(data.body),
|
||||||
|
)
|
||||||
.filter(|(ability, _)| ability.requirements_paid(data, update))
|
.filter(|(ability, _)| ability.requirements_paid(data, update))
|
||||||
{
|
{
|
||||||
update.character = CharacterState::from((
|
update.character = CharacterState::from((
|
||||||
|
@ -129,7 +129,7 @@ impl State {
|
|||||||
ecs.register::<comp::Player>();
|
ecs.register::<comp::Player>();
|
||||||
ecs.register::<comp::Stats>();
|
ecs.register::<comp::Stats>();
|
||||||
ecs.register::<comp::SkillSet>();
|
ecs.register::<comp::SkillSet>();
|
||||||
ecs.register::<comp::AbilityPool>();
|
ecs.register::<comp::ActiveAbilities>();
|
||||||
ecs.register::<comp::Buffs>();
|
ecs.register::<comp::Buffs>();
|
||||||
ecs.register::<comp::Auras>();
|
ecs.register::<comp::Auras>();
|
||||||
ecs.register::<comp::Energy>();
|
ecs.register::<comp::Energy>();
|
||||||
|
@ -5,9 +5,9 @@ use specs::{
|
|||||||
|
|
||||||
use common::{
|
use common::{
|
||||||
comp::{
|
comp::{
|
||||||
self, character_state::OutputEvents, inventory::item::MaterialStatManifest, AbilityPool,
|
self, character_state::OutputEvents, inventory::item::MaterialStatManifest,
|
||||||
Beam, Body, CharacterState, Combo, Controller, Density, Energy, Health, Inventory,
|
ActiveAbilities, Beam, Body, CharacterState, Combo, Controller, Density, Energy, Health,
|
||||||
InventoryManip, Mass, Melee, Mounting, Ori, PhysicsState, Poise, Pos, SkillSet,
|
Inventory, InventoryManip, Mass, Melee, Mounting, Ori, PhysicsState, Poise, Pos, SkillSet,
|
||||||
StateUpdate, Stats, Vel,
|
StateUpdate, Stats, Vel,
|
||||||
},
|
},
|
||||||
event::{EventBus, LocalEvent, ServerEvent},
|
event::{EventBus, LocalEvent, ServerEvent},
|
||||||
@ -39,7 +39,7 @@ pub struct ReadData<'a> {
|
|||||||
mountings: ReadStorage<'a, Mounting>,
|
mountings: ReadStorage<'a, Mounting>,
|
||||||
stats: ReadStorage<'a, Stats>,
|
stats: ReadStorage<'a, Stats>,
|
||||||
skill_sets: ReadStorage<'a, SkillSet>,
|
skill_sets: ReadStorage<'a, SkillSet>,
|
||||||
ability_pools: ReadStorage<'a, AbilityPool>,
|
active_abilities: ReadStorage<'a, ActiveAbilities>,
|
||||||
msm: Read<'a, MaterialStatManifest>,
|
msm: Read<'a, MaterialStatManifest>,
|
||||||
combos: ReadStorage<'a, Combo>,
|
combos: ReadStorage<'a, Combo>,
|
||||||
alignments: ReadStorage<'a, comp::Alignment>,
|
alignments: ReadStorage<'a, comp::Alignment>,
|
||||||
@ -109,7 +109,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
health,
|
health,
|
||||||
body,
|
body,
|
||||||
physics,
|
physics,
|
||||||
(stat, skill_set, ability_pool),
|
(stat, skill_set, active_abilities),
|
||||||
combo,
|
combo,
|
||||||
) in (
|
) in (
|
||||||
&read_data.entities,
|
&read_data.entities,
|
||||||
@ -129,7 +129,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
(
|
(
|
||||||
&read_data.stats,
|
&read_data.stats,
|
||||||
&read_data.skill_sets,
|
&read_data.skill_sets,
|
||||||
&read_data.ability_pools,
|
&read_data.active_abilities,
|
||||||
),
|
),
|
||||||
&read_data.combos,
|
&read_data.combos,
|
||||||
)
|
)
|
||||||
@ -187,7 +187,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
beam: read_data.beams.get(entity),
|
beam: read_data.beams.get(entity),
|
||||||
stat,
|
stat,
|
||||||
skill_set,
|
skill_set,
|
||||||
ability_pool,
|
active_abilities,
|
||||||
combo,
|
combo,
|
||||||
alignment: read_data.alignments.get(entity),
|
alignment: read_data.alignments.get(entity),
|
||||||
terrain: &read_data.terrain,
|
terrain: &read_data.terrain,
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
use common::{
|
use common::{
|
||||||
comp::{
|
comp::{
|
||||||
agent::{Sound, SoundKind},
|
agent::{Sound, SoundKind},
|
||||||
AbilityPool, Body, BuffChange, ControlEvent, Controller, Pos,
|
ActiveAbilities, Body, BuffChange, ControlEvent, Controller, Pos,
|
||||||
},
|
},
|
||||||
event::{EventBus, ServerEvent},
|
event::{EventBus, ServerEvent},
|
||||||
uid::UidAllocator,
|
uid::UidAllocator,
|
||||||
@ -30,7 +30,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
type SystemData = (
|
type SystemData = (
|
||||||
ReadData<'a>,
|
ReadData<'a>,
|
||||||
WriteStorage<'a, Controller>,
|
WriteStorage<'a, Controller>,
|
||||||
WriteStorage<'a, AbilityPool>,
|
WriteStorage<'a, ActiveAbilities>,
|
||||||
);
|
);
|
||||||
|
|
||||||
const NAME: &'static str = "controller";
|
const NAME: &'static str = "controller";
|
||||||
@ -39,13 +39,11 @@ impl<'a> System<'a> for Sys {
|
|||||||
|
|
||||||
fn run(
|
fn run(
|
||||||
_job: &mut Job<Self>,
|
_job: &mut Job<Self>,
|
||||||
(read_data, mut controllers, mut ability_pools): Self::SystemData,
|
(read_data, mut controllers, mut active_abilities): Self::SystemData,
|
||||||
) {
|
) {
|
||||||
let mut server_emitter = read_data.server_bus.emitter();
|
let mut server_emitter = read_data.server_bus.emitter();
|
||||||
|
|
||||||
for (entity, controller, mut ability_pool) in
|
for (entity, controller) in (&read_data.entities, &mut controllers).join() {
|
||||||
(&read_data.entities, &mut controllers, &mut ability_pools).join()
|
|
||||||
{
|
|
||||||
// Sanitize inputs to avoid clients sending bad data
|
// Sanitize inputs to avoid clients sending bad data
|
||||||
controller.inputs.sanitize();
|
controller.inputs.sanitize();
|
||||||
|
|
||||||
@ -113,7 +111,9 @@ impl<'a> System<'a> for Sys {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
ControlEvent::ChangeAbility { slot, new_ability } => {
|
ControlEvent::ChangeAbility { slot, new_ability } => {
|
||||||
ability_pool.change_ability(slot, new_ability)
|
if let Some(mut active_abilities) = active_abilities.get_mut(entity) {
|
||||||
|
active_abilities.change_ability(slot, new_ability);
|
||||||
|
}
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -770,12 +770,12 @@ pub fn handle_inventory(server: &mut Server, entity: EcsEntity, manip: comp::Inv
|
|||||||
|
|
||||||
// After any inventory manipulation, update the ability
|
// After any inventory manipulation, update the ability
|
||||||
// TODO: Make less hacky, probably remove entirely but needs UI
|
// TODO: Make less hacky, probably remove entirely but needs UI
|
||||||
if let Some(mut ability_pool) = state
|
if let Some(mut active_abilities) = state
|
||||||
.ecs()
|
.ecs()
|
||||||
.write_storage::<comp::AbilityPool>()
|
.write_storage::<comp::ActiveAbilities>()
|
||||||
.get_mut(entity)
|
.get_mut(entity)
|
||||||
{
|
{
|
||||||
ability_pool.auto_update(
|
active_abilities.auto_update(
|
||||||
state.ecs().read_storage::<comp::Inventory>().get(entity),
|
state.ecs().read_storage::<comp::Inventory>().get(entity),
|
||||||
state.ecs().read_storage::<comp::SkillSet>().get(entity),
|
state.ecs().read_storage::<comp::SkillSet>().get(entity),
|
||||||
);
|
);
|
||||||
|
@ -66,8 +66,7 @@ use common::{
|
|||||||
assets::AssetExt,
|
assets::AssetExt,
|
||||||
character::CharacterId,
|
character::CharacterId,
|
||||||
cmd::ChatCommand,
|
cmd::ChatCommand,
|
||||||
comp,
|
comp::{self, item::MaterialStatManifest},
|
||||||
comp::{item::MaterialStatManifest, CharacterAbility},
|
|
||||||
event::{EventBus, ServerEvent},
|
event::{EventBus, ServerEvent},
|
||||||
recipe::default_recipe_book,
|
recipe::default_recipe_book,
|
||||||
resources::{BattleMode, Time, TimeOfDay},
|
resources::{BattleMode, Time, TimeOfDay},
|
||||||
@ -287,7 +286,7 @@ impl Server {
|
|||||||
Arc::<RwLock<DatabaseSettings>>::clone(&database_settings),
|
Arc::<RwLock<DatabaseSettings>>::clone(&database_settings),
|
||||||
)?);
|
)?);
|
||||||
|
|
||||||
let ability_map = comp::item::tool::AbilityMap::<CharacterAbility>::load_expect_cloned(
|
let ability_map = comp::item::tool::AbilityMap::<comp::AbilityItem>::load_expect_cloned(
|
||||||
"common.abilities.ability_set_manifest",
|
"common.abilities.ability_set_manifest",
|
||||||
);
|
);
|
||||||
state.ecs_mut().insert(ability_map);
|
state.ecs_mut().insert(ability_map);
|
||||||
|
@ -215,7 +215,10 @@ impl StateExt for State {
|
|||||||
.unwrap_or(0),
|
.unwrap_or(0),
|
||||||
))
|
))
|
||||||
.with(stats)
|
.with(stats)
|
||||||
.with(comp::AbilityPool::new(Some(&inventory), Some(&skill_set)))
|
.with(comp::ActiveAbilities::new(
|
||||||
|
Some(&inventory),
|
||||||
|
Some(&skill_set),
|
||||||
|
))
|
||||||
.with(skill_set)
|
.with(skill_set)
|
||||||
.maybe_with(health)
|
.maybe_with(health)
|
||||||
.with(poise)
|
.with(poise)
|
||||||
@ -268,7 +271,7 @@ impl StateExt for State {
|
|||||||
.with(comp::Energy::new(ship.into(), 0))
|
.with(comp::Energy::new(ship.into(), 0))
|
||||||
.with(comp::Stats::new("Airship".to_string()))
|
.with(comp::Stats::new("Airship".to_string()))
|
||||||
.with(comp::SkillSet::default())
|
.with(comp::SkillSet::default())
|
||||||
.with(comp::AbilityPool::default())
|
.with(comp::ActiveAbilities::default())
|
||||||
.with(comp::Combo::default());
|
.with(comp::Combo::default());
|
||||||
|
|
||||||
if mountable {
|
if mountable {
|
||||||
@ -508,7 +511,7 @@ impl StateExt for State {
|
|||||||
self.write_component_ignore_entity_dead(entity, stats);
|
self.write_component_ignore_entity_dead(entity, stats);
|
||||||
self.write_component_ignore_entity_dead(
|
self.write_component_ignore_entity_dead(
|
||||||
entity,
|
entity,
|
||||||
comp::AbilityPool::new(Some(&inventory), Some(&skill_set)),
|
comp::ActiveAbilities::new(Some(&inventory), Some(&skill_set)),
|
||||||
);
|
);
|
||||||
self.write_component_ignore_entity_dead(entity, skill_set);
|
self.write_component_ignore_entity_dead(entity, skill_set);
|
||||||
self.write_component_ignore_entity_dead(entity, inventory);
|
self.write_component_ignore_entity_dead(entity, inventory);
|
||||||
|
@ -19,9 +19,9 @@ use common::{
|
|||||||
},
|
},
|
||||||
projectile::ProjectileConstructor,
|
projectile::ProjectileConstructor,
|
||||||
skills::{AxeSkill, BowSkill, HammerSkill, SceptreSkill, Skill, StaffSkill, SwordSkill},
|
skills::{AxeSkill, BowSkill, HammerSkill, SceptreSkill, Skill, StaffSkill, SwordSkill},
|
||||||
Agent, Alignment, BehaviorCapability, BehaviorState, Body, CharacterAbility,
|
AbilityInput, ActiveAbilities, Agent, Alignment, BehaviorCapability, BehaviorState, Body,
|
||||||
CharacterState, Combo, ControlAction, ControlEvent, Controller, Energy, Health,
|
CharacterAbility, CharacterState, Combo, ControlAction, ControlEvent, Controller, Energy,
|
||||||
HealthChange, InputKind, Inventory, InventoryAction, LightEmitter, MountState, Ori,
|
Health, HealthChange, InputKind, Inventory, InventoryAction, LightEmitter, MountState, Ori,
|
||||||
PhysicsState, Pos, Scale, SkillSet, Stats, UnresolvedChatMsg, UtteranceKind, Vel,
|
PhysicsState, Pos, Scale, SkillSet, Stats, UnresolvedChatMsg, UtteranceKind, Vel,
|
||||||
},
|
},
|
||||||
consts::GRAVITY,
|
consts::GRAVITY,
|
||||||
@ -74,6 +74,7 @@ struct AgentData<'a> {
|
|||||||
is_gliding: bool,
|
is_gliding: bool,
|
||||||
health: Option<&'a Health>,
|
health: Option<&'a Health>,
|
||||||
char_state: &'a CharacterState,
|
char_state: &'a CharacterState,
|
||||||
|
active_abilities: &'a ActiveAbilities,
|
||||||
cached_spatial_grid: &'a common::CachedSpatialGrid,
|
cached_spatial_grid: &'a common::CachedSpatialGrid,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -160,6 +161,7 @@ pub struct ReadData<'a> {
|
|||||||
rtsim_entities: ReadStorage<'a, RtSimEntity>,
|
rtsim_entities: ReadStorage<'a, RtSimEntity>,
|
||||||
buffs: ReadStorage<'a, Buffs>,
|
buffs: ReadStorage<'a, Buffs>,
|
||||||
combos: ReadStorage<'a, Combo>,
|
combos: ReadStorage<'a, Combo>,
|
||||||
|
active_abilities: ReadStorage<'a, ActiveAbilities>,
|
||||||
}
|
}
|
||||||
|
|
||||||
const DAMAGE_MEMORY_DURATION: f64 = 0.25;
|
const DAMAGE_MEMORY_DURATION: f64 = 0.25;
|
||||||
@ -212,7 +214,11 @@ impl<'a> System<'a> for Sys {
|
|||||||
),
|
),
|
||||||
read_data.bodies.maybe(),
|
read_data.bodies.maybe(),
|
||||||
&read_data.inventories,
|
&read_data.inventories,
|
||||||
&read_data.skill_set,
|
(
|
||||||
|
&read_data.char_states,
|
||||||
|
&read_data.skill_set,
|
||||||
|
&read_data.active_abilities,
|
||||||
|
),
|
||||||
&read_data.physics_states,
|
&read_data.physics_states,
|
||||||
&read_data.uids,
|
&read_data.uids,
|
||||||
&mut agents,
|
&mut agents,
|
||||||
@ -220,10 +226,9 @@ impl<'a> System<'a> for Sys {
|
|||||||
read_data.light_emitter.maybe(),
|
read_data.light_emitter.maybe(),
|
||||||
read_data.groups.maybe(),
|
read_data.groups.maybe(),
|
||||||
read_data.mount_states.maybe(),
|
read_data.mount_states.maybe(),
|
||||||
&read_data.char_states,
|
|
||||||
)
|
)
|
||||||
.par_join()
|
.par_join()
|
||||||
.filter(|(_, _, _, _, _, _, _, _, _, _, _, _, mount_state, _)| {
|
.filter(|(_, _, _, _, _, _, _, _, _, _, _, _, mount_state)| {
|
||||||
// Skip mounted entities
|
// Skip mounted entities
|
||||||
mount_state
|
mount_state
|
||||||
.map(|ms| *ms == MountState::Unmounted)
|
.map(|ms| *ms == MountState::Unmounted)
|
||||||
@ -241,7 +246,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
(pos, vel, ori),
|
(pos, vel, ori),
|
||||||
body,
|
body,
|
||||||
inventory,
|
inventory,
|
||||||
skill_set,
|
(char_state, skill_set, active_abilities),
|
||||||
physics_state,
|
physics_state,
|
||||||
uid,
|
uid,
|
||||||
agent,
|
agent,
|
||||||
@ -249,7 +254,6 @@ impl<'a> System<'a> for Sys {
|
|||||||
light_emitter,
|
light_emitter,
|
||||||
group,
|
group,
|
||||||
_,
|
_,
|
||||||
char_state,
|
|
||||||
)| {
|
)| {
|
||||||
// Hack, replace with better system when groups are more sophisticated
|
// Hack, replace with better system when groups are more sophisticated
|
||||||
// Override alignment if in a group unless entity is owned already
|
// Override alignment if in a group unless entity is owned already
|
||||||
@ -359,6 +363,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
is_gliding,
|
is_gliding,
|
||||||
health: read_data.healths.get(entity),
|
health: read_data.healths.get(entity),
|
||||||
char_state,
|
char_state,
|
||||||
|
active_abilities,
|
||||||
cached_spatial_grid: &read_data.cached_spatial_grid,
|
cached_spatial_grid: &read_data.cached_spatial_grid,
|
||||||
};
|
};
|
||||||
///////////////////////////////////////////////////////////
|
///////////////////////////////////////////////////////////
|
||||||
@ -2502,30 +2507,35 @@ impl<'a> AgentData<'a> {
|
|||||||
tgt_data: &TargetData,
|
tgt_data: &TargetData,
|
||||||
read_data: &ReadData,
|
read_data: &ReadData,
|
||||||
) {
|
) {
|
||||||
let extract_ability = |ability: &CharacterAbility| {
|
let extract_ability = |input: AbilityInput| {
|
||||||
ability
|
self.active_abilities
|
||||||
.clone()
|
.activate_ability(input, Some(self.inventory), self.skill_set, self.body)
|
||||||
.adjusted_by_skills(self.skill_set, Some(ToolKind::Staff))
|
.unwrap_or_default()
|
||||||
|
.0
|
||||||
};
|
};
|
||||||
let (flamethrower, shockwave) = self
|
let (flamethrower, shockwave) = (
|
||||||
.inventory
|
extract_ability(AbilityInput::Secondary),
|
||||||
.equipped(EquipSlot::ActiveMainhand)
|
extract_ability(AbilityInput::Auxiliary(0)),
|
||||||
.map(|i| &i.item_config_expect().abilities)
|
);
|
||||||
.map(|a| {
|
// self
|
||||||
(
|
// .inventory
|
||||||
Some(a.secondary.clone()),
|
// .equipped(EquipSlot::ActiveMainhand)
|
||||||
a.abilities.get(0).map(|(_, s)| s),
|
// .map(|i| &i.item_config_expect().abilities)
|
||||||
)
|
// .map(|a| {
|
||||||
})
|
// (
|
||||||
.map_or(
|
// Some(a.secondary.clone()),
|
||||||
(CharacterAbility::default(), CharacterAbility::default()),
|
// a.abilities.get(0).map(|(_, s)| s),
|
||||||
|(s, a)| {
|
// )
|
||||||
(
|
// })
|
||||||
extract_ability(&s.unwrap_or_default()),
|
// .map_or(
|
||||||
extract_ability(a.unwrap_or(&CharacterAbility::default())),
|
// (CharacterAbility::default(), CharacterAbility::default()),
|
||||||
)
|
// |(s, a)| {
|
||||||
},
|
// (
|
||||||
);
|
// extract_ability(&s.unwrap_or_default()),
|
||||||
|
// extract_ability(a.unwrap_or(&CharacterAbility::default())),
|
||||||
|
// )
|
||||||
|
// },
|
||||||
|
// );
|
||||||
let flamethrower_range = match flamethrower {
|
let flamethrower_range = match flamethrower {
|
||||||
CharacterAbility::BasicBeam { range, .. } => range,
|
CharacterAbility::BasicBeam { range, .. } => range,
|
||||||
_ => 20.0_f32,
|
_ => 20.0_f32,
|
||||||
|
@ -1,9 +1,9 @@
|
|||||||
use common::{
|
use common::{
|
||||||
comp::{
|
comp::{
|
||||||
item::{tool::AbilityMap, MaterialStatManifest},
|
item::{tool::AbilityMap, MaterialStatManifest},
|
||||||
AbilityPool, Auras, BeamSegment, Body, Buffs, CanBuild, CharacterState, Collider, Combo,
|
ActiveAbilities, Auras, BeamSegment, Body, Buffs, CanBuild, CharacterState, Collider,
|
||||||
Density, Energy, Group, Health, Inventory, Item, LightEmitter, Mass, MountState, Mounting,
|
Combo, Density, Energy, Group, Health, Inventory, Item, LightEmitter, Mass, MountState,
|
||||||
Ori, Player, Poise, Pos, Scale, Shockwave, SkillSet, Stats, Sticky, Vel,
|
Mounting, Ori, Player, Poise, Pos, Scale, Shockwave, SkillSet, Stats, Sticky, Vel,
|
||||||
},
|
},
|
||||||
uid::Uid,
|
uid::Uid,
|
||||||
};
|
};
|
||||||
@ -44,7 +44,7 @@ pub struct TrackedComps<'a> {
|
|||||||
pub player: ReadStorage<'a, Player>,
|
pub player: ReadStorage<'a, Player>,
|
||||||
pub stats: ReadStorage<'a, Stats>,
|
pub stats: ReadStorage<'a, Stats>,
|
||||||
pub skill_set: ReadStorage<'a, SkillSet>,
|
pub skill_set: ReadStorage<'a, SkillSet>,
|
||||||
pub ability_pool: ReadStorage<'a, AbilityPool>,
|
pub active_abilities: ReadStorage<'a, ActiveAbilities>,
|
||||||
pub buffs: ReadStorage<'a, Buffs>,
|
pub buffs: ReadStorage<'a, Buffs>,
|
||||||
pub auras: ReadStorage<'a, Auras>,
|
pub auras: ReadStorage<'a, Auras>,
|
||||||
pub energy: ReadStorage<'a, Energy>,
|
pub energy: ReadStorage<'a, Energy>,
|
||||||
@ -92,7 +92,7 @@ impl<'a> TrackedComps<'a> {
|
|||||||
.get(entity)
|
.get(entity)
|
||||||
.cloned()
|
.cloned()
|
||||||
.map(|c| comps.push(c.into()));
|
.map(|c| comps.push(c.into()));
|
||||||
self.ability_pool
|
self.active_abilities
|
||||||
.get(entity)
|
.get(entity)
|
||||||
.cloned()
|
.cloned()
|
||||||
.map(|c| comps.push(c.into()));
|
.map(|c| comps.push(c.into()));
|
||||||
@ -192,7 +192,7 @@ pub struct ReadTrackers<'a> {
|
|||||||
pub player: ReadExpect<'a, UpdateTracker<Player>>,
|
pub player: ReadExpect<'a, UpdateTracker<Player>>,
|
||||||
pub stats: ReadExpect<'a, UpdateTracker<Stats>>,
|
pub stats: ReadExpect<'a, UpdateTracker<Stats>>,
|
||||||
pub skill_set: ReadExpect<'a, UpdateTracker<SkillSet>>,
|
pub skill_set: ReadExpect<'a, UpdateTracker<SkillSet>>,
|
||||||
pub ability_pool: ReadExpect<'a, UpdateTracker<AbilityPool>>,
|
pub active_abilities: ReadExpect<'a, UpdateTracker<ActiveAbilities>>,
|
||||||
pub buffs: ReadExpect<'a, UpdateTracker<Buffs>>,
|
pub buffs: ReadExpect<'a, UpdateTracker<Buffs>>,
|
||||||
pub auras: ReadExpect<'a, UpdateTracker<Auras>>,
|
pub auras: ReadExpect<'a, UpdateTracker<Auras>>,
|
||||||
pub energy: ReadExpect<'a, UpdateTracker<Energy>>,
|
pub energy: ReadExpect<'a, UpdateTracker<Energy>>,
|
||||||
@ -229,7 +229,12 @@ impl<'a> ReadTrackers<'a> {
|
|||||||
.with_component(&comps.uid, &*self.player, &comps.player, filter)
|
.with_component(&comps.uid, &*self.player, &comps.player, filter)
|
||||||
.with_component(&comps.uid, &*self.stats, &comps.stats, filter)
|
.with_component(&comps.uid, &*self.stats, &comps.stats, filter)
|
||||||
.with_component(&comps.uid, &*self.skill_set, &comps.skill_set, filter)
|
.with_component(&comps.uid, &*self.skill_set, &comps.skill_set, filter)
|
||||||
.with_component(&comps.uid, &*self.ability_pool, &comps.ability_pool, filter)
|
.with_component(
|
||||||
|
&comps.uid,
|
||||||
|
&*self.active_abilities,
|
||||||
|
&comps.active_abilities,
|
||||||
|
filter,
|
||||||
|
)
|
||||||
.with_component(&comps.uid, &*self.buffs, &comps.buffs, filter)
|
.with_component(&comps.uid, &*self.buffs, &comps.buffs, filter)
|
||||||
.with_component(&comps.uid, &*self.auras, &comps.auras, filter)
|
.with_component(&comps.uid, &*self.auras, &comps.auras, filter)
|
||||||
.with_component(&comps.uid, &*self.energy, &comps.energy, filter)
|
.with_component(&comps.uid, &*self.energy, &comps.energy, filter)
|
||||||
@ -273,7 +278,7 @@ pub struct WriteTrackers<'a> {
|
|||||||
player: WriteExpect<'a, UpdateTracker<Player>>,
|
player: WriteExpect<'a, UpdateTracker<Player>>,
|
||||||
stats: WriteExpect<'a, UpdateTracker<Stats>>,
|
stats: WriteExpect<'a, UpdateTracker<Stats>>,
|
||||||
skill_set: WriteExpect<'a, UpdateTracker<SkillSet>>,
|
skill_set: WriteExpect<'a, UpdateTracker<SkillSet>>,
|
||||||
ability_pool: WriteExpect<'a, UpdateTracker<AbilityPool>>,
|
active_abilities: WriteExpect<'a, UpdateTracker<ActiveAbilities>>,
|
||||||
buffs: WriteExpect<'a, UpdateTracker<Buffs>>,
|
buffs: WriteExpect<'a, UpdateTracker<Buffs>>,
|
||||||
auras: WriteExpect<'a, UpdateTracker<Auras>>,
|
auras: WriteExpect<'a, UpdateTracker<Auras>>,
|
||||||
energy: WriteExpect<'a, UpdateTracker<Energy>>,
|
energy: WriteExpect<'a, UpdateTracker<Energy>>,
|
||||||
@ -304,7 +309,9 @@ fn record_changes(comps: &TrackedComps, trackers: &mut WriteTrackers) {
|
|||||||
trackers.player.record_changes(&comps.player);
|
trackers.player.record_changes(&comps.player);
|
||||||
trackers.stats.record_changes(&comps.stats);
|
trackers.stats.record_changes(&comps.stats);
|
||||||
trackers.skill_set.record_changes(&comps.skill_set);
|
trackers.skill_set.record_changes(&comps.skill_set);
|
||||||
trackers.ability_pool.record_changes(&comps.ability_pool);
|
trackers
|
||||||
|
.active_abilities
|
||||||
|
.record_changes(&comps.active_abilities);
|
||||||
trackers.buffs.record_changes(&comps.buffs);
|
trackers.buffs.record_changes(&comps.buffs);
|
||||||
trackers.auras.record_changes(&comps.auras);
|
trackers.auras.record_changes(&comps.auras);
|
||||||
trackers.energy.record_changes(&comps.energy);
|
trackers.energy.record_changes(&comps.energy);
|
||||||
@ -350,7 +357,7 @@ fn record_changes(comps: &TrackedComps, trackers: &mut WriteTrackers) {
|
|||||||
log_counts!(player, "Players");
|
log_counts!(player, "Players");
|
||||||
log_counts!(stats, "Stats");
|
log_counts!(stats, "Stats");
|
||||||
log_counts!(skill_set, "SkillSet");
|
log_counts!(skill_set, "SkillSet");
|
||||||
log_counts!(ability_pool, "AbilityPool");
|
log_counts!(active_abilities, "ActiveAbilities");
|
||||||
log_counts!(energy, "Energies");
|
log_counts!(energy, "Energies");
|
||||||
log_counts!(combo, "Combos");
|
log_counts!(combo, "Combos");
|
||||||
log_vounts!(health, "Healths");
|
log_vounts!(health, "Healths");
|
||||||
@ -377,7 +384,7 @@ pub fn register_trackers(world: &mut World) {
|
|||||||
world.register_tracker::<Player>();
|
world.register_tracker::<Player>();
|
||||||
world.register_tracker::<Stats>();
|
world.register_tracker::<Stats>();
|
||||||
world.register_tracker::<SkillSet>();
|
world.register_tracker::<SkillSet>();
|
||||||
world.register_tracker::<AbilityPool>();
|
world.register_tracker::<ActiveAbilities>();
|
||||||
world.register_tracker::<Buffs>();
|
world.register_tracker::<Buffs>();
|
||||||
world.register_tracker::<Auras>();
|
world.register_tracker::<Auras>();
|
||||||
world.register_tracker::<Energy>();
|
world.register_tracker::<Energy>();
|
||||||
|
@ -58,14 +58,14 @@ impl State {
|
|||||||
// Removes ability slots if not there and shouldn't be present
|
// Removes ability slots if not there and shouldn't be present
|
||||||
pub fn maintain_abilities(&mut self, client: &client::Client) {
|
pub fn maintain_abilities(&mut self, client: &client::Client) {
|
||||||
use specs::WorldExt;
|
use specs::WorldExt;
|
||||||
if let Some(ability_pool) = client
|
if let Some(active_abilities) = client
|
||||||
.state()
|
.state()
|
||||||
.ecs()
|
.ecs()
|
||||||
.read_storage::<common::comp::AbilityPool>()
|
.read_storage::<common::comp::ActiveAbilities>()
|
||||||
.get(client.entity())
|
.get(client.entity())
|
||||||
{
|
{
|
||||||
use common::comp::ability::AuxiliaryAbility;
|
use common::comp::ability::AuxiliaryAbility;
|
||||||
for ((i, ability), hotbar_slot) in ability_pool
|
for ((i, ability), hotbar_slot) in active_abilities
|
||||||
.abilities
|
.abilities
|
||||||
.iter()
|
.iter()
|
||||||
.enumerate()
|
.enumerate()
|
||||||
@ -82,7 +82,10 @@ impl State {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
self.slots.iter_mut().for_each(|slot| *slot = None)
|
self.slots
|
||||||
|
.iter_mut()
|
||||||
|
.filter(|slot| matches!(slot, Some(SlotContents::Ability(_))))
|
||||||
|
.for_each(|slot| *slot = None)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2640,7 +2640,7 @@ impl Hud {
|
|||||||
let inventories = ecs.read_storage::<comp::Inventory>();
|
let inventories = ecs.read_storage::<comp::Inventory>();
|
||||||
let energies = ecs.read_storage::<comp::Energy>();
|
let energies = ecs.read_storage::<comp::Energy>();
|
||||||
let skillsets = ecs.read_storage::<comp::SkillSet>();
|
let skillsets = ecs.read_storage::<comp::SkillSet>();
|
||||||
let ability_pools = ecs.read_storage::<comp::AbilityPool>();
|
let active_abilities = ecs.read_storage::<comp::ActiveAbilities>();
|
||||||
let character_states = ecs.read_storage::<comp::CharacterState>();
|
let character_states = ecs.read_storage::<comp::CharacterState>();
|
||||||
let controllers = ecs.read_storage::<comp::Controller>();
|
let controllers = ecs.read_storage::<comp::Controller>();
|
||||||
let bodies = ecs.read_storage::<comp::Body>();
|
let bodies = ecs.read_storage::<comp::Body>();
|
||||||
@ -2666,7 +2666,7 @@ impl Hud {
|
|||||||
Some(inventory),
|
Some(inventory),
|
||||||
Some(energy),
|
Some(energy),
|
||||||
Some(skillset),
|
Some(skillset),
|
||||||
Some(ability_pool),
|
Some(active_abilities),
|
||||||
Some(body),
|
Some(body),
|
||||||
Some(_character_state),
|
Some(_character_state),
|
||||||
Some(_controller),
|
Some(_controller),
|
||||||
@ -2675,7 +2675,7 @@ impl Hud {
|
|||||||
inventories.get(entity),
|
inventories.get(entity),
|
||||||
energies.get(entity),
|
energies.get(entity),
|
||||||
skillsets.get(entity),
|
skillsets.get(entity),
|
||||||
ability_pools.get(entity),
|
active_abilities.get(entity),
|
||||||
bodies.get(entity),
|
bodies.get(entity),
|
||||||
character_states.get(entity),
|
character_states.get(entity),
|
||||||
controllers.get(entity).map(|c| &c.inputs),
|
controllers.get(entity).map(|c| &c.inputs),
|
||||||
@ -2691,7 +2691,7 @@ impl Hud {
|
|||||||
inventory,
|
inventory,
|
||||||
energy,
|
energy,
|
||||||
skillset,
|
skillset,
|
||||||
ability_pool,
|
active_abilities,
|
||||||
body,
|
body,
|
||||||
//&character_state,
|
//&character_state,
|
||||||
self.pulse,
|
self.pulse,
|
||||||
|
@ -23,7 +23,7 @@ use common::comp::{
|
|||||||
self,
|
self,
|
||||||
ability::AbilityInput,
|
ability::AbilityInput,
|
||||||
item::{ItemDesc, MaterialStatManifest},
|
item::{ItemDesc, MaterialStatManifest},
|
||||||
Ability, AbilityPool, Body, Energy, Health, Inventory, SkillSet,
|
Ability, ActiveAbilities, Body, Energy, Health, Inventory, SkillSet,
|
||||||
};
|
};
|
||||||
use conrod_core::{
|
use conrod_core::{
|
||||||
color,
|
color,
|
||||||
@ -250,7 +250,7 @@ pub struct Skillbar<'a> {
|
|||||||
inventory: &'a Inventory,
|
inventory: &'a Inventory,
|
||||||
energy: &'a Energy,
|
energy: &'a Energy,
|
||||||
skillset: &'a SkillSet,
|
skillset: &'a SkillSet,
|
||||||
ability_pool: &'a AbilityPool,
|
active_abilities: &'a ActiveAbilities,
|
||||||
body: &'a Body,
|
body: &'a Body,
|
||||||
// character_state: &'a CharacterState,
|
// character_state: &'a CharacterState,
|
||||||
// controller: &'a ControllerInputs,
|
// controller: &'a ControllerInputs,
|
||||||
@ -279,7 +279,7 @@ impl<'a> Skillbar<'a> {
|
|||||||
inventory: &'a Inventory,
|
inventory: &'a Inventory,
|
||||||
energy: &'a Energy,
|
energy: &'a Energy,
|
||||||
skillset: &'a SkillSet,
|
skillset: &'a SkillSet,
|
||||||
ability_pool: &'a AbilityPool,
|
active_abilities: &'a ActiveAbilities,
|
||||||
body: &'a Body,
|
body: &'a Body,
|
||||||
// character_state: &'a CharacterState,
|
// character_state: &'a CharacterState,
|
||||||
pulse: f32,
|
pulse: f32,
|
||||||
@ -303,7 +303,7 @@ impl<'a> Skillbar<'a> {
|
|||||||
inventory,
|
inventory,
|
||||||
energy,
|
energy,
|
||||||
skillset,
|
skillset,
|
||||||
ability_pool,
|
active_abilities,
|
||||||
body,
|
body,
|
||||||
common: widget::CommonBuilder::default(),
|
common: widget::CommonBuilder::default(),
|
||||||
// character_state,
|
// character_state,
|
||||||
@ -519,7 +519,7 @@ impl<'a> Skillbar<'a> {
|
|||||||
self.inventory,
|
self.inventory,
|
||||||
self.energy,
|
self.energy,
|
||||||
self.skillset,
|
self.skillset,
|
||||||
self.ability_pool,
|
self.active_abilities,
|
||||||
self.body,
|
self.body,
|
||||||
);
|
);
|
||||||
|
|
||||||
@ -601,16 +601,16 @@ impl<'a> Skillbar<'a> {
|
|||||||
|
|
||||||
// Helper
|
// Helper
|
||||||
let tooltip_text = |slot| {
|
let tooltip_text = |slot| {
|
||||||
let (hotbar, inventory, _, _, ability_pool, _) = content_source;
|
let (hotbar, inventory, _, _, active_abilities, _) = content_source;
|
||||||
hotbar.get(slot).and_then(|content| match content {
|
hotbar.get(slot).and_then(|content| match content {
|
||||||
hotbar::SlotContents::Inventory(i) => inventory
|
hotbar::SlotContents::Inventory(i) => inventory
|
||||||
.get(i)
|
.get(i)
|
||||||
.map(|item| (item.name(), item.description())),
|
.map(|item| (item.name(), item.description())),
|
||||||
hotbar::SlotContents::Ability(i) => ability_pool
|
hotbar::SlotContents::Ability(i) => active_abilities
|
||||||
.abilities
|
.abilities
|
||||||
.get(i)
|
.get(i)
|
||||||
.and_then(|a| Ability::from(*a).ability_id(Some(inventory)))
|
.and_then(|a| Ability::from(*a).ability_id(Some(inventory)))
|
||||||
.and_then(|id| util::ability_description(id)),
|
.map(|id| util::ability_description(id)),
|
||||||
})
|
})
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -680,7 +680,7 @@ impl<'a> Skillbar<'a> {
|
|||||||
.set(state.ids.m1_slot_bg, ui);
|
.set(state.ids.m1_slot_bg, ui);
|
||||||
|
|
||||||
let primary_ability_id =
|
let primary_ability_id =
|
||||||
Ability::from(self.ability_pool.primary).ability_id(Some(self.inventory));
|
Ability::from(self.active_abilities.primary).ability_id(Some(self.inventory));
|
||||||
|
|
||||||
Button::image(
|
Button::image(
|
||||||
primary_ability_id.map_or(self.imgs.nothing, |id| util::ability_image(self.imgs, id)),
|
primary_ability_id.map_or(self.imgs.nothing, |id| util::ability_image(self.imgs, id)),
|
||||||
@ -695,7 +695,7 @@ impl<'a> Skillbar<'a> {
|
|||||||
.set(state.ids.m2_slot_bg, ui);
|
.set(state.ids.m2_slot_bg, ui);
|
||||||
|
|
||||||
let secondary_ability_id =
|
let secondary_ability_id =
|
||||||
Ability::from(self.ability_pool.secondary).ability_id(Some(self.inventory));
|
Ability::from(self.active_abilities.secondary).ability_id(Some(self.inventory));
|
||||||
|
|
||||||
Button::image(
|
Button::image(
|
||||||
secondary_ability_id.map_or(self.imgs.nothing, |id| util::ability_image(self.imgs, id)),
|
secondary_ability_id.map_or(self.imgs.nothing, |id| util::ability_image(self.imgs, id)),
|
||||||
@ -705,12 +705,12 @@ impl<'a> Skillbar<'a> {
|
|||||||
.image_color(
|
.image_color(
|
||||||
if self.energy.current()
|
if self.energy.current()
|
||||||
>= self
|
>= self
|
||||||
.ability_pool
|
.active_abilities
|
||||||
.activate_ability(
|
.activate_ability(
|
||||||
AbilityInput::Secondary,
|
AbilityInput::Secondary,
|
||||||
Some(self.inventory),
|
Some(self.inventory),
|
||||||
self.skillset,
|
self.skillset,
|
||||||
self.body,
|
Some(self.body),
|
||||||
)
|
)
|
||||||
.map_or(0.0, |(a, _)| a.get_energy_cost())
|
.map_or(0.0, |(a, _)| a.get_energy_cost())
|
||||||
{
|
{
|
||||||
|
@ -6,7 +6,8 @@ use super::{
|
|||||||
};
|
};
|
||||||
use crate::ui::slot::{self, SlotKey, SumSlot};
|
use crate::ui::slot::{self, SlotKey, SumSlot};
|
||||||
use common::comp::{
|
use common::comp::{
|
||||||
ability::AbilityInput, slot::InvSlotId, Ability, AbilityPool, Body, Energy, Inventory, SkillSet,
|
ability::AbilityInput, slot::InvSlotId, Ability, ActiveAbilities, Body, Energy, Inventory,
|
||||||
|
SkillSet,
|
||||||
};
|
};
|
||||||
use conrod_core::{image, Color};
|
use conrod_core::{image, Color};
|
||||||
use specs::Entity as EcsEntity;
|
use specs::Entity as EcsEntity;
|
||||||
@ -117,7 +118,7 @@ type HotbarSource<'a> = (
|
|||||||
&'a Inventory,
|
&'a Inventory,
|
||||||
&'a Energy,
|
&'a Energy,
|
||||||
&'a SkillSet,
|
&'a SkillSet,
|
||||||
&'a AbilityPool,
|
&'a ActiveAbilities,
|
||||||
&'a Body,
|
&'a Body,
|
||||||
);
|
);
|
||||||
type HotbarImageSource<'a> = (&'a ItemImgs, &'a img_ids::Imgs);
|
type HotbarImageSource<'a> = (&'a ItemImgs, &'a img_ids::Imgs);
|
||||||
@ -127,7 +128,7 @@ impl<'a> SlotKey<HotbarSource<'a>, HotbarImageSource<'a>> for HotbarSlot {
|
|||||||
|
|
||||||
fn image_key(
|
fn image_key(
|
||||||
&self,
|
&self,
|
||||||
(hotbar, inventory, energy, skillset, ability_pool, body): &HotbarSource<'a>,
|
(hotbar, inventory, energy, skillset, active_abilities, body): &HotbarSource<'a>,
|
||||||
) -> Option<(Self::ImageKey, Option<Color>)> {
|
) -> Option<(Self::ImageKey, Option<Color>)> {
|
||||||
hotbar.get(*self).and_then(|contents| match contents {
|
hotbar.get(*self).and_then(|contents| match contents {
|
||||||
hotbar::SlotContents::Inventory(idx) => inventory
|
hotbar::SlotContents::Inventory(idx) => inventory
|
||||||
@ -135,7 +136,7 @@ impl<'a> SlotKey<HotbarSource<'a>, HotbarImageSource<'a>> for HotbarSlot {
|
|||||||
.map(|item| HotbarImage::Item(item.into()))
|
.map(|item| HotbarImage::Item(item.into()))
|
||||||
.map(|i| (i, None)),
|
.map(|i| (i, None)),
|
||||||
hotbar::SlotContents::Ability(i) => {
|
hotbar::SlotContents::Ability(i) => {
|
||||||
let ability_id = ability_pool
|
let ability_id = active_abilities
|
||||||
.abilities
|
.abilities
|
||||||
.get(i)
|
.get(i)
|
||||||
.and_then(|a| Ability::from(*a).ability_id(Some(inventory)));
|
.and_then(|a| Ability::from(*a).ability_id(Some(inventory)));
|
||||||
@ -143,12 +144,12 @@ impl<'a> SlotKey<HotbarSource<'a>, HotbarImageSource<'a>> for HotbarSlot {
|
|||||||
ability_id
|
ability_id
|
||||||
.map(|id| HotbarImage::Ability(id.to_string()))
|
.map(|id| HotbarImage::Ability(id.to_string()))
|
||||||
.and_then(|image| {
|
.and_then(|image| {
|
||||||
ability_pool
|
active_abilities
|
||||||
.activate_ability(
|
.activate_ability(
|
||||||
AbilityInput::Auxiliary(i),
|
AbilityInput::Auxiliary(i),
|
||||||
Some(inventory),
|
Some(inventory),
|
||||||
skillset,
|
skillset,
|
||||||
body,
|
Some(body),
|
||||||
)
|
)
|
||||||
.map(|(ability, _)| {
|
.map(|(ability, _)| {
|
||||||
(
|
(
|
||||||
|
@ -326,53 +326,57 @@ pub fn ability_image(imgs: &img_ids::Imgs, ability_id: &str) -> image::Id {
|
|||||||
}
|
}
|
||||||
|
|
||||||
#[rustfmt::skip]
|
#[rustfmt::skip]
|
||||||
pub fn ability_description(ability_id: &str) -> Option<(&str, &str)> {
|
pub fn ability_description(ability_id: &str) -> (&str, &str) {
|
||||||
match ability_id {
|
match ability_id {
|
||||||
// Debug stick
|
// Debug stick
|
||||||
"common.abilities.debug.possess" => Some((
|
"common.abilities.debug.possess" => (
|
||||||
"Possessing Arrow",
|
"Possessing Arrow",
|
||||||
"\n\
|
"\n\
|
||||||
Shoots a poisonous arrow.\n\
|
Shoots a poisonous arrow.\n\
|
||||||
Lets you control your target.",
|
Lets you control your target.",
|
||||||
)),
|
),
|
||||||
// Sword
|
// Sword
|
||||||
"common.abilities.sword.spin" => Some((
|
"common.abilities.sword.spin" => (
|
||||||
"Whirlwind",
|
"Whirlwind",
|
||||||
"\n\
|
"\n\
|
||||||
Move forward while spinning with your sword.",
|
Move forward while spinning with your sword.",
|
||||||
)),
|
),
|
||||||
// Axe
|
// Axe
|
||||||
"common.abilities.axe.leap" => Some((
|
"common.abilities.axe.leap" => (
|
||||||
"Axe Jump",
|
"Axe Jump",
|
||||||
"\n\
|
"\n\
|
||||||
A jump with the slashing leap to position of cursor.",
|
A jump with the slashing leap to position of cursor.",
|
||||||
)),
|
),
|
||||||
// Hammer
|
// Hammer
|
||||||
"common.abilities.hammer.leap" => Some((
|
"common.abilities.hammer.leap" => (
|
||||||
"Smash of Doom",
|
"Smash of Doom",
|
||||||
"\n\
|
"\n\
|
||||||
An AOE attack with knockback.\n\
|
An AOE attack with knockback.\n\
|
||||||
Leaps to position of cursor.",
|
Leaps to position of cursor.",
|
||||||
)),
|
),
|
||||||
// Bow
|
// Bow
|
||||||
"common.abilities.bow.shotgun" => Some((
|
"common.abilities.bow.shotgun" => (
|
||||||
"Burst",
|
"Burst",
|
||||||
"\n\
|
"\n\
|
||||||
Launches a burst of arrows",
|
Launches a burst of arrows",
|
||||||
)),
|
),
|
||||||
// Staff
|
// Staff
|
||||||
"common.abilities.staff.fireshockwave" => Some((
|
"common.abilities.staff.fireshockwave" => (
|
||||||
"Ring of Fire",
|
"Ring of Fire",
|
||||||
"\n\
|
"\n\
|
||||||
Ignites the ground with fiery shockwave.",
|
Ignites the ground with fiery shockwave.",
|
||||||
)),
|
),
|
||||||
// Sceptre
|
// Sceptre
|
||||||
"common.abilities.sceptre.wardingaura" => Some((
|
"common.abilities.sceptre.wardingaura" => (
|
||||||
"Thorn Bulwark",
|
"Thorn Bulwark",
|
||||||
"\n\
|
"\n\
|
||||||
Protects you and your group with thorns\n\
|
Protects you and your group with thorns\n\
|
||||||
for a short amount of time.",
|
for a short amount of time.",
|
||||||
)),
|
),
|
||||||
_ => None,
|
_ => (
|
||||||
|
"Ability as no title",
|
||||||
|
"\n\
|
||||||
|
Ability has no description."
|
||||||
|
),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user