diff options
| author | 2025-01-20 04:33:28 -0600 | |
|---|---|---|
| committer | 2025-01-20 04:33:28 -0600 | |
| commit | b317a8a652d2e3a48c8b9f4940c7933d3802cfc3 (patch) | |
| tree | ec06208dd483d17eb7c764587c7629e4e4f0d100 /src/launcher.rs | |
| parent | get rid of wacky closure business (diff) | |
it runs the game
Diffstat (limited to 'src/launcher.rs')
| -rw-r--r-- | src/launcher.rs | 58 |
1 files changed, 42 insertions, 16 deletions
diff --git a/src/launcher.rs b/src/launcher.rs index a21a422..f148653 100644 --- a/src/launcher.rs +++ b/src/launcher.rs @@ -12,7 +12,7 @@ use std::borrow::Cow; use std::cmp::min; use std::env::consts::{ARCH, OS}; use std::error::Error; -use std::ffi::OsStr; +use std::ffi::{OsStr, OsString}; use std::fmt::{Display, Formatter}; use std::io::ErrorKind; use std::io::ErrorKind::AlreadyExists; @@ -39,6 +39,7 @@ use assets::{AssetError, AssetRepository}; use crate::util::{self, FileVerifyError, IntegrityError}; pub use settings::*; +pub use runner::run_the_game; use crate::assets::AssetIndex; use crate::launcher::runner::ArgumentType; use crate::launcher::strsub::SubFunc; @@ -115,6 +116,7 @@ pub enum LaunchError { LoadVersion(Box<dyn Error>), ResolveVersion(VersionResolveError), IncompatibleVersion(IncompatibleError), + MissingMainClass, // library errors LibraryDirError(PathBuf, io::Error), @@ -146,6 +148,7 @@ impl Display for LaunchError { LaunchError::LoadVersion(e) => write!(f, "error loading remote version: {e}"), LaunchError::ResolveVersion(e) => write!(f, "error resolving remote version: {e}"), LaunchError::IncompatibleVersion(e) => e.fmt(f), + LaunchError::MissingMainClass => f.write_str("main class not specified"), LaunchError::LibraryDirError(path, e) => write!(f, "failed to create library directory {}: {}", path.display(), e), LaunchError::LibraryVerifyError(e) => write!(f, "failed to verify library: {}", e), LaunchError::LibraryDownloadError => f.write_str("library download failed (see above logs for details)"), // TODO: booo this sucks @@ -198,10 +201,24 @@ struct LaunchInfo<'l, F: FeatureMatcher> { asset_index: Option<AssetIndex> } -struct FMTrivial; -impl FeatureMatcher for FMTrivial { - fn matches(&self, _feature: &str) -> bool { - false +#[derive(Debug)] +pub struct Launch { + jvm_args: Vec<OsString>, + game_args: Vec<OsString>, + main_class: String, + instance_path: PathBuf +} + +struct ProfileFeatureMatcher<'prof> { + profile: &'prof Profile +} + +impl FeatureMatcher for ProfileFeatureMatcher<'_> { + fn matches(&self, feature: &str) -> bool { + match feature { + "has_custom_resolution" => self.profile.get_resolution().is_some(), + _ => false + } } } @@ -246,10 +263,6 @@ impl Launcher { lib.natives.as_ref().map_or(None, |n| n.get(&self.system_info.os)).map(|s| s.as_str()) } - fn get_feature_matcher(&self) -> &impl FeatureMatcher { - &FMTrivial - } - async fn ensure_file(&self, path: &Path, dlinfo: &DownloadInfo) -> Result<(), LaunchError> { // verify the file match util::verify_file(path, dlinfo.size, dlinfo.sha1).await { @@ -374,7 +387,7 @@ impl Launcher { Ok(strsub::replace_string(config.client.argument.as_str(), &PathSub(path.as_ref())).to_string()) } - pub async fn prepare_launch(&self, version_id: &ProfileVersion, instance: &Instance) -> Result<(), LaunchError> { + pub async fn prepare_launch(&self, profile: &Profile, instance: &Instance) -> Result<Launch, LaunchError> { /* tasks 2 l;aunch the gayme!!!! :3 * - java runtime * - normal process (good research, past figboot :3) @@ -399,6 +412,9 @@ impl Launcher { * - launch the game * - build argument list and whatnot also */ + let feature_matcher = ProfileFeatureMatcher { profile }; + let version_id = profile.get_version(); + let Some(version_id) = self.versions.get_profile_version_id(version_id) else { // idk how common this use case actually is warn!("Can't use latest release/snapshot profiles while offline!"); @@ -429,7 +445,7 @@ impl Launcher { }; let ver = self.versions.resolve_version(ver.as_ref()).await.map_err(|e| LaunchError::ResolveVersion(e))?; - ver.rules_apply(&self.system_info, self.get_feature_matcher()).map_err(|e| LaunchError::IncompatibleVersion(e))?; + ver.rules_apply(&self.system_info, &feature_matcher).map_err(|e| LaunchError::IncompatibleVersion(e))?; info!("Resolved launch version {}!", ver.id); @@ -438,7 +454,7 @@ impl Launcher { let mut downloads = Vec::new(); for lib in ver.libraries.values() { - if lib.rules_apply(&self.system_info, self.get_feature_matcher()).is_err() { + if lib.rules_apply(&self.system_info, &feature_matcher).is_err() { continue; } @@ -548,12 +564,12 @@ impl Launcher { info!("Deriving launch arguments"); let info = LaunchInfo { launcher: self, - feature_matcher: self.get_feature_matcher(), + feature_matcher: &feature_matcher, asset_index_name: asset_idx_name.map(|s| s.to_owned()), classpath, virtual_assets_path: game_assets, - instance_home: inst_home, + instance_home: inst_home.clone(), natives_path: natives_dir, client_jar: client_jar_path, version_id: ver.id.to_string(), @@ -561,10 +577,20 @@ impl Launcher { asset_index: asset_idx }; - let jvm_args = runner::build_arguments(&info, ver.as_ref(), ArgumentType::JVM); + let Some(ref main_class) = ver.main_class else { + return Err(LaunchError::MissingMainClass); + }; + + // yuck + let jvm_args = profile.iter_arguments().map(OsString::from).chain(runner::build_arguments(&info, ver.as_ref(), ArgumentType::JVM).drain(..)).collect(); let game_args = runner::build_arguments(&info, ver.as_ref(), ArgumentType::Game); - todo!() + Ok(Launch { + jvm_args, + game_args, + main_class: main_class.to_string(), + instance_path: inst_home + }) } } |
