mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
General combat skill tree.
UI for general skill tree
This commit is contained in:
parent
58d9534496
commit
48c98b11cf
@ -1,5 +1,6 @@
|
|||||||
({
|
({
|
||||||
General(HealthIncrease): Some(10),
|
General(HealthIncrease): Some(10),
|
||||||
|
General(EnergyIncrease): Some(5),
|
||||||
Sword(TsDamage): Some(3),
|
Sword(TsDamage): Some(3),
|
||||||
Sword(TsRegen): Some(2),
|
Sword(TsRegen): Some(2),
|
||||||
Sword(TsSpeed): Some(3),
|
Sword(TsSpeed): Some(3),
|
||||||
@ -69,4 +70,7 @@
|
|||||||
Sceptre(PRadius): Some(2),
|
Sceptre(PRadius): Some(2),
|
||||||
Sceptre(PCost): Some(2),
|
Sceptre(PCost): Some(2),
|
||||||
Sceptre(PProjSpeed): Some(2),
|
Sceptre(PProjSpeed): Some(2),
|
||||||
|
Roll(Cost): Some(2),
|
||||||
|
Roll(Strength): Some(2),
|
||||||
|
Roll(Duration): Some(2),
|
||||||
})
|
})
|
@ -1,10 +1,7 @@
|
|||||||
({
|
({
|
||||||
UnlockGroup(Weapon(Sword)): {General(HealthIncrease): Some(1)},
|
Roll(Cost): {Roll(ImmuneMelee): None},
|
||||||
UnlockGroup(Weapon(Axe)): {General(HealthIncrease): Some(1)},
|
Roll(Strength): {Roll(ImmuneMelee): None},
|
||||||
UnlockGroup(Weapon(Hammer)): {General(HealthIncrease): Some(1)},
|
Roll(Duration): {Roll(ImmuneMelee): None},
|
||||||
UnlockGroup(Weapon(Bow)): {General(HealthIncrease): Some(1)},
|
|
||||||
UnlockGroup(Weapon(Staff)): {General(HealthIncrease): Some(1)},
|
|
||||||
UnlockGroup(Weapon(Sceptre)): {General(HealthIncrease): Some(1)},
|
|
||||||
Sword(TsDamage): {Sword(TsCombo): None},
|
Sword(TsDamage): {Sword(TsCombo): None},
|
||||||
Sword(TsRegen): {Sword(TsCombo): None},
|
Sword(TsRegen): {Sword(TsCombo): None},
|
||||||
Sword(TsSpeed): {Sword(TsCombo): None},
|
Sword(TsSpeed): {Sword(TsCombo): None},
|
||||||
|
@ -1,12 +1,17 @@
|
|||||||
({
|
({
|
||||||
General: [
|
General: [
|
||||||
General(HealthIncrease),
|
General(HealthIncrease),
|
||||||
|
General(EnergyIncrease),
|
||||||
UnlockGroup(Weapon(Sword)),
|
UnlockGroup(Weapon(Sword)),
|
||||||
UnlockGroup(Weapon(Axe)),
|
UnlockGroup(Weapon(Axe)),
|
||||||
UnlockGroup(Weapon(Hammer)),
|
UnlockGroup(Weapon(Hammer)),
|
||||||
UnlockGroup(Weapon(Bow)),
|
UnlockGroup(Weapon(Bow)),
|
||||||
UnlockGroup(Weapon(Staff)),
|
UnlockGroup(Weapon(Staff)),
|
||||||
UnlockGroup(Weapon(Sceptre)),
|
UnlockGroup(Weapon(Sceptre)),
|
||||||
|
Roll(ImmuneMelee),
|
||||||
|
Roll(Cost),
|
||||||
|
Roll(Strength),
|
||||||
|
Roll(Duration),
|
||||||
],
|
],
|
||||||
Weapon(Sword): [
|
Weapon(Sword): [
|
||||||
Sword(InterruptingAttacks),
|
Sword(InterruptingAttacks),
|
||||||
|
@ -1385,6 +1385,29 @@ impl Client {
|
|||||||
GeneralSkill::HealthIncrease,
|
GeneralSkill::HealthIncrease,
|
||||||
)));
|
)));
|
||||||
},
|
},
|
||||||
|
"@unlock energy" => {
|
||||||
|
self.send_msg(ClientGeneral::UnlockSkill(Skill::General(
|
||||||
|
GeneralSkill::EnergyIncrease,
|
||||||
|
)));
|
||||||
|
},
|
||||||
|
"@unlock roll melee" => {
|
||||||
|
self.send_msg(ClientGeneral::UnlockSkill(Skill::Roll(
|
||||||
|
RollSkill::ImmuneMelee,
|
||||||
|
)));
|
||||||
|
},
|
||||||
|
"@unlock roll cost" => {
|
||||||
|
self.send_msg(ClientGeneral::UnlockSkill(Skill::Roll(RollSkill::Cost)));
|
||||||
|
},
|
||||||
|
"@unlock roll strength" => {
|
||||||
|
self.send_msg(ClientGeneral::UnlockSkill(Skill::Roll(
|
||||||
|
RollSkill::Strength,
|
||||||
|
)));
|
||||||
|
},
|
||||||
|
"@unlock roll duration" => {
|
||||||
|
self.send_msg(ClientGeneral::UnlockSkill(Skill::Roll(
|
||||||
|
RollSkill::Duration,
|
||||||
|
)));
|
||||||
|
},
|
||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
|
@ -120,6 +120,7 @@ pub enum CharacterAbility {
|
|||||||
movement_duration: u64,
|
movement_duration: u64,
|
||||||
recover_duration: u64,
|
recover_duration: u64,
|
||||||
roll_strength: f32,
|
roll_strength: f32,
|
||||||
|
immune_melee: bool,
|
||||||
},
|
},
|
||||||
ComboMelee {
|
ComboMelee {
|
||||||
stage_data: Vec<combo_melee::Stage<u64>>,
|
stage_data: Vec<combo_melee::Stage<u64>>,
|
||||||
@ -305,11 +306,12 @@ impl CharacterAbility {
|
|||||||
|
|
||||||
pub fn default_roll() -> CharacterAbility {
|
pub fn default_roll() -> CharacterAbility {
|
||||||
CharacterAbility::Roll {
|
CharacterAbility::Roll {
|
||||||
energy_cost: 100,
|
energy_cost: 150,
|
||||||
buildup_duration: 100,
|
buildup_duration: 100,
|
||||||
movement_duration: 250,
|
movement_duration: 250,
|
||||||
recover_duration: 150,
|
recover_duration: 150,
|
||||||
roll_strength: 2.5,
|
roll_strength: 2.5,
|
||||||
|
immune_melee: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -502,11 +504,10 @@ impl CharacterAbility {
|
|||||||
skills: &HashMap<skills::Skill, skills::Level>,
|
skills: &HashMap<skills::Skill, skills::Level>,
|
||||||
tool: Option<ToolKind>,
|
tool: Option<ToolKind>,
|
||||||
) -> Self {
|
) -> Self {
|
||||||
use skills::Skill::*;
|
use skills::Skill::{self, *};
|
||||||
use CharacterAbility::*;
|
use CharacterAbility::*;
|
||||||
if let Some(tool) = tool {
|
|
||||||
match tool {
|
match tool {
|
||||||
ToolKind::Sword => {
|
Some(ToolKind::Sword) => {
|
||||||
use skills::SwordSkill::*;
|
use skills::SwordSkill::*;
|
||||||
match self {
|
match self {
|
||||||
ComboMelee {
|
ComboMelee {
|
||||||
@ -534,9 +535,8 @@ impl CharacterAbility {
|
|||||||
*speed_increase *= speed_level / speed_segments;
|
*speed_increase *= speed_level / speed_segments;
|
||||||
*max_speed_increase *= speed_level / speed_segments;
|
*max_speed_increase *= speed_level / speed_segments;
|
||||||
}
|
}
|
||||||
let energy_level = if let Some(level) =
|
let energy_level =
|
||||||
skills.get(&Sword(TsRegen)).copied().flatten()
|
if let Some(level) = skills.get(&Sword(TsRegen)).copied().flatten() {
|
||||||
{
|
|
||||||
level
|
level
|
||||||
} else {
|
} else {
|
||||||
0
|
0
|
||||||
@ -609,14 +609,13 @@ impl CharacterAbility {
|
|||||||
*energy_cost =
|
*energy_cost =
|
||||||
(*energy_cost as f32 * 0.75_f32.powi(level.into())) as u32;
|
(*energy_cost as f32 * 0.75_f32.powi(level.into())) as u32;
|
||||||
}
|
}
|
||||||
*num_spins = skills.get(&Sword(SSpins)).copied().flatten().unwrap_or(0)
|
*num_spins =
|
||||||
as u32
|
skills.get(&Sword(SSpins)).copied().flatten().unwrap_or(0) as u32 + 1;
|
||||||
+ 1;
|
|
||||||
},
|
},
|
||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
ToolKind::Axe => {
|
Some(ToolKind::Axe) => {
|
||||||
use skills::AxeSkill::*;
|
use skills::AxeSkill::*;
|
||||||
match self {
|
match self {
|
||||||
ComboMelee {
|
ComboMelee {
|
||||||
@ -708,7 +707,7 @@ impl CharacterAbility {
|
|||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
ToolKind::Hammer => {
|
Some(ToolKind::Hammer) => {
|
||||||
use skills::HammerSkill::*;
|
use skills::HammerSkill::*;
|
||||||
match self {
|
match self {
|
||||||
ComboMelee {
|
ComboMelee {
|
||||||
@ -719,24 +718,21 @@ impl CharacterAbility {
|
|||||||
ref mut scales_from_combo,
|
ref mut scales_from_combo,
|
||||||
..
|
..
|
||||||
} => {
|
} => {
|
||||||
if let Some(level) = skills.get(&Hammer(SsKnockback)).copied().flatten()
|
if let Some(level) = skills.get(&Hammer(SsKnockback)).copied().flatten() {
|
||||||
{
|
|
||||||
*stage_data = (*stage_data)
|
*stage_data = (*stage_data)
|
||||||
.iter()
|
.iter()
|
||||||
.map(|s| s.modify_strike(1.5_f32.powi(level.into())))
|
.map(|s| s.modify_strike(1.5_f32.powi(level.into())))
|
||||||
.collect::<Vec<combo_melee::Stage<u64>>>();
|
.collect::<Vec<combo_melee::Stage<u64>>>();
|
||||||
}
|
}
|
||||||
let speed_segments =
|
let speed_segments = Hammer(SsSpeed).get_max_level().unwrap_or(1) as f32;
|
||||||
Hammer(SsSpeed).get_max_level().unwrap_or(1) as f32;
|
|
||||||
let speed_level =
|
let speed_level =
|
||||||
skills.get(&Hammer(SsSpeed)).copied().flatten().unwrap_or(0) as f32;
|
skills.get(&Hammer(SsSpeed)).copied().flatten().unwrap_or(0) as f32;
|
||||||
{
|
{
|
||||||
*speed_increase *= speed_level / speed_segments;
|
*speed_increase *= speed_level / speed_segments;
|
||||||
*max_speed_increase *= speed_level / speed_segments;
|
*max_speed_increase *= speed_level / speed_segments;
|
||||||
}
|
}
|
||||||
let energy_level = if let Some(level) =
|
let energy_level =
|
||||||
skills.get(&Hammer(SsRegen)).copied().flatten()
|
if let Some(level) = skills.get(&Hammer(SsRegen)).copied().flatten() {
|
||||||
{
|
|
||||||
level
|
level
|
||||||
} else {
|
} else {
|
||||||
0
|
0
|
||||||
@ -746,8 +742,7 @@ impl CharacterAbility {
|
|||||||
* ((energy_level + 1) * stage_data.len() as u16) as f32
|
* ((energy_level + 1) * stage_data.len() as u16) as f32
|
||||||
/ ((Hammer(SsRegen).get_max_level().unwrap() + 1)
|
/ ((Hammer(SsRegen).get_max_level().unwrap() + 1)
|
||||||
* stage_data.len() as u16)
|
* stage_data.len() as u16)
|
||||||
as f32)
|
as f32) as u32;
|
||||||
as u32;
|
|
||||||
}
|
}
|
||||||
*scales_from_combo = skills
|
*scales_from_combo = skills
|
||||||
.get(&Hammer(SsDamage))
|
.get(&Hammer(SsDamage))
|
||||||
@ -767,8 +762,7 @@ impl CharacterAbility {
|
|||||||
*scaled_damage =
|
*scaled_damage =
|
||||||
(*scaled_damage as f32 * 1.25_f32.powi(level.into())) as u32;
|
(*scaled_damage as f32 * 1.25_f32.powi(level.into())) as u32;
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Hammer(CKnockback)).copied().flatten()
|
if let Some(level) = skills.get(&Hammer(CKnockback)).copied().flatten() {
|
||||||
{
|
|
||||||
*scaled_knockback *= 1.5_f32.powi(level.into());
|
*scaled_knockback *= 1.5_f32.powi(level.into());
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Hammer(CDrain)).copied().flatten() {
|
if let Some(level) = skills.get(&Hammer(CDrain)).copied().flatten() {
|
||||||
@ -792,8 +786,7 @@ impl CharacterAbility {
|
|||||||
*base_damage =
|
*base_damage =
|
||||||
(*base_damage as f32 * 1.4_f32.powi(level.into())) as u32;
|
(*base_damage as f32 * 1.4_f32.powi(level.into())) as u32;
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Hammer(LKnockback)).copied().flatten()
|
if let Some(level) = skills.get(&Hammer(LKnockback)).copied().flatten() {
|
||||||
{
|
|
||||||
*knockback *= 1.4_f32.powi(level.into());
|
*knockback *= 1.4_f32.powi(level.into());
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Hammer(LCost)).copied().flatten() {
|
if let Some(level) = skills.get(&Hammer(LCost)).copied().flatten() {
|
||||||
@ -811,7 +804,7 @@ impl CharacterAbility {
|
|||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
ToolKind::Bow => {
|
Some(ToolKind::Bow) => {
|
||||||
use skills::BowSkill::*;
|
use skills::BowSkill::*;
|
||||||
match self {
|
match self {
|
||||||
BasicRanged {
|
BasicRanged {
|
||||||
@ -897,7 +890,7 @@ impl CharacterAbility {
|
|||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
ToolKind::Staff => {
|
Some(ToolKind::Staff) => {
|
||||||
use skills::StaffSkill::*;
|
use skills::StaffSkill::*;
|
||||||
match self {
|
match self {
|
||||||
BasicRanged {
|
BasicRanged {
|
||||||
@ -960,9 +953,8 @@ impl CharacterAbility {
|
|||||||
*knockback = knockback.modify_strength(1.3_f32.powi(level.into()));
|
*knockback = knockback.modify_strength(1.3_f32.powi(level.into()));
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Staff(SRange)).copied().flatten() {
|
if let Some(level) = skills.get(&Staff(SRange)).copied().flatten() {
|
||||||
*shockwave_duration = (*shockwave_duration as f32
|
*shockwave_duration =
|
||||||
* 1.2_f32.powi(level.into()))
|
(*shockwave_duration as f32 * 1.2_f32.powi(level.into())) as u64;
|
||||||
as u64;
|
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Staff(SCost)).copied().flatten() {
|
if let Some(level) = skills.get(&Staff(SCost)).copied().flatten() {
|
||||||
*energy_cost =
|
*energy_cost =
|
||||||
@ -972,7 +964,7 @@ impl CharacterAbility {
|
|||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
ToolKind::Sceptre => {
|
Some(ToolKind::Sceptre) => {
|
||||||
use skills::SceptreSkill::*;
|
use skills::SceptreSkill::*;
|
||||||
match self {
|
match self {
|
||||||
BasicBeam {
|
BasicBeam {
|
||||||
@ -997,8 +989,7 @@ impl CharacterAbility {
|
|||||||
// Duration modified to keep velocity constant
|
// Duration modified to keep velocity constant
|
||||||
*beam_duration = (*beam_duration as f32 * range_mod) as u64;
|
*beam_duration = (*beam_duration as f32 * range_mod) as u64;
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Sceptre(BLifesteal)).copied().flatten()
|
if let Some(level) = skills.get(&Sceptre(BLifesteal)).copied().flatten() {
|
||||||
{
|
|
||||||
*lifesteal_eff *= 1.5_f32.powi(level.into());
|
*lifesteal_eff *= 1.5_f32.powi(level.into());
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Sceptre(BRegen)).copied().flatten() {
|
if let Some(level) = skills.get(&Sceptre(BRegen)).copied().flatten() {
|
||||||
@ -1032,23 +1023,43 @@ impl CharacterAbility {
|
|||||||
let heal = 1.2_f32.powi(heal_level.into());
|
let heal = 1.2_f32.powi(heal_level.into());
|
||||||
let power = 1.2_f32.powi(damage_level.into());
|
let power = 1.2_f32.powi(damage_level.into());
|
||||||
let range = 1.4_f32.powi(range_level.into());
|
let range = 1.4_f32.powi(range_level.into());
|
||||||
*projectile =
|
*projectile = projectile.modified_projectile(power, 1_f32, range, heal);
|
||||||
projectile.modified_projectile(power, 1_f32, range, heal);
|
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Sceptre(PCost)).copied().flatten() {
|
if let Some(level) = skills.get(&Sceptre(PCost)).copied().flatten() {
|
||||||
*energy_cost =
|
*energy_cost =
|
||||||
(*energy_cost as f32 * 0.8_f32.powi(level.into())) as u32;
|
(*energy_cost as f32 * 0.8_f32.powi(level.into())) as u32;
|
||||||
}
|
}
|
||||||
if let Some(level) = skills.get(&Sceptre(PProjSpeed)).copied().flatten()
|
if let Some(level) = skills.get(&Sceptre(PProjSpeed)).copied().flatten() {
|
||||||
{
|
|
||||||
*projectile_speed *= 1.25_f32.powi(level.into());
|
*projectile_speed *= 1.25_f32.powi(level.into());
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
_ => {},
|
_ => {},
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
_ => {},
|
None => {
|
||||||
|
use skills::RollSkill::*;
|
||||||
|
if let CharacterAbility::Roll {
|
||||||
|
ref mut immune_melee,
|
||||||
|
ref mut energy_cost,
|
||||||
|
ref mut roll_strength,
|
||||||
|
ref mut movement_duration,
|
||||||
|
..
|
||||||
|
} = self
|
||||||
|
{
|
||||||
|
*immune_melee = skills.contains_key(&Skill::Roll(ImmuneMelee));
|
||||||
|
if let Some(level) = skills.get(&Skill::Roll(Cost)).copied().flatten() {
|
||||||
|
*energy_cost = (*energy_cost as f32 * 0.8_f32.powi(level.into())) as u32;
|
||||||
}
|
}
|
||||||
|
if let Some(level) = skills.get(&Skill::Roll(Strength)).copied().flatten() {
|
||||||
|
*roll_strength *= 1.3_f32.powi(level.into());
|
||||||
|
}
|
||||||
|
if let Some(level) = skills.get(&Skill::Roll(Duration)).copied().flatten() {
|
||||||
|
*movement_duration =
|
||||||
|
(*movement_duration as f32 * 2_f32.powi(level.into())) as u64;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
_ => {},
|
||||||
}
|
}
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
@ -1165,12 +1176,14 @@ impl From<(&CharacterAbility, AbilityKey)> for CharacterState {
|
|||||||
movement_duration,
|
movement_duration,
|
||||||
recover_duration,
|
recover_duration,
|
||||||
roll_strength,
|
roll_strength,
|
||||||
|
immune_melee,
|
||||||
} => CharacterState::Roll(roll::Data {
|
} => CharacterState::Roll(roll::Data {
|
||||||
static_data: roll::StaticData {
|
static_data: roll::StaticData {
|
||||||
buildup_duration: Duration::from_millis(*buildup_duration),
|
buildup_duration: Duration::from_millis(*buildup_duration),
|
||||||
movement_duration: Duration::from_millis(*movement_duration),
|
movement_duration: Duration::from_millis(*movement_duration),
|
||||||
recover_duration: Duration::from_millis(*recover_duration),
|
recover_duration: Duration::from_millis(*recover_duration),
|
||||||
roll_strength: *roll_strength,
|
roll_strength: *roll_strength,
|
||||||
|
immune_melee: *immune_melee,
|
||||||
},
|
},
|
||||||
timer: Duration::default(),
|
timer: Duration::default(),
|
||||||
stage_section: StageSection::Buildup,
|
stage_section: StageSection::Buildup,
|
||||||
|
@ -256,6 +256,7 @@ impl Body {
|
|||||||
biped_large::Species::Dullahan => 4000,
|
biped_large::Species::Dullahan => 4000,
|
||||||
_ => 3000,
|
_ => 3000,
|
||||||
},
|
},
|
||||||
|
Body::Humanoid(_) => 750,
|
||||||
_ => 1000,
|
_ => 1000,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -263,7 +264,7 @@ impl Body {
|
|||||||
#[allow(unreachable_patterns)]
|
#[allow(unreachable_patterns)]
|
||||||
pub fn base_health(&self) -> u32 {
|
pub fn base_health(&self) -> u32 {
|
||||||
match self {
|
match self {
|
||||||
Body::Humanoid(_) => 400,
|
Body::Humanoid(_) => 500,
|
||||||
Body::QuadrupedSmall(quadruped_small) => match quadruped_small.species {
|
Body::QuadrupedSmall(quadruped_small) => match quadruped_small.species {
|
||||||
quadruped_small::Species::Boar => 360,
|
quadruped_small::Species::Boar => 360,
|
||||||
quadruped_small::Species::Batfox => 200,
|
quadruped_small::Species::Batfox => 200,
|
||||||
|
@ -143,6 +143,10 @@ impl CharacterState {
|
|||||||
|
|
||||||
pub fn is_dodge(&self) -> bool { matches!(self, CharacterState::Roll(_)) }
|
pub fn is_dodge(&self) -> bool { matches!(self, CharacterState::Roll(_)) }
|
||||||
|
|
||||||
|
pub fn is_melee_dodge(&self) -> bool {
|
||||||
|
matches!(self, CharacterState::Roll(d) if d.static_data.immune_melee)
|
||||||
|
}
|
||||||
|
|
||||||
/// Compares for shallow equality (does not check internal struct equality)
|
/// Compares for shallow equality (does not check internal struct equality)
|
||||||
pub fn same_variant(&self, other: &Self) -> bool {
|
pub fn same_variant(&self, other: &Self) -> bool {
|
||||||
// Check if state is the same without looking at the inner data
|
// Check if state is the same without looking at the inner data
|
||||||
|
@ -72,6 +72,7 @@ pub enum Skill {
|
|||||||
Staff(StaffSkill),
|
Staff(StaffSkill),
|
||||||
Sceptre(SceptreSkill),
|
Sceptre(SceptreSkill),
|
||||||
UnlockGroup(SkillGroupType),
|
UnlockGroup(SkillGroupType),
|
||||||
|
Roll(RollSkill),
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
||||||
@ -202,6 +203,15 @@ pub enum SceptreSkill {
|
|||||||
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
||||||
pub enum GeneralSkill {
|
pub enum GeneralSkill {
|
||||||
HealthIncrease,
|
HealthIncrease,
|
||||||
|
EnergyIncrease,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
||||||
|
pub enum RollSkill {
|
||||||
|
ImmuneMelee,
|
||||||
|
Cost,
|
||||||
|
Strength,
|
||||||
|
Duration,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
#[derive(Clone, Copy, Debug, Hash, PartialEq, Eq, Serialize, Deserialize)]
|
||||||
@ -237,6 +247,8 @@ impl SkillGroup {
|
|||||||
pub struct SkillSet {
|
pub struct SkillSet {
|
||||||
pub skill_groups: Vec<SkillGroup>,
|
pub skill_groups: Vec<SkillGroup>,
|
||||||
pub skills: HashMap<Skill, Level>,
|
pub skills: HashMap<Skill, Level>,
|
||||||
|
pub modify_health: bool,
|
||||||
|
pub modify_energy: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub type Level = Option<u16>;
|
pub type Level = Option<u16>;
|
||||||
@ -249,6 +261,8 @@ impl Default for SkillSet {
|
|||||||
Self {
|
Self {
|
||||||
skill_groups: vec![SkillGroup::new(SkillGroupType::General)],
|
skill_groups: vec![SkillGroup::new(SkillGroupType::General)],
|
||||||
skills: HashMap::new(),
|
skills: HashMap::new(),
|
||||||
|
modify_health: false,
|
||||||
|
modify_energy: false,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -312,6 +326,12 @@ impl SkillSet {
|
|||||||
if let Skill::UnlockGroup(group) = skill {
|
if let Skill::UnlockGroup(group) = skill {
|
||||||
self.unlock_skill_group(group);
|
self.unlock_skill_group(group);
|
||||||
}
|
}
|
||||||
|
if matches!(skill, Skill::General(GeneralSkill::HealthIncrease)) {
|
||||||
|
self.modify_health = true;
|
||||||
|
}
|
||||||
|
if matches!(skill, Skill::General(GeneralSkill::EnergyIncrease)) {
|
||||||
|
self.modify_energy = true;
|
||||||
|
}
|
||||||
self.skills.insert(skill, next_level);
|
self.skills.insert(skill, next_level);
|
||||||
} else {
|
} else {
|
||||||
warn!("Tried to unlock skill for skill group with insufficient SP");
|
warn!("Tried to unlock skill for skill group with insufficient SP");
|
||||||
|
@ -19,6 +19,8 @@ pub struct StaticData {
|
|||||||
pub recover_duration: Duration,
|
pub recover_duration: Duration,
|
||||||
/// Affects the speed and distance of the roll
|
/// Affects the speed and distance of the roll
|
||||||
pub roll_strength: f32,
|
pub roll_strength: f32,
|
||||||
|
/// Affects whether you are immune to melee attacks while rolling
|
||||||
|
pub immune_melee: bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Copy, Clone, Debug, PartialEq, Serialize, Deserialize)]
|
#[derive(Copy, Clone, Debug, PartialEq, Serialize, Deserialize)]
|
||||||
|
@ -551,21 +551,26 @@ pub fn handle_dodge_input(data: &JoinData, update: &mut StateUpdate) {
|
|||||||
if let Some(ability) = data
|
if let Some(ability) = data
|
||||||
.inventory
|
.inventory
|
||||||
.equipped(EquipSlot::Mainhand)
|
.equipped(EquipSlot::Mainhand)
|
||||||
.and_then(|i| i.item_config_expect().dodge_ability.as_ref())
|
.and_then(|i| {
|
||||||
|
i.item_config_expect().dodge_ability.as_ref().map(|a| {
|
||||||
|
a.clone()
|
||||||
|
.adjusted_by_skills(&data.stats.skill_set.skills, None)
|
||||||
|
})
|
||||||
|
})
|
||||||
.filter(|ability| ability.requirements_paid(data, update))
|
.filter(|ability| ability.requirements_paid(data, update))
|
||||||
{
|
{
|
||||||
if data.character.is_wield() {
|
if data.character.is_wield() {
|
||||||
update.character = (ability, AbilityKey::Dodge).into();
|
update.character = (&ability, AbilityKey::Dodge).into();
|
||||||
if let CharacterState::Roll(roll) = &mut update.character {
|
if let CharacterState::Roll(roll) = &mut update.character {
|
||||||
roll.was_wielded = true;
|
roll.was_wielded = true;
|
||||||
}
|
}
|
||||||
} else if data.character.is_stealthy() {
|
} else if data.character.is_stealthy() {
|
||||||
update.character = (ability, AbilityKey::Dodge).into();
|
update.character = (&ability, AbilityKey::Dodge).into();
|
||||||
if let CharacterState::Roll(roll) = &mut update.character {
|
if let CharacterState::Roll(roll) = &mut update.character {
|
||||||
roll.was_sneak = true;
|
roll.was_sneak = true;
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
update.character = (ability, AbilityKey::Dodge).into();
|
update.character = (&ability, AbilityKey::Dodge).into();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -95,7 +95,7 @@ impl<'a> System<'a> for Sys {
|
|||||||
let rad_b = body_b.radius() * scale_b;
|
let rad_b = body_b.radius() * scale_b;
|
||||||
|
|
||||||
// Check if entity is dodging
|
// Check if entity is dodging
|
||||||
let is_dodge = char_state_b_maybe.map_or(false, |c_s| c_s.is_dodge());
|
let is_dodge = char_state_b_maybe.map_or(false, |c_s| c_s.is_melee_dodge());
|
||||||
|
|
||||||
// Check if it is a hit
|
// Check if it is a hit
|
||||||
if entity != b
|
if entity != b
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
use common::{
|
use common::{
|
||||||
comp::{
|
comp::{
|
||||||
skills::SkillGroupType, CharacterState, Energy, EnergyChange, EnergySource, Health, Stats,
|
skills::{GeneralSkill, Skill, SkillGroupType},
|
||||||
|
CharacterState, Energy, EnergyChange, EnergySource, Health, Stats,
|
||||||
},
|
},
|
||||||
event::{EventBus, ServerEvent},
|
event::{EventBus, ServerEvent},
|
||||||
metrics::SysMetrics,
|
metrics::SysMetrics,
|
||||||
@ -93,6 +94,45 @@ impl<'a> System<'a> for Sys {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Apply effects from leveling skills
|
||||||
|
for (mut stats, mut health, mut energy) in (
|
||||||
|
&mut stats.restrict_mut(),
|
||||||
|
&mut healths.restrict_mut(),
|
||||||
|
&mut energies.restrict_mut(),
|
||||||
|
)
|
||||||
|
.join()
|
||||||
|
{
|
||||||
|
let stat = stats.get_unchecked();
|
||||||
|
if stat.skill_set.modify_health {
|
||||||
|
let mut health = health.get_mut_unchecked();
|
||||||
|
let health_level = stat
|
||||||
|
.skill_set
|
||||||
|
.skills
|
||||||
|
.get(&Skill::General(GeneralSkill::HealthIncrease))
|
||||||
|
.copied()
|
||||||
|
.flatten()
|
||||||
|
.unwrap_or(0);
|
||||||
|
health.update_max_hp(Some(stat.body_type), health_level.into());
|
||||||
|
let mut stat = stats.get_mut_unchecked();
|
||||||
|
stat.skill_set.modify_health = false;
|
||||||
|
}
|
||||||
|
let stat = stats.get_unchecked();
|
||||||
|
if stat.skill_set.modify_energy {
|
||||||
|
let mut energy = energy.get_mut_unchecked();
|
||||||
|
let energy_level = stat
|
||||||
|
.skill_set
|
||||||
|
.skills
|
||||||
|
.get(&Skill::General(GeneralSkill::EnergyIncrease))
|
||||||
|
.copied()
|
||||||
|
.flatten()
|
||||||
|
.unwrap_or(0) as u32;
|
||||||
|
let energy_max = stat.body_type.base_energy() + 50 * energy_level;
|
||||||
|
energy.set_maximum(energy_max);
|
||||||
|
let mut stat = stats.get_mut_unchecked();
|
||||||
|
stat.skill_set.modify_energy = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Update energies
|
// Update energies
|
||||||
for (character_state, mut energy) in
|
for (character_state, mut energy) in
|
||||||
(&character_states, &mut energies.restrict_mut()).join()
|
(&character_states, &mut energies.restrict_mut()).join()
|
||||||
|
@ -366,6 +366,8 @@ pub fn convert_stats_from_database(
|
|||||||
new_stats.skill_set = skills::SkillSet {
|
new_stats.skill_set = skills::SkillSet {
|
||||||
skill_groups: convert_skill_groups_from_database(skill_groups),
|
skill_groups: convert_skill_groups_from_database(skill_groups),
|
||||||
skills: convert_skills_from_database(skills),
|
skills: convert_skills_from_database(skills),
|
||||||
|
modify_health: true,
|
||||||
|
modify_energy: true,
|
||||||
};
|
};
|
||||||
|
|
||||||
new_stats
|
new_stats
|
||||||
|
@ -124,16 +124,8 @@ impl<'a> Widget for BuffsBar<'a> {
|
|||||||
.font_id(self.fonts.cyri.conrod_id)
|
.font_id(self.fonts.cyri.conrod_id)
|
||||||
.desc_text_color(TEXT_COLOR);
|
.desc_text_color(TEXT_COLOR);
|
||||||
if let BuffPosition::Bar = buff_position {
|
if let BuffPosition::Bar = buff_position {
|
||||||
let show_health = if self.health.current() != self.health.maximum() {
|
let show_health = self.health.current() != self.health.maximum();
|
||||||
true
|
let show_stamina = self.energy.current() != self.energy.maximum();
|
||||||
} else {
|
|
||||||
false
|
|
||||||
};
|
|
||||||
let show_stamina = if self.energy.current() != self.energy.maximum() {
|
|
||||||
true
|
|
||||||
} else {
|
|
||||||
false
|
|
||||||
};
|
|
||||||
let offset = if show_health && show_stamina {
|
let offset = if show_health && show_stamina {
|
||||||
140.0
|
140.0
|
||||||
} else if show_health || show_stamina {
|
} else if show_health || show_stamina {
|
||||||
|
@ -14,7 +14,10 @@ use conrod_core::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
use client::{self, Client};
|
use client::{self, Client};
|
||||||
use common::comp::skills::{self, Skill};
|
use common::comp::{
|
||||||
|
item::tool::ToolKind,
|
||||||
|
skills::{self, Skill},
|
||||||
|
};
|
||||||
use inline_tweak::*;
|
use inline_tweak::*;
|
||||||
|
|
||||||
widget_ids! {
|
widget_ids! {
|
||||||
@ -123,6 +126,19 @@ widget_ids! {
|
|||||||
skill_sceptre_bomb_2,
|
skill_sceptre_bomb_2,
|
||||||
skill_sceptre_bomb_3,
|
skill_sceptre_bomb_3,
|
||||||
skill_sceptre_bomb_4,
|
skill_sceptre_bomb_4,
|
||||||
|
general_combat_render,
|
||||||
|
skill_general_stat_0,
|
||||||
|
skill_general_stat_1,
|
||||||
|
skill_general_tree_0,
|
||||||
|
skill_general_tree_1,
|
||||||
|
skill_general_tree_2,
|
||||||
|
skill_general_tree_3,
|
||||||
|
skill_general_tree_4,
|
||||||
|
skill_general_tree_5,
|
||||||
|
skill_general_roll_0,
|
||||||
|
skill_general_roll_1,
|
||||||
|
skill_general_roll_2,
|
||||||
|
skill_general_roll_3,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -194,9 +210,18 @@ pub enum SelectedSkillTree {
|
|||||||
Sceptre,
|
Sceptre,
|
||||||
Bow,
|
Bow,
|
||||||
StaffFire,
|
StaffFire,
|
||||||
|
GeneralCombat,
|
||||||
}
|
}
|
||||||
|
|
||||||
const WEAPONS: [&str; 6] = ["Sword", "Hammer", "Axe", "Sceptre", "Bow", "Fire Staff"];
|
const WEAPONS: [&str; 7] = [
|
||||||
|
"General Combat",
|
||||||
|
"Sword",
|
||||||
|
"Hammer",
|
||||||
|
"Axe",
|
||||||
|
"Sceptre",
|
||||||
|
"Bow",
|
||||||
|
"Fire Staff",
|
||||||
|
];
|
||||||
|
|
||||||
pub enum Event {
|
pub enum Event {
|
||||||
Close,
|
Close,
|
||||||
@ -298,6 +323,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
for i in WEAPONS.iter().copied().enumerate() {
|
for i in WEAPONS.iter().copied().enumerate() {
|
||||||
// Background weapon image
|
// Background weapon image
|
||||||
let img = Image::new(match i.1 {
|
let img = Image::new(match i.1 {
|
||||||
|
"General Combat" => self.imgs.not_found,
|
||||||
"Sword" => self.imgs.sword,
|
"Sword" => self.imgs.sword,
|
||||||
"Hammer" => self.imgs.hammer,
|
"Hammer" => self.imgs.hammer,
|
||||||
"Axe" => self.imgs.axe,
|
"Axe" => self.imgs.axe,
|
||||||
@ -317,6 +343,10 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
.set(state.weapon_imgs[i.0], ui);
|
.set(state.weapon_imgs[i.0], ui);
|
||||||
// Weapon icons
|
// Weapon icons
|
||||||
if Button::image(match i.1 {
|
if Button::image(match i.1 {
|
||||||
|
"General Combat" => match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => self.imgs.wpn_icon_border_pressed,
|
||||||
|
_ => self.imgs.wpn_icon_border,
|
||||||
|
},
|
||||||
"Sword" => match sel_tab {
|
"Sword" => match sel_tab {
|
||||||
SelectedSkillTree::Sword => self.imgs.wpn_icon_border_pressed,
|
SelectedSkillTree::Sword => self.imgs.wpn_icon_border_pressed,
|
||||||
_ => self.imgs.wpn_icon_border,
|
_ => self.imgs.wpn_icon_border,
|
||||||
@ -345,6 +375,10 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
})
|
})
|
||||||
.w_h(tweak!(50.0), tweak!(50.0))
|
.w_h(tweak!(50.0), tweak!(50.0))
|
||||||
.hover_image(match i.1 {
|
.hover_image(match i.1 {
|
||||||
|
"General Combat" => match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => self.imgs.wpn_icon_border_pressed,
|
||||||
|
_ => self.imgs.wpn_icon_border_mo,
|
||||||
|
},
|
||||||
"Sword" => match sel_tab {
|
"Sword" => match sel_tab {
|
||||||
SelectedSkillTree::Sword => self.imgs.wpn_icon_border_pressed,
|
SelectedSkillTree::Sword => self.imgs.wpn_icon_border_pressed,
|
||||||
_ => self.imgs.wpn_icon_border_mo,
|
_ => self.imgs.wpn_icon_border_mo,
|
||||||
@ -372,6 +406,10 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
_ => self.imgs.wpn_icon_border,
|
_ => self.imgs.wpn_icon_border,
|
||||||
})
|
})
|
||||||
.press_image(match i.1 {
|
.press_image(match i.1 {
|
||||||
|
"General Combat" => match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => self.imgs.wpn_icon_border_pressed,
|
||||||
|
_ => self.imgs.wpn_icon_border_press,
|
||||||
|
},
|
||||||
"Sword" => match sel_tab {
|
"Sword" => match sel_tab {
|
||||||
SelectedSkillTree::Sword => self.imgs.wpn_icon_border_pressed,
|
SelectedSkillTree::Sword => self.imgs.wpn_icon_border_pressed,
|
||||||
_ => self.imgs.wpn_icon_border_press,
|
_ => self.imgs.wpn_icon_border_press,
|
||||||
@ -403,6 +441,9 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
.was_clicked()
|
.was_clicked()
|
||||||
{
|
{
|
||||||
match i.1 {
|
match i.1 {
|
||||||
|
"General Combat" => {
|
||||||
|
events.push(Event::ChangeWeaponTree(SelectedSkillTree::GeneralCombat))
|
||||||
|
},
|
||||||
"Sword" => events.push(Event::ChangeWeaponTree(SelectedSkillTree::Sword)),
|
"Sword" => events.push(Event::ChangeWeaponTree(SelectedSkillTree::Sword)),
|
||||||
"Hammer" => events.push(Event::ChangeWeaponTree(SelectedSkillTree::Hammer)),
|
"Hammer" => events.push(Event::ChangeWeaponTree(SelectedSkillTree::Hammer)),
|
||||||
"Axe" => events.push(Event::ChangeWeaponTree(SelectedSkillTree::Axe)),
|
"Axe" => events.push(Event::ChangeWeaponTree(SelectedSkillTree::Axe)),
|
||||||
@ -436,6 +477,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
// Number of skills per rectangle per weapon, start counting at 0
|
// Number of skills per rectangle per weapon, start counting at 0
|
||||||
// Maximum of 9 skills/8 indices
|
// Maximum of 9 skills/8 indices
|
||||||
let skills_top_l = match sel_tab {
|
let skills_top_l = match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => 2,
|
||||||
SelectedSkillTree::Sword => 4,
|
SelectedSkillTree::Sword => 4,
|
||||||
SelectedSkillTree::Axe => 4,
|
SelectedSkillTree::Axe => 4,
|
||||||
SelectedSkillTree::Hammer => 4,
|
SelectedSkillTree::Hammer => 4,
|
||||||
@ -445,6 +487,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
_ => 0,
|
_ => 0,
|
||||||
};
|
};
|
||||||
let skills_top_r = match sel_tab {
|
let skills_top_r = match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => 6,
|
||||||
SelectedSkillTree::Sword => 6,
|
SelectedSkillTree::Sword => 6,
|
||||||
SelectedSkillTree::Axe => 5,
|
SelectedSkillTree::Axe => 5,
|
||||||
SelectedSkillTree::Hammer => 4,
|
SelectedSkillTree::Hammer => 4,
|
||||||
@ -454,6 +497,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
_ => 0,
|
_ => 0,
|
||||||
};
|
};
|
||||||
let skills_bot_l = match sel_tab {
|
let skills_bot_l = match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => 4,
|
||||||
SelectedSkillTree::Sword => 5,
|
SelectedSkillTree::Sword => 5,
|
||||||
SelectedSkillTree::Axe => 5,
|
SelectedSkillTree::Axe => 5,
|
||||||
SelectedSkillTree::Hammer => 6,
|
SelectedSkillTree::Hammer => 6,
|
||||||
@ -565,14 +609,283 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
}
|
}
|
||||||
// Skill-Icons and Functionality
|
// Skill-Icons and Functionality
|
||||||
// Art dimensions
|
// Art dimensions
|
||||||
let art_size = [tweak!(490.0), tweak!(490.0)];
|
let art_size = [tweak!(320.0), tweak!(320.0)];
|
||||||
match sel_tab {
|
match sel_tab {
|
||||||
|
SelectedSkillTree::GeneralCombat => {
|
||||||
|
use skills::{GeneralSkill::*, RollSkill::*, SkillGroupType::*};
|
||||||
|
use ToolKind::*;
|
||||||
|
// General Combat
|
||||||
|
Image::new(self.imgs.not_found)
|
||||||
|
.wh(art_size)
|
||||||
|
.middle_of(state.content_align)
|
||||||
|
.graphics_for(state.content_align)
|
||||||
|
.color(Some(Color::Rgba(1.0, 1.0, 1.0, tweak!(1.0))))
|
||||||
|
.set(state.general_combat_render, ui);
|
||||||
|
// Top Left skills
|
||||||
|
// 5 1 6
|
||||||
|
// 3 0 4
|
||||||
|
// 8 2 7
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_l[0])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Increase Health",
|
||||||
|
"Increases health",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_stat_0, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::General(HealthIncrease)));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_l[1])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Increase Energy",
|
||||||
|
"Increases energy",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_stat_1, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::General(EnergyIncrease)));
|
||||||
|
};
|
||||||
|
// Top right skills
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_r[0])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Unlock Sword",
|
||||||
|
"Unlocks sword skill tree",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_tree_0, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::UnlockGroup(Weapon(Sword))));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_r[1])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Unlock Axe",
|
||||||
|
"Unlocks axe skill tree",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_tree_1, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::UnlockGroup(Weapon(Axe))));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_r[2])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Unlock Hammer",
|
||||||
|
"Unlocks hammer skill tree",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_tree_2, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::UnlockGroup(Weapon(Hammer))));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_r[3])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Unlock Bow",
|
||||||
|
"Unlocks bow skill tree",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_tree_3, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::UnlockGroup(Weapon(Bow))));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_r[4])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Unlock Staff",
|
||||||
|
"Unlocks staff skill tree",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_tree_4, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::UnlockGroup(Weapon(Staff))));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_top_r[5])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Unlock Sceptre",
|
||||||
|
"Unlocks sceptre skill tree",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_tree_5, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::UnlockGroup(Weapon(Sceptre))));
|
||||||
|
};
|
||||||
|
// Bottom left skills
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_bot_l[0])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Dodge",
|
||||||
|
"Ground-yeeting dodges melee attacks",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_roll_0, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::Roll(ImmuneMelee)));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_bot_l[1])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Cost",
|
||||||
|
"Decreases cost of ground-yeeting yourself",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_roll_1, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::Roll(Cost)));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_bot_l[2])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Strength",
|
||||||
|
"Increases how far you ground-yeet yourself",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_roll_2, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::Roll(Strength)));
|
||||||
|
};
|
||||||
|
if Button::image(self.imgs.not_found)
|
||||||
|
.w_h(tweak!(74.0), tweak!(74.0))
|
||||||
|
.middle_of(state.skills_bot_l[3])
|
||||||
|
.label(&self.example_skill_count.to_string())
|
||||||
|
.label_y(conrod_core::position::Relative::Scalar(tweak!(-28.0)))
|
||||||
|
.label_x(conrod_core::position::Relative::Scalar(tweak!(32.0)))
|
||||||
|
.label_color(TEXT_COLOR)
|
||||||
|
.label_font_size(self.fonts.cyri.scale(tweak!(16)))
|
||||||
|
.label_font_id(self.fonts.cyri.conrod_id)
|
||||||
|
.with_tooltip(
|
||||||
|
self.tooltip_manager,
|
||||||
|
"Duration",
|
||||||
|
"Increases for how long you ground-yeet yourself",
|
||||||
|
&diary_tooltip,
|
||||||
|
TEXT_COLOR,
|
||||||
|
)
|
||||||
|
.set(state.skill_general_roll_3, ui)
|
||||||
|
.was_clicked()
|
||||||
|
{
|
||||||
|
events.push(Event::UnlockSkill(Skill::Roll(Duration)));
|
||||||
|
};
|
||||||
|
},
|
||||||
SelectedSkillTree::Sword => {
|
SelectedSkillTree::Sword => {
|
||||||
use skills::SwordSkill::*;
|
use skills::SwordSkill::*;
|
||||||
// Sword
|
// Sword
|
||||||
Image::new(
|
Image::new(
|
||||||
self.item_imgs
|
self.item_imgs
|
||||||
.img_id_or_not_found_img(Tool("example_sword".to_string()).clone()),
|
.img_id_or_not_found_img(Tool("example_sword".to_string())),
|
||||||
)
|
)
|
||||||
.wh(art_size)
|
.wh(art_size)
|
||||||
.middle_of(state.content_align)
|
.middle_of(state.content_align)
|
||||||
@ -928,7 +1241,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
// Axe
|
// Axe
|
||||||
Image::new(
|
Image::new(
|
||||||
self.item_imgs
|
self.item_imgs
|
||||||
.img_id_or_not_found_img(Tool("example_axe".to_string()).clone()),
|
.img_id_or_not_found_img(Tool("example_axe".to_string())),
|
||||||
)
|
)
|
||||||
.wh(art_size)
|
.wh(art_size)
|
||||||
.middle_of(state.content_align)
|
.middle_of(state.content_align)
|
||||||
@ -1241,7 +1554,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
// Hammer
|
// Hammer
|
||||||
Image::new(
|
Image::new(
|
||||||
self.item_imgs
|
self.item_imgs
|
||||||
.img_id_or_not_found_img(Tool("example_hammer".to_string()).clone()),
|
.img_id_or_not_found_img(Tool("example_hammer".to_string())),
|
||||||
)
|
)
|
||||||
.wh(art_size)
|
.wh(art_size)
|
||||||
.middle_of(state.content_align)
|
.middle_of(state.content_align)
|
||||||
@ -1554,7 +1867,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
// Bow
|
// Bow
|
||||||
Image::new(
|
Image::new(
|
||||||
self.item_imgs
|
self.item_imgs
|
||||||
.img_id_or_not_found_img(Tool("example_bow".to_string()).clone()),
|
.img_id_or_not_found_img(Tool("example_bow".to_string())),
|
||||||
)
|
)
|
||||||
.wh(art_size)
|
.wh(art_size)
|
||||||
.middle_of(state.content_align)
|
.middle_of(state.content_align)
|
||||||
@ -1867,7 +2180,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
// Staff
|
// Staff
|
||||||
Image::new(
|
Image::new(
|
||||||
self.item_imgs
|
self.item_imgs
|
||||||
.img_id_or_not_found_img(Tool("example_staff_fire".to_string()).clone()),
|
.img_id_or_not_found_img(Tool("example_staff_fire".to_string())),
|
||||||
)
|
)
|
||||||
.wh(art_size)
|
.wh(art_size)
|
||||||
.middle_of(state.content_align)
|
.middle_of(state.content_align)
|
||||||
@ -2159,7 +2472,7 @@ impl<'a> Widget for Diary<'a> {
|
|||||||
// Sceptre
|
// Sceptre
|
||||||
Image::new(
|
Image::new(
|
||||||
self.item_imgs
|
self.item_imgs
|
||||||
.img_id_or_not_found_img(Tool("example_sceptre".to_string()).clone()),
|
.img_id_or_not_found_img(Tool("example_sceptre".to_string())),
|
||||||
)
|
)
|
||||||
.wh(art_size)
|
.wh(art_size)
|
||||||
.middle_of(state.content_align)
|
.middle_of(state.content_align)
|
||||||
|
@ -757,7 +757,7 @@ impl Hud {
|
|||||||
group_menu: false,
|
group_menu: false,
|
||||||
mini_map: true,
|
mini_map: true,
|
||||||
settings_tab: SettingsTab::Interface,
|
settings_tab: SettingsTab::Interface,
|
||||||
skilltreetab: SelectedSkillTree::Sword,
|
skilltreetab: SelectedSkillTree::GeneralCombat,
|
||||||
social_tab: SocialTab::Online,
|
social_tab: SocialTab::Online,
|
||||||
want_grab: true,
|
want_grab: true,
|
||||||
ingame: true,
|
ingame: true,
|
||||||
|
@ -351,16 +351,8 @@ impl<'a> Widget for Skillbar<'a> {
|
|||||||
.mid_bottom_with_margin_on(ui.window, 10.0)
|
.mid_bottom_with_margin_on(ui.window, 10.0)
|
||||||
.set(state.ids.frame, ui);
|
.set(state.ids.frame, ui);
|
||||||
// Health and Stamina bar
|
// Health and Stamina bar
|
||||||
let show_health = if self.health.current() != self.health.maximum() {
|
let show_health = self.health.current() != self.health.maximum();
|
||||||
true
|
let show_stamina = self.energy.current() != self.energy.maximum();
|
||||||
} else {
|
|
||||||
false
|
|
||||||
};
|
|
||||||
let show_stamina = if self.energy.current() != self.energy.maximum() {
|
|
||||||
true
|
|
||||||
} else {
|
|
||||||
false
|
|
||||||
};
|
|
||||||
|
|
||||||
if show_health && !self.health.is_dead {
|
if show_health && !self.health.is_dead {
|
||||||
let offset = if show_stamina {
|
let offset = if show_stamina {
|
||||||
@ -424,7 +416,12 @@ impl<'a> Widget for Skillbar<'a> {
|
|||||||
* living players */
|
* living players */
|
||||||
(self.health.maximum() / 10) as u32
|
(self.health.maximum() / 10) as u32
|
||||||
);
|
);
|
||||||
let mut energy_txt = format!("{}", energy_percentage as u32);
|
let mut energy_txt = format!(
|
||||||
|
"{}/{}",
|
||||||
|
(self.energy.current() / 10) as u32,
|
||||||
|
(self.energy.maximum() / 10) as u32
|
||||||
|
);
|
||||||
|
//let mut energy_txt = format!("{}", energy_percentage as u32);
|
||||||
if self.health.is_dead {
|
if self.health.is_dead {
|
||||||
hp_txt = self.localized_strings.get("hud.group.dead").to_string();
|
hp_txt = self.localized_strings.get("hud.group.dead").to_string();
|
||||||
energy_txt = self.localized_strings.get("hud.group.dead").to_string();
|
energy_txt = self.localized_strings.get("hud.group.dead").to_string();
|
||||||
|
Loading…
Reference in New Issue
Block a user