引入新的配置项

This commit is contained in:
2026-02-03 22:19:47 +08:00
parent 55c1e49142
commit 54b86a44e1
6 changed files with 287 additions and 17 deletions

View File

@@ -40,6 +40,14 @@ mod ffi {
fn is_decompose(cfg: &Box<Config>) -> bool;
fn set_decompose(cfg: &mut Box<Config>, value: bool);
/// 倍攻
fn is_attack_power(cfg: &Box<Config>) -> bool;
fn set_attack_power(cfg: &mut Box<Config>, value: bool);
/// 装备变换
fn is_equip_transform(cfg: &Box<Config>) -> bool;
fn set_equip_transform(cfg: &mut Box<Config>, value: bool);
/// 从配置文件中读取一个配置项
fn get_config_value(
path: &CxxString,
@@ -73,17 +81,23 @@ pub struct Config {
is_forest: bool,
/// 分解
is_decompose: bool,
/// 倍攻
is_attack_power: bool,
/// 装备变换
is_equip_transform: bool,
}
impl Default for Config {
fn default() -> Self {
Self {
is_daily_missions: false,
is_archipelago: false,
is_spiral_abyss: false,
is_demonic_energy: false,
is_forest: false,
is_decompose: false,
is_daily_missions: true,
is_archipelago: true,
is_spiral_abyss: true,
is_demonic_energy: true,
is_forest: true,
is_decompose: true,
is_attack_power: true,
is_equip_transform: true,
}
}
}
@@ -94,7 +108,6 @@ impl Config {
// 你也可以加一个总注释、版本号等
format!(
r#"# 自动生成的配置文件
# 实现可能修改配置存储结构请不要使用程序化工具修改此配置文件如果非要这么做请链接utils.lib后使用其提供的接口。
# 做不做每日任务
is_daily_missions = {is_daily_missions}
@@ -113,6 +126,12 @@ is_forest = {is_forest}
# 分解
is_decompose = {is_decompose}
# 倍攻
is_attack_power = {is_attack_power}
# 装备变换
is_equip_transform = {is_equip_transform}
"#,
is_daily_missions = self.is_daily_missions,
is_archipelago = self.is_archipelago,
@@ -120,15 +139,17 @@ is_decompose = {is_decompose}
is_demonic_energy = self.is_demonic_energy,
is_forest = self.is_forest,
is_decompose = self.is_decompose,
is_attack_power = self.is_attack_power,
is_equip_transform = self.is_equip_transform,
)
}
pub fn save_with_comments(&self, path: impl AsRef<Path>) -> io::Result<()> {
/*let path = path.as_ref();
let path = path.as_ref();
if let Some(parent) = path.parent() {
fs::create_dir_all(parent)?;
}
fs::write(path, self.to_toml_with_comments())*/
fs::write(path, self.to_toml_with_comments())?;
Ok(())
}
@@ -137,7 +158,7 @@ is_decompose = {is_decompose}
/// - toml 缺字段:会自动用 Default 补齐(因为 #[serde(default)]
/// - 可选:如果你想“读取后把缺的字段补齐回写”,这里也做了回写
pub fn load_or_create(path: impl AsRef<Path>) -> Result<Self, Box<dyn std::error::Error>> {
/*let path = path.as_ref();
let path = path.as_ref();
if !path.exists() {
let cfg = Self::default();
@@ -150,15 +171,15 @@ is_decompose = {is_decompose}
// 可选:自动回写补全(比如用户旧版配置少字段时,补齐并带注释写回去)
// 如果你不想覆盖用户文件,把下面两行删掉即可。
cfg.save_with_comments(path)?;*/
let cfg = Config {
cfg.save_with_comments(path)?;
/*let cfg = Config {
is_daily_missions: true,
is_archipelago: true,
is_spiral_abyss: false,
is_demonic_energy: true,
is_forest: true,
is_decompose: true,
};
};*/
Ok(cfg)
}
@@ -227,6 +248,20 @@ pub(crate) fn set_decompose(this: &mut Box<Config>, flag: bool) {
this.is_decompose = flag;
}
fn is_attack_power(cfg: &Box<Config>) -> bool {
cfg.is_attack_power
}
fn set_attack_power(cfg: &mut Box<Config>, value: bool) {
cfg.is_attack_power = value;
}
fn is_equip_transform(cfg: &Box<Config>) -> bool {
cfg.is_equip_transform
}
fn set_equip_transform(cfg: &mut Box<Config>, value: bool) {
cfg.is_equip_transform = value;
}
pub(crate) fn set_config_value(
path: &CxxString,
path_name: &CxxString,

View File

@@ -7,6 +7,7 @@ use encoding_rs::Encoding;
use futures_util::SinkExt;
use prost::Message as WebMessage;
use spin::Mutex;
use std::ffi::CString;
use std::sync::OnceLock;
use std::sync::mpsc;
use tokio::net::TcpStream;
@@ -17,6 +18,7 @@ static LOGGER_SENDER: OnceLock<mpsc::Sender<Starpoles>> = OnceLock::new();
mod config;
mod log;
mod login;
mod network;
pub mod protobuf;
pub mod utils;

116
src/login.rs Normal file
View File

@@ -0,0 +1,116 @@
use crate::log::get_current_dir;
use crate::utils::cxx_string_to_string;
use cxx::CxxString;
use log::info;
use serde::{Deserialize, Serialize};
use std::fmt::Display;
use std::path::{Path, PathBuf};
use std::process::Command;
use std::{fs, io};
use sysinfo::{ProcessesToUpdate, System};
use toml::Value;
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(default)]
#[derive(Default)]
pub struct User {
username: String,
password: String,
server: String,
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(default)]
#[derive(Default)]
pub struct Login {
/// 协议登录exe路径
login_exe: String,
game_path: String,
list: Vec<User>,
}
#[cxx::bridge]
mod ffi {
extern "Rust" {
type Login;
fn load_login_config() -> Result<Box<Login>>;
fn get_login_size(cfg: &Box<Login>) -> usize;
fn get_login_exe(cfg: &Box<Login>) -> String;
fn login_game(cfg: &Box<Login>, index: usize) -> bool;
fn get_username(cfg: &Box<Login>, index: usize) -> String;
fn get_password(cfg: &Box<Login>, index: usize) -> String;
fn get_server(cfg: &Box<Login>, index: usize) -> String;
fn is_process_running() -> bool;
}
}
pub(crate) fn load_login_config() -> Result<Box<Login>, Box<dyn std::error::Error>> {
let path = PathBuf::from("C:\\Windows\\Starpoles\\login.toml"); /* get_current_dir().join("config").join("login.toml");*/
if !path.exists() {
fs::create_dir_all(path.parent().unwrap())?;
let cfg = Login::default();
fs::write(path, toml::to_string(&cfg).unwrap())?;
return Ok(Box::new(cfg));
}
let text = fs::read_to_string(path)?;
let cfg: Login = toml::from_str(&text)?;
Ok(Box::new(cfg))
}
pub(crate) fn get_login_size(p0: &Box<Login>) -> usize {
p0.list.len()
}
pub(crate) fn get_login_exe(p0: &Box<Login>) -> String {
p0.login_exe.clone()
}
pub(crate) fn get_username(p0: &Box<Login>, p1: usize) -> String {
p0.list[p1].username.clone()
}
pub(crate) fn get_password(p0: &Box<Login>, p1: usize) -> String {
p0.list[p1].password.clone()
}
pub(crate) fn get_server(p0: &Box<Login>, p1: usize) -> String {
p0.list[p1].server.clone()
}
pub(crate) fn login_game(p0: &Box<Login>, p1: usize) -> bool {
info!(
"协议登录:{}user:{}password:{},server:{}",
p0.login_exe, p0.list[p1].username, p0.list[p1].password, p0.list[p1].server
);
let status = Command::new(p0.login_exe.clone())
.args([
"-g",
&p0.game_path,
"-u",
&p0.list[p1].username,
"-p",
&p0.list[p1].password,
"-a",
&p0.list[p1].server,
])
.status()
.unwrap();
status.success()
}
fn is_process_running() -> bool {
let mut sys = System::new();
sys.refresh_processes(ProcessesToUpdate::All, true);
sys.processes()
.values()
.any(|p| p.name().eq_ignore_ascii_case("dnf.exe"))
}