Compare commits
4 commits
Author | SHA1 | Date | |
---|---|---|---|
af2cef394b | |||
23fcde33f5 | |||
543727ce4e | |||
7412dcec2d |
73 changed files with 49932 additions and 40571 deletions
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -41,7 +41,7 @@ Start each service in order from option `a)`.
|
|||
Most of the configuration (database, encryption keys) is stored in a shared environment configuration file (`environment.toml`). Some of server-specific options are stored in their respective configuration files (which are created upon first startup of each server).
|
||||
|
||||
### Logging in
|
||||
To login to this server, you have to obtain a compatible game client. Currently supported one is `OSPRODWin1.6.0`, you can get it from game launcher. Next, you have to apply the necessary [client patch](https://git.xeondev.com/ObolSquad/trigger-patch). It allows you to connect to the local server and replaces encryption keys with custom ones.
|
||||
To login to this server, you have to obtain a compatible game client. Currently supported one is `CNBetaWin1.7.0`, you can get it from uploads found on [Our Discord Server](https://discord.gg/reversedrooms). Next, you have to apply the necessary [client patch](https://git.xeondev.com/ObolSquad/trigger-patch). It allows you to connect to the local server and replaces encryption keys with custom ones.
|
||||
|
||||
### Management
|
||||
You can use the [trigger-muip-tool](https://git.xeondev.com/ObolSquad/trigger-muip-tool) to communicate with MUIP server and execute GM commands.
|
||||
|
|
|
@ -1,7 +1,10 @@
|
|||
use std::collections::HashMap;
|
||||
|
||||
use trigger_protocol::DungeonEquipInfo;
|
||||
|
||||
pub struct AvatarUnit {
|
||||
pub avatar_id: u32,
|
||||
pub properties: HashMap<u32, i32>,
|
||||
}
|
||||
|
||||
pub struct BuddyUnit {
|
||||
|
@ -29,6 +32,7 @@ impl Dungeon {
|
|||
.iter()
|
||||
.map(|unit| AvatarUnitInfo {
|
||||
avatar_id: unit.avatar_id,
|
||||
properties: unit.properties.clone(),
|
||||
})
|
||||
.collect(),
|
||||
buddy_list: self
|
||||
|
|
|
@ -1,4 +1,5 @@
|
|||
mod dungeon;
|
||||
mod property_util;
|
||||
|
||||
pub use dungeon::*;
|
||||
pub mod scene;
|
||||
|
@ -39,7 +40,14 @@ impl GameState {
|
|||
quest_id: *quest_id,
|
||||
avatar_list: avatar_id_list
|
||||
.iter()
|
||||
.map(|&avatar_id| AvatarUnit { avatar_id })
|
||||
.map(|&avatar_id| AvatarUnit {
|
||||
avatar_id,
|
||||
properties: property_util::calculate_for_avatar(
|
||||
avatar_id,
|
||||
filecfg,
|
||||
dungeon_equip,
|
||||
),
|
||||
})
|
||||
.collect(),
|
||||
buddy_list: vec![BuddyUnit {
|
||||
buddy_type: 0,
|
||||
|
@ -71,7 +79,14 @@ impl GameState {
|
|||
quest_id: *quest_id,
|
||||
avatar_list: avatar_id_list
|
||||
.iter()
|
||||
.map(|&avatar_id| AvatarUnit { avatar_id })
|
||||
.map(|&avatar_id| AvatarUnit {
|
||||
avatar_id,
|
||||
properties: property_util::calculate_for_avatar(
|
||||
avatar_id,
|
||||
filecfg,
|
||||
dungeon_equip,
|
||||
),
|
||||
})
|
||||
.collect(),
|
||||
buddy_list: vec![BuddyUnit {
|
||||
buddy_type: 0,
|
||||
|
|
717
crates/battle-server/src/logic/property_util.rs
Normal file
717
crates/battle-server/src/logic/property_util.rs
Normal file
|
@ -0,0 +1,717 @@
|
|||
use std::collections::HashMap;
|
||||
|
||||
use trigger_fileconfig::{
|
||||
AvatarBattleTemplate, AvatarLevelAdvanceTemplate, AvatarPassiveSkillTemplate, NapFileCfg,
|
||||
WeaponLevelTemplate, WeaponStarTemplate, WeaponTemplate,
|
||||
};
|
||||
use trigger_logic::{battle::EPropertyType, skill::EAvatarSkillType};
|
||||
use trigger_protocol::{Avatar, DungeonEquipInfo, Equip, Weapon};
|
||||
|
||||
struct AvatarFileCfg<'a> {
|
||||
pub avatar_battle_template: AvatarBattleTemplate<'a>,
|
||||
pub avatar_passive_skill_templates: Vec<AvatarPassiveSkillTemplate<'a>>,
|
||||
pub avatar_level_advances: Vec<AvatarLevelAdvanceTemplate<'a>>,
|
||||
}
|
||||
|
||||
struct WeaponFileCfg<'a> {
|
||||
pub weapon_template: WeaponTemplate<'a>,
|
||||
pub weapon_level_template: WeaponLevelTemplate<'a>,
|
||||
pub weapon_star_template: WeaponStarTemplate<'a>,
|
||||
}
|
||||
|
||||
const BEN_AVATAR_ID: u32 = 1121;
|
||||
const BEN_CORE_PASSIVE_PERCENTAGE: [i32; 7] = [40, 46, 52, 60, 66, 72, 80];
|
||||
|
||||
pub fn calculate_for_avatar(
|
||||
avatar_id: u32,
|
||||
filecfg: &'static NapFileCfg,
|
||||
dungeon_equip: &DungeonEquipInfo,
|
||||
) -> HashMap<u32, i32> {
|
||||
let mut calculated_properties = HashMap::<_, _>::new();
|
||||
let Some(player_avatar) = dungeon_equip
|
||||
.avatar_list
|
||||
.iter()
|
||||
.find(|a| (*a).id == avatar_id)
|
||||
else {
|
||||
return calculated_properties;
|
||||
};
|
||||
let Some(avatar_file_cfg) = get_avatar_filecfg(avatar_id, filecfg) else {
|
||||
return calculated_properties;
|
||||
};
|
||||
insert_avatar_battle_template_properties(&avatar_file_cfg, &mut calculated_properties);
|
||||
insert_avatar_battle_level_advance_properties(
|
||||
&avatar_file_cfg,
|
||||
player_avatar,
|
||||
&mut calculated_properties,
|
||||
);
|
||||
perform_avatar_growth_promotion_calculations(player_avatar, &mut calculated_properties);
|
||||
add_avatar_passive_skill_properties(
|
||||
&avatar_file_cfg,
|
||||
player_avatar,
|
||||
&mut calculated_properties,
|
||||
);
|
||||
let player_weapon = dungeon_equip
|
||||
.weapon_list
|
||||
.iter()
|
||||
.find(|w| w.uid == player_avatar.cur_weapon_uid);
|
||||
if player_weapon.is_some() {
|
||||
match get_weapon_filecfg(player_weapon.unwrap(), filecfg) {
|
||||
Some(weapon_file_cfg) => {
|
||||
add_weapon_template_properties(&weapon_file_cfg, &mut calculated_properties);
|
||||
}
|
||||
None => {}
|
||||
};
|
||||
}
|
||||
let player_dressed_equip_uids: Vec<u32> = player_avatar
|
||||
.dressed_equip_list
|
||||
.iter()
|
||||
.map(|de| de.equip_uid)
|
||||
.collect();
|
||||
let player_equips: Vec<&Equip> = dungeon_equip
|
||||
.equip_list
|
||||
.iter()
|
||||
.filter(|e| player_dressed_equip_uids.contains(&e.uid))
|
||||
.collect();
|
||||
if player_equips.len() > 0 {
|
||||
add_player_equip_properties(&player_equips, filecfg, &mut calculated_properties);
|
||||
add_equipment_suit_properties(&player_equips, filecfg, &mut calculated_properties);
|
||||
}
|
||||
calculate_final_properties(&mut calculated_properties);
|
||||
add_ben_core_passive(avatar_id, player_avatar, &mut calculated_properties);
|
||||
remove_custom_properties(&mut calculated_properties);
|
||||
set_battle_properties(&mut calculated_properties);
|
||||
|
||||
calculated_properties
|
||||
}
|
||||
|
||||
fn get_avatar_filecfg(
|
||||
avatar_id: u32,
|
||||
filecfg: &'static NapFileCfg,
|
||||
) -> Option<AvatarFileCfg<'static>> {
|
||||
let Some(avatar_battle_template) = filecfg
|
||||
.avatar_battle_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.id() == avatar_id as i32)
|
||||
else {
|
||||
return None;
|
||||
};
|
||||
|
||||
let avatar_passive_skill_templates: Vec<AvatarPassiveSkillTemplate> = filecfg
|
||||
.avatar_passive_skill_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.filter(|tmpl| tmpl.avatar_id() == avatar_id as i32)
|
||||
.collect();
|
||||
if avatar_passive_skill_templates.len() == 0 {
|
||||
return None;
|
||||
}
|
||||
|
||||
let avatar_level_advances: Vec<AvatarLevelAdvanceTemplate> = filecfg
|
||||
.avatar_level_advance_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.filter(|tmpl| tmpl.avatar_id() == avatar_id as i32)
|
||||
.collect();
|
||||
if avatar_level_advances.len() == 0 {
|
||||
return None;
|
||||
}
|
||||
|
||||
Some(AvatarFileCfg {
|
||||
avatar_battle_template,
|
||||
avatar_passive_skill_templates,
|
||||
avatar_level_advances,
|
||||
})
|
||||
}
|
||||
|
||||
fn insert_avatar_battle_template_properties(
|
||||
avatar_file_cfg: &AvatarFileCfg,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
properties.insert(
|
||||
EPropertyType::HpMaxBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.hp_max(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::HpMaxGrowth.into(),
|
||||
avatar_file_cfg.avatar_battle_template.health_growth(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AtkBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.attack(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AtkGrowth.into(),
|
||||
avatar_file_cfg.avatar_battle_template.attack_growth(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::BreakStunBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.break_stun(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::DefBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.defence(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::DefGrowth.into(),
|
||||
avatar_file_cfg.avatar_battle_template.defence_growth(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::CritBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.crit(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::CritDmgBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.crit_damage(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::PenBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.pen_rate(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::PenValueBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.pen_delta(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::SpRecoverBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.sp_recover(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::ElementMysteryBase.into(),
|
||||
avatar_file_cfg.avatar_battle_template.element_mystery(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::ElementAbnormalPowerBase.into(),
|
||||
avatar_file_cfg
|
||||
.avatar_battle_template
|
||||
.element_abnormal_power(),
|
||||
);
|
||||
}
|
||||
|
||||
fn insert_avatar_battle_level_advance_properties(
|
||||
avatar_file_cfg: &AvatarFileCfg,
|
||||
player_avatar: &Avatar,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
let Some(avatar_level_advance) = avatar_file_cfg
|
||||
.avatar_level_advances
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.id() == player_avatar.rank as i32)
|
||||
else {
|
||||
properties.insert(EPropertyType::HpMaxAdvance.into(), 0);
|
||||
properties.insert(EPropertyType::AtkAdvance.into(), 0);
|
||||
properties.insert(EPropertyType::DefAdvance.into(), 0);
|
||||
|
||||
return;
|
||||
};
|
||||
|
||||
properties.insert(
|
||||
EPropertyType::HpMaxAdvance.into(),
|
||||
avatar_level_advance.hp_max(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AtkAdvance.into(),
|
||||
avatar_level_advance.attack(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::DefAdvance.into(),
|
||||
avatar_level_advance.defence(),
|
||||
);
|
||||
}
|
||||
|
||||
fn perform_avatar_growth_promotion_calculations(
|
||||
player_avatar: &Avatar,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
properties.insert(
|
||||
EPropertyType::HpMaxBase.into(),
|
||||
properties.get(&EPropertyType::HpMaxBase.into()).unwrap()
|
||||
+ (((player_avatar.level - 1) as f32
|
||||
* *properties.get(&EPropertyType::HpMaxGrowth.into()).unwrap() as f32)
|
||||
/ 10000f32) as i32
|
||||
+ properties.get(&EPropertyType::HpMaxAdvance.into()).unwrap(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AtkBase.into(),
|
||||
properties.get(&EPropertyType::AtkBase.into()).unwrap()
|
||||
+ (((player_avatar.level - 1) as f32
|
||||
* *properties.get(&EPropertyType::AtkGrowth.into()).unwrap() as f32)
|
||||
/ 10000f32) as i32
|
||||
+ properties.get(&EPropertyType::AtkAdvance.into()).unwrap(),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::DefBase.into(),
|
||||
properties.get(&EPropertyType::DefBase.into()).unwrap()
|
||||
+ (((player_avatar.level - 1) as f32
|
||||
* *properties.get(&EPropertyType::DefGrowth.into()).unwrap() as f32)
|
||||
/ 10000f32) as i32
|
||||
+ properties.get(&EPropertyType::DefAdvance.into()).unwrap(),
|
||||
);
|
||||
}
|
||||
|
||||
fn add_avatar_passive_skill_properties(
|
||||
avatar_file_cfg: &AvatarFileCfg,
|
||||
player_avatar: &Avatar,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
let passive_skill_level = player_avatar
|
||||
.skill_type_level
|
||||
.iter()
|
||||
.find(|s| s.skill_type == EAvatarSkillType::CoreSkill as u32)
|
||||
.unwrap()
|
||||
.level;
|
||||
|
||||
avatar_file_cfg
|
||||
.avatar_passive_skill_templates
|
||||
.iter()
|
||||
.find(|a| a.unlock_passive_skill_level() == passive_skill_level as i32)
|
||||
.map(|tmpl| tmpl.propertys().unwrap())
|
||||
.unwrap()
|
||||
.iter()
|
||||
.for_each(|p| {
|
||||
properties.insert(
|
||||
p.property() as u32,
|
||||
properties.get(&(p.property() as u32)).unwrap_or(&0) + p.value(),
|
||||
);
|
||||
});
|
||||
}
|
||||
|
||||
fn get_weapon_filecfg(
|
||||
player_weapon: &Weapon,
|
||||
filecfg: &'static NapFileCfg,
|
||||
) -> Option<WeaponFileCfg<'static>> {
|
||||
let Some(weapon_template) = filecfg
|
||||
.weapon_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.item_id() == player_weapon.id as i32)
|
||||
else {
|
||||
return None;
|
||||
};
|
||||
|
||||
let Some(weapon_level_template) = filecfg
|
||||
.weapon_level_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.level() == player_weapon.level as i32)
|
||||
else {
|
||||
return None;
|
||||
};
|
||||
|
||||
let Some(weapon_star_template) = filecfg
|
||||
.weapon_star_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.star() == player_weapon.star as i32)
|
||||
else {
|
||||
return None;
|
||||
};
|
||||
|
||||
Some(WeaponFileCfg {
|
||||
weapon_template,
|
||||
weapon_level_template,
|
||||
weapon_star_template,
|
||||
})
|
||||
}
|
||||
|
||||
fn add_weapon_template_properties(
|
||||
weapon_file_cfg: &WeaponFileCfg,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
let base_property = weapon_file_cfg.weapon_template.base_property().unwrap();
|
||||
let base_property_value = base_property.value()
|
||||
+ (base_property.value() as f32 * weapon_file_cfg.weapon_level_template.rate() as f32
|
||||
/ 10000f32) as i32
|
||||
+ (base_property.value() as f32 * weapon_file_cfg.weapon_star_template.star_rate() as f32
|
||||
/ 10000f32) as i32;
|
||||
properties.insert(
|
||||
base_property.property() as u32,
|
||||
*properties
|
||||
.get(&(base_property.property() as u32))
|
||||
.unwrap_or(&0)
|
||||
+ base_property_value,
|
||||
);
|
||||
let rand_property = weapon_file_cfg.weapon_template.rand_property().unwrap();
|
||||
let rand_property_value = rand_property.value()
|
||||
+ (rand_property.value() as f32 * weapon_file_cfg.weapon_star_template.rand_rate() as f32
|
||||
/ 10000f32) as i32;
|
||||
properties.insert(
|
||||
rand_property.property() as u32,
|
||||
*properties
|
||||
.get(&(rand_property.property() as u32))
|
||||
.unwrap_or(&0)
|
||||
+ rand_property_value,
|
||||
);
|
||||
}
|
||||
|
||||
fn add_player_equip_properties(
|
||||
player_equips: &Vec<&Equip>,
|
||||
filecfg: &'static NapFileCfg,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
player_equips.iter().for_each(|pe| {
|
||||
let equip_rarity = (pe.id / 10) % 10;
|
||||
let property_rate = filecfg
|
||||
.equipment_level_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.rarity() == equip_rarity as i32 && tmpl.level() == pe.level as i32)
|
||||
.map(|tmpl| tmpl.property_rate())
|
||||
.unwrap_or(1);
|
||||
pe.propertys.iter().for_each(|p| {
|
||||
properties.insert(
|
||||
p.key,
|
||||
properties.get(&p.key).unwrap_or(&0)
|
||||
+ p.base_value as i32
|
||||
+ (p.base_value as f32 * property_rate as f32 / 10000f32) as i32,
|
||||
);
|
||||
});
|
||||
pe.sub_propertys.iter().for_each(|p| {
|
||||
properties.insert(
|
||||
p.key,
|
||||
properties.get(&p.key).unwrap_or(&0)
|
||||
+ (p.base_value as f32 * p.add_value as f32) as i32,
|
||||
);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
fn add_equipment_suit_properties(
|
||||
player_equips: &Vec<&Equip>,
|
||||
filecfg: &'static NapFileCfg,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
let mut suit_counts = HashMap::<i32, i32>::new();
|
||||
player_equips.iter().for_each(|pe| {
|
||||
let suit_id = pe.id as i32 / 100 * 100;
|
||||
suit_counts.insert(suit_id, *suit_counts.get(&suit_id).unwrap_or(&0) + 1);
|
||||
});
|
||||
suit_counts.iter().for_each(|sc| {
|
||||
let Some(equipment_suit_template) = filecfg
|
||||
.equipment_suit_template_tb()
|
||||
.data()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.find(|tmpl| tmpl.id() == *sc.0)
|
||||
else {
|
||||
return;
|
||||
};
|
||||
if equipment_suit_template.primary_condition() <= *sc.1 {
|
||||
equipment_suit_template
|
||||
.primary_suit_propertys()
|
||||
.unwrap()
|
||||
.iter()
|
||||
.for_each(|p| {
|
||||
properties.insert(
|
||||
p.property() as u32,
|
||||
properties.get(&(p.property() as u32)).unwrap_or(&0) + p.value(),
|
||||
);
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
fn calculate_final_properties(properties: &mut HashMap<u32, i32>) {
|
||||
properties.insert(
|
||||
EPropertyType::HpMax.into(),
|
||||
properties.get(&EPropertyType::HpMaxBase.into()).unwrap()
|
||||
+ (*properties.get(&EPropertyType::HpMaxBase.into()).unwrap() as f32
|
||||
* *properties
|
||||
.get(&EPropertyType::HpMaxRatio.into())
|
||||
.unwrap_or(&0) as f32
|
||||
/ 10000f32)
|
||||
.ceil() as i32
|
||||
+ properties
|
||||
.get(&EPropertyType::HpMaxDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::Atk.into(),
|
||||
properties.get(&EPropertyType::AtkBase.into()).unwrap()
|
||||
+ (*properties.get(&EPropertyType::AtkBase.into()).unwrap() as f32
|
||||
* *properties
|
||||
.get(&EPropertyType::AtkRatio.into())
|
||||
.unwrap_or(&0) as f32
|
||||
/ 10000f32) as i32
|
||||
+ properties
|
||||
.get(&EPropertyType::AtkDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::BreakStun.into(),
|
||||
properties
|
||||
.get(&EPropertyType::BreakStunBase.into())
|
||||
.unwrap()
|
||||
+ (*properties
|
||||
.get(&EPropertyType::BreakStunBase.into())
|
||||
.unwrap() as f32
|
||||
* *properties
|
||||
.get(&EPropertyType::BreakStunRatio.into())
|
||||
.unwrap_or(&0) as f32
|
||||
/ 10000f32) as i32
|
||||
+ properties
|
||||
.get(&EPropertyType::BreakStunDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::Def.into(),
|
||||
properties.get(&EPropertyType::DefBase.into()).unwrap()
|
||||
+ (*properties.get(&EPropertyType::DefBase.into()).unwrap() as f32
|
||||
* *properties
|
||||
.get(&EPropertyType::DefRatio.into())
|
||||
.unwrap_or(&0) as f32
|
||||
/ 10000f32) as i32
|
||||
+ properties
|
||||
.get(&EPropertyType::DefDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::Crit.into(),
|
||||
properties.get(&EPropertyType::CritBase.into()).unwrap()
|
||||
+ properties
|
||||
.get(&EPropertyType::CritDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::CritDmg.into(),
|
||||
properties.get(&EPropertyType::CritDmgBase.into()).unwrap()
|
||||
+ properties
|
||||
.get(&EPropertyType::CritDmgDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::Pen.into(),
|
||||
properties.get(&EPropertyType::PenBase.into()).unwrap()
|
||||
+ properties
|
||||
.get(&EPropertyType::PenDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::PenValue.into(),
|
||||
properties.get(&EPropertyType::PenValueBase.into()).unwrap()
|
||||
+ properties
|
||||
.get(&EPropertyType::PenValueDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::SpRecover.into(),
|
||||
properties
|
||||
.get(&EPropertyType::SpRecoverBase.into())
|
||||
.unwrap()
|
||||
+ (*properties
|
||||
.get(&EPropertyType::SpRecoverBase.into())
|
||||
.unwrap() as f32
|
||||
* *properties
|
||||
.get(&EPropertyType::SpRecoverRatio.into())
|
||||
.unwrap_or(&0) as f32
|
||||
/ 10000f32) as i32
|
||||
+ properties
|
||||
.get(&EPropertyType::SpRecoverDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::ElementMystery.into(),
|
||||
properties
|
||||
.get(&EPropertyType::ElementMysteryBase.into())
|
||||
.unwrap()
|
||||
+ properties
|
||||
.get(&EPropertyType::ElementMysteryDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::ElementAbnormalPower.into(),
|
||||
properties
|
||||
.get(&EPropertyType::ElementAbnormalPowerBase.into())
|
||||
.unwrap()
|
||||
+ (*properties
|
||||
.get(&EPropertyType::ElementAbnormalPowerBase.into())
|
||||
.unwrap() as f32
|
||||
* *properties
|
||||
.get(&EPropertyType::ElementAbnormalPowerRatio.into())
|
||||
.unwrap_or(&0) as f32
|
||||
/ 10000f32) as i32
|
||||
+ properties
|
||||
.get(&EPropertyType::ElementAbnormalPowerDelta.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioPhysics.into(),
|
||||
properties
|
||||
.get(&EPropertyType::AddedDamageRatioPhysics1.into())
|
||||
.unwrap_or(&0)
|
||||
+ properties
|
||||
.get(&EPropertyType::AddedDamageRatioPhysics3.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioFire.into(),
|
||||
properties
|
||||
.get(&EPropertyType::AddedDamageRatioFire1.into())
|
||||
.unwrap_or(&0)
|
||||
+ properties
|
||||
.get(&EPropertyType::AddedDamageRatioFire3.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioIce.into(),
|
||||
properties
|
||||
.get(&EPropertyType::AddedDamageRatioIce1.into())
|
||||
.unwrap_or(&0)
|
||||
+ properties
|
||||
.get(&EPropertyType::AddedDamageRatioIce3.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioElec.into(),
|
||||
properties
|
||||
.get(&EPropertyType::AddedDamageRatioElec1.into())
|
||||
.unwrap_or(&0)
|
||||
+ properties
|
||||
.get(&EPropertyType::AddedDamageRatioElec3.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioEther.into(),
|
||||
properties
|
||||
.get(&EPropertyType::AddedDamageRatioEther1.into())
|
||||
.unwrap_or(&0)
|
||||
+ properties
|
||||
.get(&EPropertyType::AddedDamageRatioEther3.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
}
|
||||
|
||||
fn add_ben_core_passive(
|
||||
avatar_id: u32,
|
||||
player_avatar: &Avatar,
|
||||
properties: &mut HashMap<u32, i32>,
|
||||
) {
|
||||
if avatar_id != BEN_AVATAR_ID {
|
||||
return;
|
||||
}
|
||||
let core_level = player_avatar
|
||||
.skill_type_level
|
||||
.iter()
|
||||
.find(|sl| sl.skill_type == EAvatarSkillType::CoreSkill as u32)
|
||||
.unwrap()
|
||||
.level as usize;
|
||||
let def_atk_bonus = match core_level {
|
||||
1..=7 => {
|
||||
*properties.get(&EPropertyType::Def.into()).unwrap_or(&0)
|
||||
* BEN_CORE_PASSIVE_PERCENTAGE[core_level - 1]
|
||||
/ 100
|
||||
}
|
||||
_ => 0,
|
||||
};
|
||||
properties.insert(
|
||||
EPropertyType::Atk.into(),
|
||||
*properties.get(&EPropertyType::Atk.into()).unwrap_or(&0) + def_atk_bonus,
|
||||
);
|
||||
}
|
||||
|
||||
fn remove_custom_properties(properties: &mut HashMap<u32, i32>) {
|
||||
properties.remove(&EPropertyType::HpMaxGrowth.into());
|
||||
properties.remove(&EPropertyType::AtkGrowth.into());
|
||||
properties.remove(&EPropertyType::DefGrowth.into());
|
||||
properties.remove(&EPropertyType::HpMaxAdvance.into());
|
||||
properties.remove(&EPropertyType::AtkAdvance.into());
|
||||
properties.remove(&EPropertyType::DefAdvance.into());
|
||||
}
|
||||
|
||||
fn set_battle_properties(properties: &mut HashMap<u32, i32>) {
|
||||
properties.insert(
|
||||
EPropertyType::Hp.into(),
|
||||
*properties.get(&EPropertyType::HpMax.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::HpMaxBattle.into(),
|
||||
*properties.get(&EPropertyType::HpMax.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AtkBattle.into(),
|
||||
*properties.get(&EPropertyType::Atk.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::BreakStunBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::BreakStun.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::DefBattle.into(),
|
||||
*properties.get(&EPropertyType::Def.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::CritBattle.into(),
|
||||
*properties.get(&EPropertyType::Crit.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::CritDmgBattle.into(),
|
||||
*properties.get(&EPropertyType::CritDmg.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::PenRatioBattle.into(),
|
||||
*properties.get(&EPropertyType::Pen.into()).unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::PenDeltaBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::PenValue.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::SpRecoverBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::SpRecover.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::ElementMysteryBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::ElementMystery.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::ElementAbnormalPowerBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::ElementAbnormalPower.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioPhysicsBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::AddedDamageRatioPhysics.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioFireBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::AddedDamageRatioFire.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioIceBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::AddedDamageRatioIce.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioElecBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::AddedDamageRatioElec.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
properties.insert(
|
||||
EPropertyType::AddedDamageRatioEtherBattle.into(),
|
||||
*properties
|
||||
.get(&EPropertyType::AddedDamageRatioEther.into())
|
||||
.unwrap_or(&0),
|
||||
);
|
||||
}
|
|
@ -10,7 +10,7 @@ use trigger_sv::{
|
|||
net::ServerType,
|
||||
};
|
||||
|
||||
use crate::{logic::GameState, session::BattleSession, AppState};
|
||||
use crate::{AppState, logic::GameState, session::BattleSession};
|
||||
|
||||
pub async fn handle_message(state: &'static AppState, packet: trigger_sv::message::NetworkPacket) {
|
||||
match packet.opcode {
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
use trigger_encoding::Decodeable;
|
||||
use trigger_protocol::{util::ProtocolUnit, ClientCmdID, EndBattleCsReq};
|
||||
use trigger_protocol::{ClientCmdID, EndBattleCsReq, util::ProtocolUnit};
|
||||
use trigger_sv::message::GameStateCallback;
|
||||
|
||||
use super::BattleSession;
|
||||
|
|
|
@ -13,7 +13,7 @@ area = 2
|
|||
[bound_server]
|
||||
name = "trigger_rs"
|
||||
title = "Trigger-RS"
|
||||
seed = "70fed6d1bdf76412"
|
||||
seed = "789bd844f8c04bc3"
|
||||
addr = "127.0.0.1"
|
||||
port = 20501
|
||||
is_kcp = false
|
||||
|
|
|
@ -3,7 +3,7 @@ use std::{
|
|||
sync::{LazyLock, OnceLock},
|
||||
};
|
||||
|
||||
use axum::{routing::get, Router};
|
||||
use axum::{Router, routing::get};
|
||||
use config::DispatchConfig;
|
||||
use tokio::net::TcpListener;
|
||||
use tracing::error;
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
use axum::{extract::State, Json};
|
||||
use axum::{Json, extract::State};
|
||||
|
||||
use crate::{
|
||||
data::{QueryDispatchRsp, ServerListInfo},
|
||||
AppState,
|
||||
data::{QueryDispatchRsp, ServerListInfo},
|
||||
};
|
||||
|
||||
pub const ROUTE_ENDPOINT: &str = "/query_dispatch";
|
||||
|
|
|
@ -1,20 +1,20 @@
|
|||
use axum::{
|
||||
Json,
|
||||
extract::{Query, State},
|
||||
response::IntoResponse,
|
||||
Json,
|
||||
};
|
||||
use base64::{display::Base64Display, engine::general_purpose::STANDARD, Engine};
|
||||
use base64::{Engine, display::Base64Display, engine::general_purpose::STANDARD};
|
||||
use serde::{Deserialize, Serialize, Serializer};
|
||||
use tracing::debug;
|
||||
use trigger_cryptography::rsa;
|
||||
use trigger_sv::config::RsaSetting;
|
||||
|
||||
use crate::{
|
||||
AppState,
|
||||
data::{
|
||||
CdnConfExt, CdnDesignData, CdnGameRes, CdnSilenceData, RegionExtension, RegionSwitchFunc,
|
||||
ServerDispatchData, ServerGateway,
|
||||
},
|
||||
AppState,
|
||||
};
|
||||
|
||||
pub const ROUTE_ENDPOINT: &str = "/query_gateway";
|
||||
|
@ -127,7 +127,10 @@ fn internal_process(
|
|||
msg: String::with_capacity(0),
|
||||
region_name: Borrowed(&server.name),
|
||||
title: Borrowed(&server.title),
|
||||
client_secret_key: Owned(base64::engine::general_purpose::STANDARD.encode(&state.environment.security.static_key.seed_buf)),
|
||||
client_secret_key: Owned(
|
||||
base64::engine::general_purpose::STANDARD
|
||||
.encode(&state.environment.security.static_key.seed_buf),
|
||||
),
|
||||
cdn_check_url: String::with_capacity(0),
|
||||
gateway: Some(ServerGateway {
|
||||
ip: Borrowed(&server.addr),
|
||||
|
@ -139,21 +142,33 @@ fn internal_process(
|
|||
cdn_conf_ext: Some(CdnConfExt {
|
||||
// TODO: unhardcode this
|
||||
design_data: CdnDesignData {
|
||||
base_url: Borrowed("https://autopatchos.zenlesszonezero.com/design_data/1.6_live/output_6898738_6ffe812558/client/"),
|
||||
data_revision: Borrowed("6898738"),
|
||||
md5_files: Borrowed(r#"[{"fileName": "data_version", "fileSize": 2065, "fileMD5": "16970197844668905690"}]"#),
|
||||
base_url: Borrowed(
|
||||
"https://autopatchcn.juequling.com/design_data/beta_live/output_7054632_323d17319c/client/",
|
||||
),
|
||||
data_revision: Borrowed("7054632"),
|
||||
md5_files: Borrowed(
|
||||
r#"[{"fileName": "data_version", "fileSize": 4503, "fileMD5": "419987357302147246"}]"#,
|
||||
),
|
||||
},
|
||||
game_res: CdnGameRes {
|
||||
audio_revision: Borrowed("6898738"),
|
||||
base_url: Borrowed("https://autopatchos.zenlesszonezero.com/game_res/1.6_live/output_6898738_6ffe812558/client/"),
|
||||
audio_revision: Borrowed("7025371"),
|
||||
base_url: Borrowed(
|
||||
"https://autopatchcn.juequling.com/game_res/beta_live/output_7054632_323d17319c/client/",
|
||||
),
|
||||
branch: Borrowed("beta_live"),
|
||||
md5_files: Borrowed(r#"[{"fileName": "res_version", "fileSize": 1167660, "fileMD5": "8072678507435758384"}, {"fileName": "audio_version", "fileSize": 15447, "fileMD5": "5401804085122358755"}, {"fileName": "base_revision", "fileSize": 4, "fileMD5": "4524394692449115962"}]"#),
|
||||
res_revision: Borrowed("6898738"),
|
||||
md5_files: Borrowed(
|
||||
r#"[{"fileName": "res_version", "fileSize": 2379030, "fileMD5": "15840336186912297231"}, {"fileName": "audio_version", "fileSize": 30435, "fileMD5": "15675397132378459243"}, {"fileName": "base_revision", "fileSize": 18, "fileMD5": "18079377284431001248"}]"#,
|
||||
),
|
||||
res_revision: Borrowed("7054632"),
|
||||
},
|
||||
silence_data: CdnSilenceData {
|
||||
base_url: Borrowed("https://autopatchos.zenlesszonezero.com/design_data/1.6_live/output_6898738_6ffe812558/client_silence/"),
|
||||
md5_files: Borrowed(r#"[{"fileName": "silence_version", "fileSize": 130, "fileMD5": "2077712550601860122"}]"#),
|
||||
silence_revision: Borrowed("6898738"),
|
||||
base_url: Borrowed(
|
||||
"https://autopatchcn.juequling.com/design_data/beta_live/output_7054632_323d17319c/client_silence/",
|
||||
),
|
||||
md5_files: Borrowed(
|
||||
r#"[{"fileName": "silence_version", "fileSize": 647, "fileMD5": "15019531890587528788"}]"#,
|
||||
),
|
||||
silence_revision: Borrowed("7042559"),
|
||||
},
|
||||
pre_download: None,
|
||||
}),
|
||||
|
@ -174,7 +189,7 @@ fn internal_process(
|
|||
url_check_nap: String::new(),
|
||||
url_check_sdk: String::new(),
|
||||
}),
|
||||
}
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
use tracing::{debug, warn};
|
||||
use trigger_logic::quest::EQuestType;
|
||||
use trigger_protocol::{util::ProtocolUnit, AvatarSync, CafeSync, ItemSync, PlayerSyncScNotify};
|
||||
use trigger_protocol::{AvatarSync, CafeSync, ItemSync, PlayerSyncScNotify, util::ProtocolUnit};
|
||||
use trigger_sv::gm_command::GMCommand;
|
||||
|
||||
use crate::AppState;
|
||||
|
||||
use super::{player::AvatarPropertyChanges, NapPlayer};
|
||||
use super::{NapPlayer, player::AvatarPropertyChanges};
|
||||
|
||||
pub struct CommandContext<'player> {
|
||||
pub player: &'player mut NapPlayer,
|
||||
|
|
|
@ -6,7 +6,7 @@ use quest::QuestModel;
|
|||
use ramen::RamenModel;
|
||||
use role::RoleModel;
|
||||
use scene::SceneModel;
|
||||
use trigger_database::{entity::*, prelude::*, DatabaseConnection};
|
||||
use trigger_database::{DatabaseConnection, entity::*, prelude::*};
|
||||
use trigger_fileconfig::NapFileCfg;
|
||||
use trigger_logic::scene::ESceneType;
|
||||
use trigger_protocol::PlayerBasicInfo;
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use trigger_database::DatabaseConnection;
|
||||
use trigger_database::entity::*;
|
||||
use trigger_database::prelude::*;
|
||||
use trigger_database::DatabaseConnection;
|
||||
|
||||
pub async fn load_player_basic_info(
|
||||
db: &DatabaseConnection,
|
||||
|
|
|
@ -23,8 +23,6 @@ pub struct AvatarPropertyChanges {
|
|||
}
|
||||
|
||||
impl RoleModel {
|
||||
const PIDORS: &[i32] = &[1331, 1291];
|
||||
|
||||
pub async fn init(context: NapContext) -> Self {
|
||||
let avatar_map = Self::load_or_create_avatar_map(&context).await;
|
||||
|
||||
|
@ -332,7 +330,6 @@ impl RoleModel {
|
|||
pub async fn unlock_avatars(&mut self, avatar_id_list: &[i32]) -> Vec<u32> {
|
||||
let models = avatar_id_list
|
||||
.iter()
|
||||
.filter(|id| !Self::PIDORS.contains(*id))
|
||||
.filter(|id| !self.is_avatar_unlocked(**id as u32))
|
||||
.map(|id| {
|
||||
self.context
|
||||
|
|
|
@ -12,7 +12,7 @@ use tracing::{error, info};
|
|||
use trigger_database::DatabaseConnection;
|
||||
use trigger_fileconfig::NapFileCfg;
|
||||
use trigger_sv::{
|
||||
config::{load_json_config, ServerEnvironmentConfiguration, TomlConfig},
|
||||
config::{ServerEnvironmentConfiguration, TomlConfig, load_json_config},
|
||||
die, logging,
|
||||
net::{ServerNetworkManager, ServerType},
|
||||
print_banner,
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
use std::sync::Arc;
|
||||
|
||||
use crate::{
|
||||
logic::{gm_util, NapPlayer},
|
||||
session::GameSession,
|
||||
AppState,
|
||||
logic::{NapPlayer, gm_util},
|
||||
session::GameSession,
|
||||
};
|
||||
use tokio::sync::Mutex;
|
||||
use tracing::{debug, info, warn};
|
||||
|
|
|
@ -179,6 +179,20 @@ mod client_systems_module {
|
|||
}
|
||||
}
|
||||
|
||||
pub async fn on_end_newbie(
|
||||
_context: &mut MessageContext<'_, '_>,
|
||||
_request: EndNewbieCsReq,
|
||||
) -> EndNewbieScRsp {
|
||||
EndNewbieScRsp { retcode: 0 }
|
||||
}
|
||||
|
||||
pub async fn on_sync_global_variables(
|
||||
_context: &mut MessageContext<'_, '_>,
|
||||
_request: SyncGlobalVariablesCsReq,
|
||||
) -> SyncGlobalVariablesScRsp {
|
||||
SyncGlobalVariablesScRsp { retcode: 0 }
|
||||
}
|
||||
|
||||
pub async fn on_get_trashbin_hermit_data(
|
||||
_context: &mut MessageContext<'_, '_>,
|
||||
_request: GetTrashbinHermitDataCsReq,
|
||||
|
|
12
crates/game-server/src/session/message/flower_shop.rs
Normal file
12
crates/game-server/src/session/message/flower_shop.rs
Normal file
|
@ -0,0 +1,12 @@
|
|||
use super::MessageContext;
|
||||
use trigger_codegen::handlers;
|
||||
|
||||
#[handlers]
|
||||
mod flower_shop_module {
|
||||
pub async fn on_get_flower_shop_data(
|
||||
_context: &mut MessageContext<'_, '_>,
|
||||
_request: GetFlowerShopDataCsReq,
|
||||
) -> GetFlowerShopDataScRsp {
|
||||
GetFlowerShopDataScRsp { retcode: 0 }
|
||||
}
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
use trigger_encoding::Encodeable;
|
||||
use trigger_protocol::{util::ProtocolUnit, ClientCmdID};
|
||||
use trigger_protocol::{ClientCmdID, util::ProtocolUnit};
|
||||
|
||||
use super::GameSession;
|
||||
use crate::AppState;
|
||||
|
@ -40,7 +40,8 @@ modules! {
|
|||
miniscape_entrust,
|
||||
fishing_contest,
|
||||
ridus_got_boo,
|
||||
qa_game
|
||||
qa_game,
|
||||
flower_shop
|
||||
}
|
||||
|
||||
client_message_forwarding! {
|
||||
|
|
|
@ -15,7 +15,7 @@ use trigger_sv::{
|
|||
net::{ServerNetworkManager, ServerType},
|
||||
};
|
||||
|
||||
use crate::logic::{scene_util, NapPlayer};
|
||||
use crate::logic::{NapPlayer, scene_util};
|
||||
|
||||
pub mod message;
|
||||
|
||||
|
|
|
@ -12,10 +12,10 @@ use trigger_sv::{
|
|||
};
|
||||
|
||||
use crate::{
|
||||
AppState,
|
||||
net::{Connection, NetPacket},
|
||||
session::SessionState,
|
||||
util::BinExt,
|
||||
AppState,
|
||||
};
|
||||
|
||||
pub async fn handle_message(connection: &Connection, state: &'static AppState, packet: NetPacket) {
|
||||
|
@ -41,20 +41,33 @@ pub async fn handle_message(connection: &Connection, state: &'static AppState, p
|
|||
on_keep_alive(
|
||||
connection,
|
||||
state,
|
||||
KeepAliveNotify::decode(&*packet.body).unwrap_or_default()
|
||||
).await
|
||||
KeepAliveNotify::decode(&*packet.body).unwrap_or_default(),
|
||||
)
|
||||
.await
|
||||
}
|
||||
cmd_id if connection.session.is_logged_in() => {
|
||||
match trigger_protobuf::pb_to_common_protocol_unit(cmd_id, &packet.body) {
|
||||
Ok(Some(unit)) => state.network_mgr.send_to(ServerType::GameServer, 0, ForwardClientProtocolMessage {
|
||||
session_id: connection.session.id,
|
||||
request_id: head.packet_id,
|
||||
message: unit,
|
||||
}).await,
|
||||
Ok(Some(unit)) => {
|
||||
state
|
||||
.network_mgr
|
||||
.send_to(
|
||||
ServerType::GameServer,
|
||||
0,
|
||||
ForwardClientProtocolMessage {
|
||||
session_id: connection.session.id,
|
||||
request_id: head.packet_id,
|
||||
message: unit,
|
||||
},
|
||||
)
|
||||
.await
|
||||
}
|
||||
Ok(None) => warn!("ignoring message with unknown cmd_id: {cmd_id}"),
|
||||
Err(err) => error!(
|
||||
"failed to decode a message with cmd_id: {} from {} (player_uid: {}), error: {}",
|
||||
cmd_id, connection.addr(), connection.session.player_uid(), err
|
||||
cmd_id,
|
||||
connection.addr(),
|
||||
connection.session.player_uid(),
|
||||
err
|
||||
),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
use tokio::sync::mpsc;
|
||||
use tracing::warn;
|
||||
|
||||
use crate::{net::NetPacket, AppState};
|
||||
use crate::{AppState, net::NetPacket};
|
||||
|
||||
#[derive(Clone)]
|
||||
pub struct MessageHandler(mpsc::UnboundedSender<(u64, NetPacket)>);
|
||||
|
|
|
@ -2,8 +2,8 @@ use std::{
|
|||
io,
|
||||
net::SocketAddr,
|
||||
sync::{
|
||||
atomic::{AtomicU32, Ordering::SeqCst},
|
||||
Arc, OnceLock,
|
||||
atomic::{AtomicU32, Ordering::SeqCst},
|
||||
},
|
||||
time::Duration,
|
||||
};
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use std::io::{Cursor, Write};
|
||||
|
||||
use byteorder::{WriteBytesExt, BE};
|
||||
use byteorder::{BE, WriteBytesExt};
|
||||
use trigger_protobuf::PacketHead;
|
||||
|
||||
pub struct NetPacket {
|
||||
|
|
|
@ -3,7 +3,7 @@ use std::{io, net::SocketAddr};
|
|||
use tokio::net::TcpListener;
|
||||
use tracing::info;
|
||||
|
||||
use crate::{message_handler::MessageHandler, AppState};
|
||||
use crate::{AppState, message_handler::MessageHandler};
|
||||
|
||||
pub async fn serve(
|
||||
addr: SocketAddr,
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use std::sync::{
|
||||
atomic::{AtomicI64, Ordering::SeqCst},
|
||||
OnceLock,
|
||||
atomic::{AtomicI64, Ordering::SeqCst},
|
||||
};
|
||||
|
||||
use atomic_enum::atomic_enum;
|
||||
|
|
|
@ -107,6 +107,6 @@ use trigger_protocol::{
|
|||
};
|
||||
use trigger_sv::message::GameStateCallback;
|
||||
|
||||
use crate::logic::{message::RunEventGraphEvent, GameStateListener};
|
||||
use crate::logic::{GameStateListener, message::RunEventGraphEvent};
|
||||
|
||||
use super::scene_unit::{InteractContainer, SceneUnitTag};
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use bevy_ecs::{prelude::*, query::QueryData};
|
||||
use tracing::warn;
|
||||
use trigger_fileconfig::{main_city_script::MainCityConfig, NapFileCfg};
|
||||
use trigger_fileconfig::{NapFileCfg, main_city_script::MainCityConfig};
|
||||
|
||||
use crate::logic::save::HallSceneSaveData;
|
||||
|
||||
|
|
|
@ -3,13 +3,13 @@ use tracing::{debug, warn};
|
|||
use trigger_protocol::InteractWithUnitScRsp;
|
||||
use trigger_sv::message::GameStateCallback;
|
||||
|
||||
use crate::logic::{message::InteractWithUnitEvent, GameStateListener};
|
||||
use crate::logic::{GameStateListener, message::InteractWithUnitEvent};
|
||||
|
||||
use super::{
|
||||
NapResources,
|
||||
event_graph::{ActionChangeInteractCfgEvent, EventGraph, GraphEvent},
|
||||
hall::MainCitySection,
|
||||
scene_unit::{InteractContainer, SceneUnitTag},
|
||||
NapResources,
|
||||
};
|
||||
|
||||
pub fn tick_change_interact(
|
||||
|
|
|
@ -8,11 +8,11 @@ use scene::PlayerEnterScene;
|
|||
use trigger_fileconfig::main_city_script::MainCityConfig;
|
||||
|
||||
use super::{
|
||||
GameStateListener,
|
||||
message::{
|
||||
EnterSectionEvent, InteractWithUnitEvent, PlayerMoveEvent, RunEventGraphEvent,
|
||||
SwitchRoleEvent,
|
||||
},
|
||||
GameStateListener,
|
||||
};
|
||||
|
||||
pub mod event_graph;
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
use bevy_ecs::prelude::*;
|
||||
|
||||
use crate::logic::{
|
||||
save::{HallSceneSaveData, MainCityPositionSave},
|
||||
GameStateListener,
|
||||
save::{HallSceneSaveData, MainCityPositionSave},
|
||||
};
|
||||
|
||||
use super::{
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use bevy_ecs::system::Resource;
|
||||
use trigger_encoding::Encodeable;
|
||||
use trigger_protocol::{util::ProtocolUnit, ClientCmdID};
|
||||
use trigger_protocol::{ClientCmdID, util::ProtocolUnit};
|
||||
use trigger_sv::{
|
||||
message::{GameStateCallback, GameStateCallbackMessage},
|
||||
net::{ServerNetworkManager, ServerType},
|
||||
|
|
|
@ -2,8 +2,8 @@ use bevy_ecs::event::Event;
|
|||
use trigger_encoding::Decodeable;
|
||||
use trigger_logic::scene::Transform;
|
||||
use trigger_protocol::{
|
||||
util::ProtocolUnit, ClientCmdID, EnterSectionCsReq, InteractWithUnitCsReq, RunEventGraphCsReq,
|
||||
SavePosInMainCityCsReq, SwitchRoleCsReq,
|
||||
ClientCmdID, EnterSectionCsReq, InteractWithUnitCsReq, RunEventGraphCsReq,
|
||||
SavePosInMainCityCsReq, SwitchRoleCsReq, util::ProtocolUnit,
|
||||
};
|
||||
|
||||
use super::ecs::NapEcs;
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use std::{collections::HashMap, sync::mpsc, thread};
|
||||
|
||||
use ecs::{scene::PlayerEnterScene, NapEcs};
|
||||
use ecs::{NapEcs, scene::PlayerEnterScene};
|
||||
use message::ProtocolEventHandler;
|
||||
use tracing::debug;
|
||||
use trigger_protocol::util::ProtocolUnit;
|
||||
|
@ -11,8 +11,8 @@ mod listener;
|
|||
mod message;
|
||||
|
||||
pub mod save;
|
||||
pub use ecs::hall::HallInitData;
|
||||
pub use ecs::NapResources;
|
||||
pub use ecs::hall::HallInitData;
|
||||
pub use listener::GameStateListener;
|
||||
|
||||
#[derive(Clone)]
|
||||
|
|
|
@ -8,9 +8,9 @@ use dashmap::DashMap;
|
|||
use logic::{GameRunner, NapResources};
|
||||
use session::HallSession;
|
||||
use tracing::{error, info};
|
||||
use trigger_fileconfig::{main_city_script::MainCityConfig, NapFileCfg};
|
||||
use trigger_fileconfig::{NapFileCfg, main_city_script::MainCityConfig};
|
||||
use trigger_sv::{
|
||||
config::{load_json_config, ServerEnvironmentConfiguration, TomlConfig},
|
||||
config::{ServerEnvironmentConfiguration, TomlConfig, load_json_config},
|
||||
die, logging,
|
||||
net::{ServerNetworkManager, ServerType},
|
||||
print_banner,
|
||||
|
|
|
@ -5,9 +5,9 @@ use trigger_sv::message::{
|
|||
};
|
||||
|
||||
use crate::{
|
||||
AppState,
|
||||
logic::{GameStateListener, HallInitData},
|
||||
session::HallSession,
|
||||
AppState,
|
||||
};
|
||||
|
||||
pub async fn handle_message(state: &'static AppState, packet: trigger_sv::message::NetworkPacket) {
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
use std::borrow::Cow;
|
||||
|
||||
use axum::{
|
||||
Json, Router,
|
||||
extract::{Query, State},
|
||||
routing::get,
|
||||
Json, Router,
|
||||
};
|
||||
use serde::{Deserialize, Serialize};
|
||||
use tokio::net::TcpListener;
|
||||
|
@ -64,7 +64,7 @@ async fn gm_api(
|
|||
return Json(Response {
|
||||
retcode: 2,
|
||||
message: Some(Cow::Owned(format!("invalid command format: {err}"))),
|
||||
})
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
use proc_macro2::TokenStream;
|
||||
use quote::quote;
|
||||
use syn::{
|
||||
parse_macro_input, Data, DeriveInput, Field, Fields, GenericArgument, PathArguments, Type,
|
||||
TypePath,
|
||||
Data, DeriveInput, Field, Fields, GenericArgument, PathArguments, Type, TypePath,
|
||||
parse_macro_input,
|
||||
};
|
||||
|
||||
pub fn impl_gm_input(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
|
||||
|
@ -114,7 +114,7 @@ pub fn impl_gm_input(input: proc_macro::TokenStream) -> proc_macro::TokenStream
|
|||
fn from_str(input: &str) -> Result<Self, GMInputParseError> {
|
||||
use GMInputParseError::*;
|
||||
|
||||
static CMD_TYPE_MAP: ::std::sync::LazyLock<::std::collections::HashMap<&'static str, #internal_enum_name>> =
|
||||
static CMD_TYPE_MAP: ::std::sync::LazyLock<::std::collections::HashMap<&'static str, #internal_enum_name>> =
|
||||
::std::sync::LazyLock::new(|| ::std::collections::HashMap::from([#internal_enum_mapping]));
|
||||
|
||||
let mut data = input.split(' ');
|
||||
|
@ -165,4 +165,3 @@ fn get_field_sub_type(field: &Field) -> String {
|
|||
_ => panic!("Unsupported field type"),
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use proc_macro2::TokenStream;
|
||||
use quote::quote;
|
||||
use syn::{parse_macro_input, Data, DeriveInput, Fields, Ident};
|
||||
use syn::{Data, DeriveInput, Fields, Ident, parse_macro_input};
|
||||
|
||||
pub fn impl_decodeable(item: proc_macro::TokenStream) -> proc_macro::TokenStream {
|
||||
let input = parse_macro_input!(item as DeriveInput);
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use proc_macro2::TokenStream;
|
||||
use quote::quote;
|
||||
use syn::{parse_macro_input, Data, DeriveInput, Fields, Ident};
|
||||
use syn::{Data, DeriveInput, Fields, Ident, parse_macro_input};
|
||||
|
||||
pub fn impl_encodeable(item: proc_macro::TokenStream) -> proc_macro::TokenStream {
|
||||
let input = parse_macro_input!(item as DeriveInput);
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use proc_macro2::TokenStream;
|
||||
use quote::{quote, ToTokens};
|
||||
use syn::{parse_macro_input, FnArg, Item, ItemMod, ReturnType};
|
||||
use quote::{ToTokens, quote};
|
||||
use syn::{FnArg, Item, ItemMod, ReturnType, parse_macro_input};
|
||||
|
||||
pub fn imp(input: proc_macro::TokenStream) -> proc_macro::TokenStream {
|
||||
const INVALID_FUNCTION_SIGNATURE_MSG: &str = "functions in message handler module should have following signature: fn(&mut MessageContext<'_>, CsReq) -> ScRsp";
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use proc_macro::TokenStream;
|
||||
use quote::{quote, ToTokens};
|
||||
use syn::{parse_macro_input, DeriveInput, Meta, MetaList};
|
||||
use quote::{ToTokens, quote};
|
||||
use syn::{DeriveInput, Meta, MetaList, parse_macro_input};
|
||||
|
||||
mod commands;
|
||||
mod decodeable;
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
#![allow(unused)]
|
||||
|
||||
use super::tables::{
|
||||
LOOKUP_G11, LOOKUP_G13, LOOKUP_G14, LOOKUP_G2, LOOKUP_G3, LOOKUP_G9, LOOKUP_RCON, LOOKUP_SBOX,
|
||||
LOOKUP_G2, LOOKUP_G3, LOOKUP_G9, LOOKUP_G11, LOOKUP_G13, LOOKUP_G14, LOOKUP_RCON, LOOKUP_SBOX,
|
||||
LOOKUP_SBOX_INV, SHIFT_ROWS_TABLE, SHIFT_ROWS_TABLE_INV,
|
||||
};
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use rsa::{
|
||||
pkcs1v15::SigningKey, sha2::Sha256, signature::RandomizedSigner, Pkcs1v15Encrypt,
|
||||
RsaPrivateKey, RsaPublicKey,
|
||||
Pkcs1v15Encrypt, RsaPrivateKey, RsaPublicKey, pkcs1v15::SigningKey, sha2::Sha256,
|
||||
signature::RandomizedSigner,
|
||||
};
|
||||
|
||||
const RSA_CHUNK_SIZE: usize = 117;
|
||||
|
|
|
@ -10,10 +10,10 @@ pub use sea_orm::DbErr;
|
|||
use tracing::error;
|
||||
|
||||
pub mod prelude {
|
||||
pub use sea_orm::entity::prelude::*;
|
||||
pub use sea_orm::entity::ActiveValue::*;
|
||||
pub use sea_orm::query::Condition;
|
||||
pub use sea_orm::TransactionTrait;
|
||||
pub use sea_orm::entity::ActiveValue::*;
|
||||
pub use sea_orm::entity::prelude::*;
|
||||
pub use sea_orm::query::Condition;
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
use byteorder::{ReadBytesExt, WriteBytesExt, BE};
|
||||
use byteorder::{BE, ReadBytesExt, WriteBytesExt};
|
||||
use std::collections::HashMap;
|
||||
use std::io::{self, Read, Write};
|
||||
|
||||
|
|
|
@ -215,17 +215,32 @@ table EquipmentSuitTemplate {
|
|||
id: int;
|
||||
name: string;
|
||||
primary_condition: int;
|
||||
primary_suit_propertys: [Property];
|
||||
unk_3: int;
|
||||
primary_suit_ability: int;
|
||||
primary_description: string;
|
||||
secondary_condition: int;
|
||||
secondary_suit_propertys: [Property];
|
||||
unk_7: int;
|
||||
secondary_suit_ability: int;
|
||||
secondary_description: string;
|
||||
suit_item_icon: string;
|
||||
suit_icon: string;
|
||||
suit_story: string;
|
||||
suit_filter_option: string;
|
||||
suit_icon: string;
|
||||
suit_item_icon: string;
|
||||
unk_14: int;
|
||||
order: int;
|
||||
unk_16: int;
|
||||
unk_17: int;
|
||||
unk_18: int;
|
||||
unk_19: int;
|
||||
unk_20: int;
|
||||
unk_21: int;
|
||||
primary_suit_propertys: [Property];
|
||||
unk_23: [int];
|
||||
unk_24: int;
|
||||
unk_25: [int];
|
||||
unk_26: [int];
|
||||
unk_27: [int];
|
||||
tag: string;
|
||||
}
|
||||
|
||||
table HollowConfigTemplate {
|
||||
|
@ -380,6 +395,160 @@ table ConditionConfigTemplate {
|
|||
type: int;
|
||||
}
|
||||
|
||||
table AvatarBattleTemplate {
|
||||
id: int;
|
||||
unk_1: [int];
|
||||
unk_2: [int];
|
||||
unk_3: [int];
|
||||
unk_4: [int];
|
||||
unk_5: [int];
|
||||
unk_6: [int];
|
||||
unk_7: [int];
|
||||
unk_8: int;
|
||||
unk_9: int;
|
||||
unk_10: int;
|
||||
avatar_piece_id: int;
|
||||
unk_12: int;
|
||||
unk_13: int;
|
||||
hp_max: int;
|
||||
health_growth: int;
|
||||
unk_16: int;
|
||||
unk_17: int;
|
||||
unk_18: int;
|
||||
unk_19: int;
|
||||
unk_20: int;
|
||||
attack: int;
|
||||
attack_growth: int;
|
||||
defence: int;
|
||||
defence_growth: int;
|
||||
crit: int;
|
||||
crit_damage: int;
|
||||
crit_res: int;
|
||||
crit_damage_res: int;
|
||||
pen_rate: int;
|
||||
pen_delta: int;
|
||||
luck: int;
|
||||
stun: int;
|
||||
break_stun: int;
|
||||
element_abnormal_power: int;
|
||||
sp_bar_point: int;
|
||||
sp_recover: int;
|
||||
element_mystery: int;
|
||||
rbl: int;
|
||||
rbl_correction_factor: int;
|
||||
rbl_probability: int;
|
||||
unk_41: int;
|
||||
unk_42: int;
|
||||
unk_43: int;
|
||||
unk_44: int;
|
||||
unk_45: int;
|
||||
unk_46: int;
|
||||
unk_47: int;
|
||||
unk_48: int;
|
||||
unk_49: int;
|
||||
unk_50: int;
|
||||
unk_51: int;
|
||||
unk_52: int;
|
||||
unk_53: int;
|
||||
unk_54: int;
|
||||
unk_55: int;
|
||||
unk_56: int;
|
||||
unk_57: int;
|
||||
unk_58: int;
|
||||
unk_59: int;
|
||||
unk_60: int;
|
||||
unk_61: int;
|
||||
unk_62: int;
|
||||
unk_63: int;
|
||||
unk_64: int;
|
||||
unk_65: int;
|
||||
unk_66: int;
|
||||
tags: [string];
|
||||
unk_68: [int];
|
||||
unk_69: [int];
|
||||
unk_70: int;
|
||||
unk_71: int;
|
||||
element: [int];
|
||||
hit_type: [int];
|
||||
unk_element_camp: [string];
|
||||
unk_75: int;
|
||||
unk_76: short;
|
||||
}
|
||||
|
||||
table AvatarLevelAdvanceTemplate {
|
||||
avatar_id: int;
|
||||
id: int;
|
||||
min_level: int;
|
||||
max_level: int;
|
||||
hp_max: int;
|
||||
unk_5: int;
|
||||
unk_6: int;
|
||||
attack: int;
|
||||
defence: int;
|
||||
unk_9: int;
|
||||
unk_10: int;
|
||||
unk_11: int;
|
||||
unk_12: int;
|
||||
unk_13: int;
|
||||
unk_14: int;
|
||||
unk_15: int;
|
||||
unk_16: int;
|
||||
unk_17: int;
|
||||
unk_18: [int];
|
||||
promotion_costs: [RefineCost];
|
||||
}
|
||||
|
||||
table WeaponLevelTemplate {
|
||||
rarity: int;
|
||||
level: int;
|
||||
rate: int;
|
||||
exp: int;
|
||||
}
|
||||
|
||||
table WeaponStarTemplate {
|
||||
rarity: int;
|
||||
star: int;
|
||||
min_level: int;
|
||||
max_level: int;
|
||||
star_rate: int;
|
||||
rand_rate: int;
|
||||
unk_6: int;
|
||||
unk_7: int;
|
||||
unk_8: int;
|
||||
unk_9: int;
|
||||
unk_10: int;
|
||||
unk_11: int;
|
||||
unk_12: int;
|
||||
}
|
||||
|
||||
table AvatarPassiveSkillTemplate {
|
||||
skill_id: int;
|
||||
avatar_id: int;
|
||||
min_avatar_level: int;
|
||||
min_passive_skill_level: int;
|
||||
unlock_passive_skill_level: int;
|
||||
unk_5: int;
|
||||
unk_levelup: string;
|
||||
unk_7: int;
|
||||
unk_8: int;
|
||||
unk_9: int;
|
||||
unk_10: int;
|
||||
propertys: [Property];
|
||||
names: [string];
|
||||
descriptions: [string];
|
||||
materials_costs: [RefineCost];
|
||||
}
|
||||
|
||||
table EquipmentLevelTemplate {
|
||||
rarity: int;
|
||||
level: int;
|
||||
property_rate: int;
|
||||
unk_3: int;
|
||||
unk_4: int;
|
||||
unk_5: int;
|
||||
unk_6: int;
|
||||
}
|
||||
|
||||
table AvatarBaseTemplateTb {
|
||||
data: [AvatarBaseTemplate];
|
||||
}
|
||||
|
@ -451,3 +620,27 @@ table TeleportConfigTemplateTb {
|
|||
table ConditionConfigTemplateTb {
|
||||
data: [ConditionConfigTemplate];
|
||||
}
|
||||
|
||||
table AvatarBattleTemplateTb {
|
||||
data: [AvatarBattleTemplate];
|
||||
}
|
||||
|
||||
table AvatarLevelAdvanceTemplateTb {
|
||||
data: [AvatarLevelAdvanceTemplate];
|
||||
}
|
||||
|
||||
table WeaponLevelTemplateTb {
|
||||
data: [WeaponLevelTemplate];
|
||||
}
|
||||
|
||||
table WeaponStarTemplateTb {
|
||||
data: [WeaponStarTemplate];
|
||||
}
|
||||
|
||||
table AvatarPassiveSkillTemplateTb {
|
||||
data: [AvatarPassiveSkillTemplate];
|
||||
}
|
||||
|
||||
table EquipmentLevelTemplateTb {
|
||||
data: [EquipmentLevelTemplate];
|
||||
}
|
File diff suppressed because it is too large
Load diff
|
@ -58,4 +58,10 @@ file_cfg! {
|
|||
BattleGroupConfigTemplateTb;
|
||||
MusicPlayerConfigTemplateTb;
|
||||
TeleportConfigTemplateTb;
|
||||
AvatarBattleTemplateTb;
|
||||
AvatarLevelAdvanceTemplateTb;
|
||||
WeaponLevelTemplateTb;
|
||||
WeaponStarTemplateTb;
|
||||
AvatarPassiveSkillTemplateTb;
|
||||
EquipmentLevelTemplateTb;
|
||||
}
|
||||
|
|
91
crates/trigger-logic/src/battle.rs
Normal file
91
crates/trigger-logic/src/battle.rs
Normal file
|
@ -0,0 +1,91 @@
|
|||
use num_enum::{IntoPrimitive, TryFromPrimitive};
|
||||
|
||||
#[repr(u32)]
|
||||
#[derive(IntoPrimitive, TryFromPrimitive)]
|
||||
pub enum EPropertyType {
|
||||
Hp = 1,
|
||||
HpMax = 111,
|
||||
Atk = 121,
|
||||
BreakStun = 122,
|
||||
Def = 131,
|
||||
Crit = 201,
|
||||
CritDmg = 211,
|
||||
Pen = 231,
|
||||
PenValue = 232,
|
||||
SpRecover = 305,
|
||||
ElementMystery = 312,
|
||||
ElementAbnormalPower = 314,
|
||||
AddedDamageRatioPhysics = 315,
|
||||
AddedDamageRatioFire = 316,
|
||||
AddedDamageRatioIce = 317,
|
||||
AddedDamageRatioElec = 318,
|
||||
AddedDamageRatioEther = 319,
|
||||
// battle
|
||||
HpMaxBattle = 1111,
|
||||
AtkBattle = 1121,
|
||||
BreakStunBattle = 1122,
|
||||
DefBattle = 1131,
|
||||
CritBattle = 1201,
|
||||
CritDmgBattle = 1211,
|
||||
PenRatioBattle = 1231,
|
||||
PenDeltaBattle = 1232,
|
||||
SpRecoverBattle = 1305,
|
||||
ElementMysteryBattle = 1312,
|
||||
ElementAbnormalPowerBattle = 1314,
|
||||
AddedDamageRatioPhysicsBattle = 1315,
|
||||
AddedDamageRatioFireBattle = 1316,
|
||||
AddedDamageRatioIceBattle = 1317,
|
||||
AddedDamageRatioElecBattle = 1318,
|
||||
AddedDamageRatioEtherBattle = 1319,
|
||||
// base
|
||||
HpMaxBase = 11101,
|
||||
AtkBase = 12101,
|
||||
BreakStunBase = 12201,
|
||||
DefBase = 13101,
|
||||
CritBase = 20101,
|
||||
CritDmgBase = 21101,
|
||||
PenBase = 23101,
|
||||
PenValueBase = 23201,
|
||||
SpRecoverBase = 30501,
|
||||
ElementMysteryBase = 31201,
|
||||
ElementAbnormalPowerBase = 31401,
|
||||
// ratio
|
||||
HpMaxRatio = 11102,
|
||||
AtkRatio = 12102,
|
||||
BreakStunRatio = 12202,
|
||||
DefRatio = 13102,
|
||||
SpRecoverRatio = 30502,
|
||||
ElementAbnormalPowerRatio = 31402,
|
||||
// delta
|
||||
HpMaxDelta = 11103,
|
||||
AtkDelta = 12103,
|
||||
BreakStunDelta = 12203,
|
||||
DefDelta = 13103,
|
||||
CritDelta = 20103,
|
||||
CritDmgDelta = 21103,
|
||||
PenDelta = 23103,
|
||||
PenValueDelta = 23203,
|
||||
SpRecoverDelta = 30503,
|
||||
ElementMysteryDelta = 31203,
|
||||
ElementAbnormalPowerDelta = 31403,
|
||||
// damage ratios 1/3
|
||||
AddedDamageRatioPhysics1 = 31501,
|
||||
AddedDamageRatioPhysics3 = 31503,
|
||||
AddedDamageRatioFire1 = 31601,
|
||||
AddedDamageRatioFire3 = 31603,
|
||||
AddedDamageRatioIce1 = 31701,
|
||||
AddedDamageRatioIce3 = 31703,
|
||||
AddedDamageRatioElec1 = 31801,
|
||||
AddedDamageRatioElec3 = 31803,
|
||||
AddedDamageRatioEther1 = 31901,
|
||||
AddedDamageRatioEther3 = 31903,
|
||||
// --- custom
|
||||
// growth
|
||||
HpMaxGrowth = 9999_111_0,
|
||||
AtkGrowth = 9999_121_0,
|
||||
DefGrowth = 9999_131_0,
|
||||
// advance
|
||||
HpMaxAdvance = 9999_111_1,
|
||||
AtkAdvance = 9999_121_1,
|
||||
DefAdvance = 9999_131_1,
|
||||
}
|
|
@ -1,4 +1,5 @@
|
|||
pub mod action_pb;
|
||||
pub mod battle;
|
||||
pub mod item;
|
||||
pub mod quest;
|
||||
pub mod scene;
|
||||
|
|
|
@ -5,7 +5,7 @@ use std::{
|
|||
path::Path,
|
||||
};
|
||||
|
||||
use quote::{quote, ToTokens};
|
||||
use quote::{ToTokens, quote};
|
||||
use syn::{Field, GenericArgument, Item, PathArguments, Type, TypePath};
|
||||
|
||||
fn main() {
|
||||
|
|
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
@ -22,7 +22,7 @@ include!("../out/_.rs");
|
|||
include!("../out/protocol_map.rs");
|
||||
|
||||
#[derive(trigger_protobuf_derive::CmdID)]
|
||||
#[cmdid(8128)]
|
||||
#[cmdid(5636)]
|
||||
#[derive(trigger_protobuf_derive::XorFields, Clone, Copy, PartialEq, ::prost::Message)]
|
||||
pub struct FallbackRsp {}
|
||||
|
||||
|
|
|
@ -355,6 +355,7 @@ pub struct DungeonEquipInfo {
|
|||
#[derive(Default, Debug, Clone, Encodeable, Decodeable)]
|
||||
pub struct AvatarUnitInfo {
|
||||
pub avatar_id: u32,
|
||||
pub properties: HashMap<u32, i32>,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable)]
|
||||
|
@ -1222,6 +1223,30 @@ pub struct GetNewsStandDataScRsp {
|
|||
pub news_stand_data: Option<NewsStandData>,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(1323)]
|
||||
pub struct EndNewbieCsReq {
|
||||
pub group_id: u32,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(1324)]
|
||||
pub struct EndNewbieScRsp {
|
||||
pub retcode: i32,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(1325)]
|
||||
pub struct SyncGlobalVariablesCsReq {
|
||||
pub global_variables: HashMap<u32, i32>,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(1326)]
|
||||
pub struct SyncGlobalVariablesScRsp {
|
||||
pub retcode: i32,
|
||||
}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(1340)]
|
||||
pub struct GetTrashbinHermitDataCsReq {}
|
||||
|
@ -1757,3 +1782,15 @@ pub struct GetQuestionsAnswerGameDataCsReq {}
|
|||
pub struct GetQuestionsAnswerGameDataScRsp {
|
||||
pub retcode: i32,
|
||||
}
|
||||
|
||||
// FlowerShop
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(7150)]
|
||||
pub struct GetFlowerShopDataCsReq {}
|
||||
|
||||
#[derive(Default, Debug, Clone, Encodeable, Decodeable, ClientCmdID)]
|
||||
#[id(7151)]
|
||||
pub struct GetFlowerShopDataScRsp {
|
||||
pub retcode: i32,
|
||||
}
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
use serde::{de::DeserializeOwned, Deserialize, Deserializer};
|
||||
use serde::{Deserialize, Deserializer, de::DeserializeOwned};
|
||||
use std::net::SocketAddr;
|
||||
use tracing::error;
|
||||
use trigger_database::DatabaseSetting;
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
use crate::message::opcode;
|
||||
use trigger_codegen::{Decodeable, Encodeable};
|
||||
use trigger_protocol::{util::ProtocolUnit, DungeonEquipInfo};
|
||||
use trigger_protocol::{DungeonEquipInfo, util::ProtocolUnit};
|
||||
|
||||
#[derive(Debug, Encodeable, Decodeable)]
|
||||
pub struct BindClientSessionMessage {
|
||||
|
|
|
@ -4,7 +4,7 @@ use futures::future::BoxFuture;
|
|||
use tokio::task::JoinHandle;
|
||||
use tracing::warn;
|
||||
use trigger_encoding::Decodeable;
|
||||
use zeromq::{prelude::*, PullSocket, ZmqError};
|
||||
use zeromq::{PullSocket, ZmqError, prelude::*};
|
||||
|
||||
use crate::message::NetworkPacket;
|
||||
|
||||
|
|
|
@ -3,7 +3,7 @@ mod socket;
|
|||
|
||||
use std::{collections::HashMap, io::Cursor, net::SocketAddr};
|
||||
|
||||
pub use listener::{listen, RecvCallback};
|
||||
pub use listener::{RecvCallback, listen};
|
||||
use num_enum::{IntoPrimitive, TryFromPrimitive};
|
||||
pub use socket::ServerSocket;
|
||||
|
||||
|
|
|
@ -5,8 +5,8 @@ use std::time::Duration;
|
|||
use tokio::sync::mpsc;
|
||||
use tracing::warn;
|
||||
use trigger_encoding::Encodeable;
|
||||
use zeromq::prelude::*;
|
||||
use zeromq::PushSocket;
|
||||
use zeromq::prelude::*;
|
||||
|
||||
use crate::message::NetworkPacket;
|
||||
|
||||
|
|
|
@ -30,7 +30,7 @@ user = "root"
|
|||
password = "root"
|
||||
|
||||
[security]
|
||||
static_key = "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"
|
||||
static_key = "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"
|
||||
|
||||
[[security.rsa_versions]]
|
||||
version = 3
|
||||
|
|
Loading…
Reference in a new issue