feat(core): implemented SDK 0.5.12
This change allows to support game edition switching in settings
This commit is contained in:
parent
941851c234
commit
deacef3759
9 changed files with 118 additions and 41 deletions
4
Cargo.lock
generated
4
Cargo.lock
generated
|
@ -86,8 +86,8 @@ dependencies = [
|
||||||
|
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "anime-launcher-sdk"
|
name = "anime-launcher-sdk"
|
||||||
version = "0.5.11"
|
version = "0.5.12"
|
||||||
source = "git+https://github.com/an-anime-team/anime-launcher-sdk?tag=0.5.11#46547a886f51ba8c58918c0903273c3d3c63d5fa"
|
source = "git+https://github.com/an-anime-team/anime-launcher-sdk?tag=0.5.12#06f0f486b9e099fc96db71be339332e1961dd0f6"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"anime-game-core",
|
"anime-game-core",
|
||||||
"anyhow",
|
"anyhow",
|
||||||
|
|
|
@ -17,7 +17,7 @@ glib-build-tools = "0.17"
|
||||||
|
|
||||||
[dependencies.anime-launcher-sdk]
|
[dependencies.anime-launcher-sdk]
|
||||||
git = "https://github.com/an-anime-team/anime-launcher-sdk"
|
git = "https://github.com/an-anime-team/anime-launcher-sdk"
|
||||||
tag = "0.5.11"
|
tag = "0.5.12"
|
||||||
|
|
||||||
# path = "../anime-launcher-sdk" # ! for dev purposes only
|
# path = "../anime-launcher-sdk" # ! for dev purposes only
|
||||||
|
|
||||||
|
|
|
@ -37,7 +37,7 @@ lazy_static::lazy_static! {
|
||||||
/// This one is used to prepare some launcher UI components on start
|
/// This one is used to prepare some launcher UI components on start
|
||||||
pub static ref CONFIG: config::Config = config::get().expect("Failed to load config");
|
pub static ref CONFIG: config::Config = config::get().expect("Failed to load config");
|
||||||
|
|
||||||
pub static ref GAME: Game = Game::new(&CONFIG.game.path);
|
pub static ref GAME: Game = Game::new(CONFIG.game.path.for_edition(CONFIG.launcher.edition));
|
||||||
|
|
||||||
/// Path to launcher folder. Standard is `$HOME/.local/share/anime-game-launcher`
|
/// Path to launcher folder. Standard is `$HOME/.local/share/anime-game-launcher`
|
||||||
pub static ref LAUNCHER_FOLDER: PathBuf = launcher_dir().expect("Failed to get launcher folder");
|
pub static ref LAUNCHER_FOLDER: PathBuf = launcher_dir().expect("Failed to get launcher folder");
|
||||||
|
|
|
@ -18,7 +18,8 @@ pub struct DefaultPathsApp {
|
||||||
runners: PathBuf,
|
runners: PathBuf,
|
||||||
dxvks: PathBuf,
|
dxvks: PathBuf,
|
||||||
prefix: PathBuf,
|
prefix: PathBuf,
|
||||||
game: PathBuf,
|
game_global: PathBuf,
|
||||||
|
game_china: PathBuf,
|
||||||
fps_unlocker: PathBuf,
|
fps_unlocker: PathBuf,
|
||||||
components: PathBuf,
|
components: PathBuf,
|
||||||
patch: PathBuf,
|
patch: PathBuf,
|
||||||
|
@ -31,7 +32,8 @@ pub enum Folders {
|
||||||
Runners,
|
Runners,
|
||||||
DXVK,
|
DXVK,
|
||||||
Prefix,
|
Prefix,
|
||||||
Game,
|
GameGlobal,
|
||||||
|
GameChina,
|
||||||
FpsUnlocker,
|
FpsUnlocker,
|
||||||
Components,
|
Components,
|
||||||
Patch,
|
Patch,
|
||||||
|
@ -144,9 +146,20 @@ impl SimpleAsyncComponent for DefaultPathsApp {
|
||||||
set_activatable: true,
|
set_activatable: true,
|
||||||
|
|
||||||
#[watch]
|
#[watch]
|
||||||
set_subtitle: model.game.to_str().unwrap(),
|
set_subtitle: model.game_global.to_str().unwrap(),
|
||||||
|
|
||||||
connect_activated => DefaultPathsAppMsg::ChoosePath(Folders::Game)
|
connect_activated => DefaultPathsAppMsg::ChoosePath(Folders::GameGlobal)
|
||||||
|
},
|
||||||
|
|
||||||
|
adw::ActionRow {
|
||||||
|
set_title: &tr("game-installation-folder"), // FIXME
|
||||||
|
set_icon_name: Some("folder-symbolic"),
|
||||||
|
set_activatable: true,
|
||||||
|
|
||||||
|
#[watch]
|
||||||
|
set_subtitle: model.game_china.to_str().unwrap(),
|
||||||
|
|
||||||
|
connect_activated => DefaultPathsAppMsg::ChoosePath(Folders::GameChina)
|
||||||
},
|
},
|
||||||
|
|
||||||
adw::ActionRow {
|
adw::ActionRow {
|
||||||
|
@ -233,7 +246,8 @@ impl SimpleAsyncComponent for DefaultPathsApp {
|
||||||
runners: CONFIG.game.wine.builds.clone(),
|
runners: CONFIG.game.wine.builds.clone(),
|
||||||
dxvks: CONFIG.game.dxvk.builds.clone(),
|
dxvks: CONFIG.game.dxvk.builds.clone(),
|
||||||
prefix: CONFIG.game.wine.prefix.clone(),
|
prefix: CONFIG.game.wine.prefix.clone(),
|
||||||
game: CONFIG.game.path.clone(),
|
game_global: CONFIG.game.path.global.clone(),
|
||||||
|
game_china: CONFIG.game.path.china.clone(),
|
||||||
fps_unlocker: CONFIG.game.enhancements.fps_unlocker.path.clone(),
|
fps_unlocker: CONFIG.game.enhancements.fps_unlocker.path.clone(),
|
||||||
components: CONFIG.components.path.clone(),
|
components: CONFIG.components.path.clone(),
|
||||||
patch: CONFIG.patch.path.clone(),
|
patch: CONFIG.patch.path.clone(),
|
||||||
|
@ -264,23 +278,21 @@ impl SimpleAsyncComponent for DefaultPathsApp {
|
||||||
self.runners = result.join("runners");
|
self.runners = result.join("runners");
|
||||||
self.dxvks = result.join("dxvks");
|
self.dxvks = result.join("dxvks");
|
||||||
self.prefix = result.join("prefix");
|
self.prefix = result.join("prefix");
|
||||||
|
self.game_global = result.join(concat!("Ge", "nshi", "n Imp", "act"));
|
||||||
|
self.game_china = result.join(concat!("Yu", "anS", "hen"));
|
||||||
self.fps_unlocker = result.join("fps-unlocker");
|
self.fps_unlocker = result.join("fps-unlocker");
|
||||||
self.components = result.join("components");
|
self.components = result.join("components");
|
||||||
self.patch = result.join("patch");
|
self.patch = result.join("patch");
|
||||||
self.temp = result.clone();
|
self.temp = result.clone();
|
||||||
|
|
||||||
self.game = result.join(match CONFIG.launcher.edition.into() {
|
|
||||||
GameEdition::Global => concat!("Ge", "nshi", "n Imp", "act"),
|
|
||||||
GameEdition::China => concat!("Yu", "anS", "hen")
|
|
||||||
});
|
|
||||||
|
|
||||||
self.launcher = result;
|
self.launcher = result;
|
||||||
}
|
}
|
||||||
|
|
||||||
Folders::Runners => self.runners = result,
|
Folders::Runners => self.runners = result,
|
||||||
Folders::DXVK => self.dxvks = result,
|
Folders::DXVK => self.dxvks = result,
|
||||||
Folders::Prefix => self.prefix = result,
|
Folders::Prefix => self.prefix = result,
|
||||||
Folders::Game => self.game = result,
|
Folders::GameGlobal => self.game_global = result,
|
||||||
|
Folders::GameChina => self.game_china = result,
|
||||||
Folders::FpsUnlocker => self.fps_unlocker = result,
|
Folders::FpsUnlocker => self.fps_unlocker = result,
|
||||||
Folders::Components => self.components = result,
|
Folders::Components => self.components = result,
|
||||||
Folders::Patch => self.patch = result,
|
Folders::Patch => self.patch = result,
|
||||||
|
@ -313,7 +325,8 @@ impl DefaultPathsApp {
|
||||||
config.game.wine.builds = self.runners.clone();
|
config.game.wine.builds = self.runners.clone();
|
||||||
config.game.dxvk.builds = self.dxvks.clone();
|
config.game.dxvk.builds = self.dxvks.clone();
|
||||||
config.game.wine.prefix = self.prefix.clone();
|
config.game.wine.prefix = self.prefix.clone();
|
||||||
config.game.path = self.game.clone();
|
config.game.path.global = self.game_global.clone();
|
||||||
|
config.game.path.china = self.game_china.clone();
|
||||||
config.components.path = self.components.clone();
|
config.components.path = self.components.clone();
|
||||||
config.patch.path = self.patch.clone();
|
config.patch.path = self.patch.clone();
|
||||||
config.launcher.temp = Some(self.temp.clone());
|
config.launcher.temp = Some(self.temp.clone());
|
||||||
|
|
|
@ -21,7 +21,7 @@ pub fn apply_patch<T: PatchExt + Send + Sync + 'static>(sender: ComponentSender<
|
||||||
std::thread::spawn(move || {
|
std::thread::spawn(move || {
|
||||||
let mut apply_patch_if_needed = true;
|
let mut apply_patch_if_needed = true;
|
||||||
|
|
||||||
if let Err(err) = patch.apply(&config.game.path, config.patch.root) {
|
if let Err(err) = patch.apply(config.game.path.for_edition(config.launcher.edition), config.patch.root) {
|
||||||
tracing::error!("Failed to patch the game");
|
tracing::error!("Failed to patch the game");
|
||||||
|
|
||||||
sender.input(AppMsg::Toast {
|
sender.input(AppMsg::Toast {
|
||||||
|
|
|
@ -18,9 +18,10 @@ pub fn download_diff(sender: ComponentSender<App>, progress_bar_input: Sender<Pr
|
||||||
|
|
||||||
std::thread::spawn(move || {
|
std::thread::spawn(move || {
|
||||||
let config = config::get().unwrap();
|
let config = config::get().unwrap();
|
||||||
|
let game_path = config.game.path.for_edition(config.launcher.edition).to_path_buf();
|
||||||
|
|
||||||
#[allow(unused_must_use)]
|
#[allow(unused_must_use)]
|
||||||
let result = diff.install_to_by(config.game.path, config.launcher.temp, clone!(@strong sender => move |state| {
|
let result = diff.install_to_by(game_path, config.launcher.temp, clone!(@strong sender => move |state| {
|
||||||
match &state {
|
match &state {
|
||||||
InstallerUpdate::DownloadingError(err) => {
|
InstallerUpdate::DownloadingError(err) => {
|
||||||
tracing::error!("Downloading failed: {err}");
|
tracing::error!("Downloading failed: {err}");
|
||||||
|
|
|
@ -554,7 +554,12 @@ impl SimpleComponent for App {
|
||||||
})));
|
})));
|
||||||
|
|
||||||
group.add_action::<GameFolder>(&RelmAction::new_stateless(clone!(@strong sender => move |_| {
|
group.add_action::<GameFolder>(&RelmAction::new_stateless(clone!(@strong sender => move |_| {
|
||||||
if let Err(err) = open::that(&CONFIG.game.path) {
|
let path = match config::get() {
|
||||||
|
Ok(config) => config.game.path.for_edition(config.launcher.edition).to_path_buf(),
|
||||||
|
Err(_) => CONFIG.game.path.for_edition(CONFIG.launcher.edition).to_path_buf(),
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Err(err) = open::that(path) {
|
||||||
sender.input(AppMsg::Toast {
|
sender.input(AppMsg::Toast {
|
||||||
title: tr("game-folder-opening-error"),
|
title: tr("game-folder-opening-error"),
|
||||||
description: Some(err.to_string())
|
description: Some(err.to_string())
|
||||||
|
@ -590,8 +595,10 @@ impl SimpleComponent for App {
|
||||||
|
|
||||||
group.add_action::<WishUrl>(&RelmAction::new_stateless(clone!(@strong sender => move |_| {
|
group.add_action::<WishUrl>(&RelmAction::new_stateless(clone!(@strong sender => move |_| {
|
||||||
std::thread::spawn(clone!(@strong sender => move || {
|
std::thread::spawn(clone!(@strong sender => move || {
|
||||||
let web_cache = CONFIG.game.path
|
let config = config::get().unwrap_or_else(|_| CONFIG.clone());
|
||||||
.join(GameEdition::selected().data_folder())
|
|
||||||
|
let web_cache = config.game.path.for_edition(config.launcher.edition)
|
||||||
|
.join(GameEdition::from(config.launcher.edition).data_folder())
|
||||||
.join("webCaches/Cache/Cache_Data/data_2");
|
.join("webCaches/Cache/Cache_Data/data_2");
|
||||||
|
|
||||||
if !web_cache.exists() {
|
if !web_cache.exists() {
|
||||||
|
|
|
@ -3,6 +3,8 @@ use relm4::{
|
||||||
Sender
|
Sender
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use gtk::glib::clone;
|
||||||
|
|
||||||
use std::path::Path;
|
use std::path::Path;
|
||||||
|
|
||||||
use anime_launcher_sdk::config;
|
use anime_launcher_sdk::config;
|
||||||
|
@ -23,7 +25,8 @@ pub fn repair_game(sender: ComponentSender<App>, progress_bar_input: Sender<Prog
|
||||||
match repairer::try_get_integrity_files(None) {
|
match repairer::try_get_integrity_files(None) {
|
||||||
Ok(mut files) => {
|
Ok(mut files) => {
|
||||||
// Add voiceovers files
|
// Add voiceovers files
|
||||||
let game = Game::new(&config.game.path);
|
let game_path = config.game.path.for_edition(config.launcher.edition).to_path_buf();
|
||||||
|
let game = Game::new(&game_path);
|
||||||
|
|
||||||
if let Ok(voiceovers) = game.get_voice_packages() {
|
if let Ok(voiceovers) = game.get_voice_packages() {
|
||||||
for package in voiceovers {
|
for package in voiceovers {
|
||||||
|
@ -61,10 +64,9 @@ pub fn repair_game(sender: ComponentSender<App>, progress_bar_input: Sender<Prog
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let game_path = config.game.path.clone();
|
|
||||||
let thread_sender = verify_sender.clone();
|
let thread_sender = verify_sender.clone();
|
||||||
|
|
||||||
std::thread::spawn(move || {
|
std::thread::spawn(clone!(@strong game_path => move || {
|
||||||
for file in thread_files {
|
for file in thread_files {
|
||||||
let status = if config.launcher.repairer.fast {
|
let status = if config.launcher.repairer.fast {
|
||||||
file.fast_verify(&game_path)
|
file.fast_verify(&game_path)
|
||||||
|
@ -74,7 +76,7 @@ pub fn repair_game(sender: ComponentSender<App>, progress_bar_input: Sender<Prog
|
||||||
|
|
||||||
thread_sender.send((file, status)).unwrap();
|
thread_sender.send((file, status)).unwrap();
|
||||||
}
|
}
|
||||||
});
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
// We have [config.launcher.repairer.threads] copies of this sender + the original one
|
// We have [config.launcher.repairer.threads] copies of this sender + the original one
|
||||||
|
@ -105,10 +107,10 @@ pub fn repair_game(sender: ComponentSender<App>, progress_bar_input: Sender<Prog
|
||||||
let total = broken.len() as f64;
|
let total = broken.len() as f64;
|
||||||
|
|
||||||
let player_patch = UnityPlayerPatch::from_folder(&config.patch.path).unwrap()
|
let player_patch = UnityPlayerPatch::from_folder(&config.patch.path).unwrap()
|
||||||
.is_applied(&config.game.path).unwrap();
|
.is_applied(&game_path).unwrap();
|
||||||
|
|
||||||
let xlua_patch = UnityPlayerPatch::from_folder(&config.patch.path).unwrap()
|
let xlua_patch = XluaPatch::from_folder(&config.patch.path).unwrap()
|
||||||
.is_applied(&config.game.path).unwrap();
|
.is_applied(&game_path).unwrap();
|
||||||
|
|
||||||
tracing::debug!("Patches status: player({player_patch}), xlua({xlua_patch})");
|
tracing::debug!("Patches status: player({player_patch}), xlua({xlua_patch})");
|
||||||
|
|
||||||
|
@ -145,7 +147,7 @@ pub fn repair_game(sender: ComponentSender<App>, progress_bar_input: Sender<Prog
|
||||||
if !should_ignore(&file.path, player_patch, xlua_patch) {
|
if !should_ignore(&file.path, player_patch, xlua_patch) {
|
||||||
tracing::debug!("Repairing file: {}", file.path.to_string_lossy());
|
tracing::debug!("Repairing file: {}", file.path.to_string_lossy());
|
||||||
|
|
||||||
if let Err(err) = file.repair(&config.game.path) {
|
if let Err(err) = file.repair(&game_path) {
|
||||||
sender.input(AppMsg::Toast {
|
sender.input(AppMsg::Toast {
|
||||||
title: tr("game-file-repairing-error"),
|
title: tr("game-file-repairing-error"),
|
||||||
description: Some(err.to_string())
|
description: Some(err.to_string())
|
||||||
|
|
|
@ -16,6 +16,7 @@ use anime_launcher_sdk::config::launcher::LauncherStyle;
|
||||||
use anime_launcher_sdk::components::*;
|
use anime_launcher_sdk::components::*;
|
||||||
use anime_launcher_sdk::components::wine::WincompatlibWine;
|
use anime_launcher_sdk::components::wine::WincompatlibWine;
|
||||||
use anime_launcher_sdk::env_emulation::Environment;
|
use anime_launcher_sdk::env_emulation::Environment;
|
||||||
|
use anime_launcher_sdk::config::launcher::GameEdition;
|
||||||
|
|
||||||
use super::main::PreferencesAppMsg;
|
use super::main::PreferencesAppMsg;
|
||||||
use crate::ui::migrate_installation::MigrateInstallationApp;
|
use crate::ui::migrate_installation::MigrateInstallationApp;
|
||||||
|
@ -301,15 +302,41 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
#[local_ref]
|
adw::ComboRow {
|
||||||
voice_packages -> adw::ExpanderRow {
|
set_title: "Game edition",
|
||||||
set_title: &tr("game-voiceovers"),
|
|
||||||
set_subtitle: "List of downloaded game voiceovers. You can select them in the game settings"
|
set_model: Some(>k::StringList::new(&[
|
||||||
|
"Global",
|
||||||
|
"China"
|
||||||
|
])),
|
||||||
|
|
||||||
|
set_selected: match CONFIG.launcher.edition {
|
||||||
|
GameEdition::Global => 0,
|
||||||
|
GameEdition::China => 1
|
||||||
|
},
|
||||||
|
|
||||||
|
connect_selected_notify[sender] => move |row| {
|
||||||
|
if is_ready() {
|
||||||
|
#[allow(unused_must_use)]
|
||||||
|
if let Ok(mut config) = config::get() {
|
||||||
|
config.launcher.edition = match row.selected() {
|
||||||
|
0 => GameEdition::Global,
|
||||||
|
1 => GameEdition::China,
|
||||||
|
|
||||||
|
_ => unreachable!()
|
||||||
|
};
|
||||||
|
|
||||||
|
config::update(config);
|
||||||
|
|
||||||
|
sender.output(PreferencesAppMsg::UpdateLauncherState);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
adw::ComboRow {
|
adw::ComboRow {
|
||||||
set_title: "Environment emulation",
|
set_title: "Game environment",
|
||||||
set_subtitle: "Experimental feature. Emulate game environment to get specific features like additional payment methods",
|
set_subtitle: "Get specific features like additional payment methods",
|
||||||
|
|
||||||
set_model: Some(>k::StringList::new(&[
|
set_model: Some(>k::StringList::new(&[
|
||||||
"PC",
|
"PC",
|
||||||
|
@ -339,6 +366,12 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
|
#[local_ref]
|
||||||
|
voice_packages -> adw::ExpanderRow {
|
||||||
|
set_title: &tr("game-voiceovers"),
|
||||||
|
set_subtitle: "List of downloaded game voiceovers. You can select them in the game settings"
|
||||||
|
},
|
||||||
|
|
||||||
gtk::Box {
|
gtk::Box {
|
||||||
set_orientation: gtk::Orientation::Horizontal,
|
set_orientation: gtk::Orientation::Horizontal,
|
||||||
set_spacing: 8,
|
set_spacing: 8,
|
||||||
|
@ -442,7 +475,12 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
PatchStatus::Preparation { .. } |
|
PatchStatus::Preparation { .. } |
|
||||||
PatchStatus::Testing { .. } => &["warning"],
|
PatchStatus::Testing { .. } => &["warning"],
|
||||||
PatchStatus::Available { .. } => unsafe {
|
PatchStatus::Available { .. } => unsafe {
|
||||||
if let Ok(true) = model.unity_player_patch.as_ref().unwrap_unchecked().is_applied(&CONFIG.game.path) {
|
let path = match config::get() {
|
||||||
|
Ok(config) => config.game.path.for_edition(config.launcher.edition).to_path_buf(),
|
||||||
|
Err(_) => CONFIG.game.path.for_edition(CONFIG.launcher.edition).to_path_buf(),
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Ok(true) = model.unity_player_patch.as_ref().unwrap_unchecked().is_applied(path) {
|
||||||
&["success"]
|
&["success"]
|
||||||
} else {
|
} else {
|
||||||
&["warning"]
|
&["warning"]
|
||||||
|
@ -464,7 +502,12 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
PatchStatus::Preparation { .. } => tr("patch-preparation-tooltip"),
|
PatchStatus::Preparation { .. } => tr("patch-preparation-tooltip"),
|
||||||
PatchStatus::Testing { .. } => tr("patch-testing-tooltip"),
|
PatchStatus::Testing { .. } => tr("patch-testing-tooltip"),
|
||||||
PatchStatus::Available { .. } => unsafe {
|
PatchStatus::Available { .. } => unsafe {
|
||||||
if let Ok(true) = model.unity_player_patch.as_ref().unwrap_unchecked().is_applied(&CONFIG.game.path) {
|
let path = match config::get() {
|
||||||
|
Ok(config) => config.game.path.for_edition(config.launcher.edition).to_path_buf(),
|
||||||
|
Err(_) => CONFIG.game.path.for_edition(CONFIG.launcher.edition).to_path_buf(),
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Ok(true) = model.unity_player_patch.as_ref().unwrap_unchecked().is_applied(path) {
|
||||||
String::new()
|
String::new()
|
||||||
} else {
|
} else {
|
||||||
tr("patch-not-applied-tooltip")
|
tr("patch-not-applied-tooltip")
|
||||||
|
@ -503,7 +546,12 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
PatchStatus::Preparation { .. } |
|
PatchStatus::Preparation { .. } |
|
||||||
PatchStatus::Testing { .. } => &["warning"],
|
PatchStatus::Testing { .. } => &["warning"],
|
||||||
PatchStatus::Available { .. } => unsafe {
|
PatchStatus::Available { .. } => unsafe {
|
||||||
if let Ok(true) = model.xlua_patch.as_ref().unwrap_unchecked().is_applied(&CONFIG.game.path) {
|
let path = match config::get() {
|
||||||
|
Ok(config) => config.game.path.for_edition(config.launcher.edition).to_path_buf(),
|
||||||
|
Err(_) => CONFIG.game.path.for_edition(CONFIG.launcher.edition).to_path_buf(),
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Ok(true) = model.xlua_patch.as_ref().unwrap_unchecked().is_applied(path) {
|
||||||
&["success"]
|
&["success"]
|
||||||
} else {
|
} else {
|
||||||
&["warning"]
|
&["warning"]
|
||||||
|
@ -525,7 +573,12 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
PatchStatus::Preparation { .. } => tr("patch-preparation-tooltip"),
|
PatchStatus::Preparation { .. } => tr("patch-preparation-tooltip"),
|
||||||
PatchStatus::Testing { .. } => tr("patch-testing-tooltip"),
|
PatchStatus::Testing { .. } => tr("patch-testing-tooltip"),
|
||||||
PatchStatus::Available { .. } => unsafe {
|
PatchStatus::Available { .. } => unsafe {
|
||||||
if let Ok(true) = model.xlua_patch.as_ref().unwrap_unchecked().is_applied(&CONFIG.game.path) {
|
let path = match config::get() {
|
||||||
|
Ok(config) => config.game.path.for_edition(config.launcher.edition).to_path_buf(),
|
||||||
|
Err(_) => CONFIG.game.path.for_edition(CONFIG.launcher.edition).to_path_buf(),
|
||||||
|
};
|
||||||
|
|
||||||
|
if let Ok(true) = model.xlua_patch.as_ref().unwrap_unchecked().is_applied(path) {
|
||||||
String::new()
|
String::new()
|
||||||
} else {
|
} else {
|
||||||
tr("patch-not-applied-tooltip")
|
tr("patch-not-applied-tooltip")
|
||||||
|
@ -867,10 +920,11 @@ impl SimpleAsyncComponent for GeneralApp {
|
||||||
config::update(config.clone());
|
config::update(config.clone());
|
||||||
|
|
||||||
let package = VoicePackage::with_locale(package.locale).unwrap();
|
let package = VoicePackage::with_locale(package.locale).unwrap();
|
||||||
|
let game_path = config.game.path.for_edition(config.launcher.edition).to_path_buf();
|
||||||
|
|
||||||
if package.is_installed_in(&config.game.path) {
|
if package.is_installed_in(&game_path) {
|
||||||
std::thread::spawn(move || {
|
std::thread::spawn(move || {
|
||||||
if let Err(err) = package.delete_in(&config.game.path) {
|
if let Err(err) = package.delete_in(game_path) {
|
||||||
tracing::error!("Failed to delete voice package: {:?}", package.locale());
|
tracing::error!("Failed to delete voice package: {:?}", package.locale());
|
||||||
|
|
||||||
sender.input(GeneralAppMsg::Toast {
|
sender.input(GeneralAppMsg::Toast {
|
||||||
|
|
Loading…
Reference in a new issue