OneLauncher-Cracked/packages/core/src/store/settings.rs
Pauline 28b1f9f0e3
Feature: Package API (#75) (i'm just going to merge this because the other branches are inactive)
* feat: Start work on package api

* feat: Browser Context Controller

* feat: Add packages to cluster metadata
feat: Change structure of Package

* 🐛 fix: format

* 🔨 feat: Add more functions wrapping around Modrinth

* 🔨 feat: Start working on browser frontend

* feat: BrowserPackage work + markdown support

* 🐛 fix: fmt

Signed-off-by: Pauline <git@ethanlibs.co>

* 🚧 wip: h

Signed-off-by: Pauline <git@ethanlibs.co>

* feat: Download button for packages for suitable clusters + tweaks

* 🚧 wip: markdown and stuff

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: some patches

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: remove react bloat

Signed-off-by: Pauline <git@ethanlibs.co>

* 🔨 chore(pkg/infer): try to reduce reused code

Signed-off-by: Pauline <git@ethanlibs.co>

* 🔨 chore: bump deps

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: markdown innerhtml

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: h

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: tweak

Signed-off-by: Pauline <git@ethanlibs.co>

* 🚧 wip: idk

Signed-off-by: Pauline <git@ethanlibs.co>

* fix: Gamemode compile error
chore: Add missing and remove unused libraries
feat: usePreventLeave hook
feat: ClusterOverview edit mode continues with navigation (assuming there was a navigation attempt) after pressing Yes or No for save

* feat: Add reload clusters button on home page

* feat: More information provided to BrowserPackage

* fix: Minor fixes (Navbar isActive, Markdown click prevention, Markdown list styling)

* 🐛 fix: h

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: highlighting

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: forge modern

Signed-off-by: Pauline <git@ethanlibs.co>

* 🔨 chore: bump deps

Signed-off-by: Pauline <git@ethanlibs.co>

* fix: Markdown-it issue + Added promptOpener hook for Markdown links

* feat: Made BrowserPackage sidebar sticky

* refactor: Package system (not yet in a working state)

* 🚧 wip: bump deps temp

Signed-off-by: Pauline <git@ethanlibs.co>

* feat: Added a package manager

* ✨ feature: start prisma work, but it doesnt break anything so we can keep it until its done. also fix some stuff

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: pushing

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: linting

Signed-off-by: Pauline <git@ethanlibs.co>

* ✨ feature: start ingress integration

Signed-off-by: Pauline <git@ethanlibs.co>

* feat: Package Manager should work now 👍

* fix: Package manager tracing spam

* feat: Added tauri commands for cluster packages
format: Auto formatted frontend + backend

* 🐛 fix: tmp

Signed-off-by: Pauline <git@ethanlibs.co>

* 🔨 chore: format

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: specta extension

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: github actions

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: alias

Signed-off-by: Pauline <git@ethanlibs.co>

* chore: Some tweaks and fixes

* chore: Rebase + gitignore bindings.ts

* chore: Remove bindings.ts

* 🐛 fix: migrate

Signed-off-by: Pauline <git@ethanlibs.co>

* 🚧 wip: not sure

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: finalize prisma init schema

Signed-off-by: Pauline <git@ethanlibs.co>

* 🔨 chore: format

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: bump deps

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: system deps

Signed-off-by: Pauline <git@ethanlibs.co>

* fix: solid-router navigation issue

* feat: Added new BrowserMain page

* feat: Tweaks + new package list view

* 🐛 fix: bump + format (todo: tauri2, etc)

Signed-off-by: Pauline <git@ethanlibs.co>

* 🐛 fix: devx (fixes #126)

Signed-off-by: Pauline <git@ethanlibs.co>

* 🔨 chore: migrate to consola

Signed-off-by: Pauline <git@ethanlibs.co>

---------

Signed-off-by: Pauline <git@ethanlibs.co>
Co-authored-by: LynithDev <61880709+LynithDev@users.noreply.github.com>
2024-08-31 16:23:24 -04:00

216 lines
6.4 KiB
Rust

//! Handles user-inputted settings and global values
use super::{Directories, JavaVersions};
use crate::constants::CURRENT_SETTINGS_FORMAT_VERSION;
use crate::utils::io;
use serde::{Deserialize, Serialize};
use std::path::{Path, PathBuf};
/// A global settings state for the launcher.
#[cfg_attr(feature = "specta", derive(specta::Type))]
#[derive(Debug, Serialize, Deserialize, Clone)]
pub struct Settings {
/// A OneLauncher [`Theme`] managed by the core GUI.
pub theme: Theme,
/// A global browser list view for the OneLauncher GUI.
#[serde(default)]
pub browser_list_view: BrowserListView,
/// Does not ask for confirmation when closing the OneLauncher GUI
#[serde(default)]
pub hide_close_prompt: bool,
/// Disables animations in the OneLauncher GUI
#[serde(default)]
pub disable_animations: bool,
/// A global fullscreen Minecraft state.
#[serde(default)]
pub force_fullscreen: bool,
/// Whether to allow launching the same cluster under the same account.
#[serde(default)]
pub allow_parallel_running_clusters: bool,
/// Whether to launch Feral Gamemode on Linux systems.
#[serde(default)]
pub enable_gamemode: bool,
/// A global default [`Resolution`] for Minecraft.
pub resolution: Resolution,
/// A global [`JavaVersions`] list and default version.
pub java_versions: JavaVersions,
/// A global [`Memory`] settings store for Java memory settings.
pub memory: Memory,
/// Global and default initialization hooks .
pub init_hooks: InitHooks,
/// Global and default custom Java arguments.
pub custom_java_args: Vec<String>,
/// Global and default custom environment variables.
pub custom_env_args: Vec<(String, String)>,
/// Global and default maximum [`Semaphore`] I/O operations.
pub max_async_io_operations: usize,
/// Global and default maximum [`Semaphore`] HTTP operations.
pub max_async_fetches: usize,
/// The [`CURRENT_FORMAT_VERSION`] of this settings file.
pub version: u32,
/// Whether or not to disable Discord IPC.
#[serde(default)]
pub disable_discord: bool,
/// Whether or not to enable a debug mode in the launcher.
#[serde(default)]
pub debug_mode: bool,
/// Whether or not to disable Plausible and Sentry analytics.
#[serde(default)]
pub disable_analytics: bool,
/// The core global config directory stored as a [`PathBuf`].
#[serde(default = "Directories::init_settings_dir")]
pub config_dir: Option<PathBuf>,
/// Whether or not to minimize the launcher upon a game launch.
#[serde(default)]
pub hide_on_launch: bool,
/// Enable/disable advanced rendering and window decorations.
#[serde(default)]
pub rendering: bool,
}
impl Settings {
/// Initializes the global settings state.
#[tracing::instrument]
pub async fn initialize(file: &Path) -> crate::Result<Self> {
let mut recovered_corruption = false;
let settings = if file.exists() {
let read_settings = io::read(&file)
.await
.map_err(|err| anyhow::anyhow!("error reading settings file: {0}", err).into())
.and_then(|it| serde_json::from_slice::<Settings>(&it).map_err(crate::Error::from));
if let Err(ref err) = read_settings {
tracing::error!("failed to load settings file: {err}.");
let backup = file.with_extension("json.bak");
tracing::error!(
"corrupted settings will be backed up as {}, and a new one will be created",
backup.display()
);
let _ = io::rename(file, backup).await;
recovered_corruption = true;
}
read_settings.ok()
} else {
None
};
if let Some(settings) = settings {
Ok(settings)
} else {
let settings = Self {
theme: Theme::Dark,
browser_list_view: BrowserListView::Grid,
hide_close_prompt: true,
disable_animations: false,
force_fullscreen: false,
allow_parallel_running_clusters: false,
#[cfg(target_os = "linux")]
enable_gamemode: true,
#[cfg(not(target_os = "linux"))]
enable_gamemode: false,
resolution: Resolution::default(),
java_versions: JavaVersions::new(),
memory: Memory::default(),
init_hooks: InitHooks::default(),
custom_env_args: Vec::new(),
custom_java_args: Vec::new(),
max_async_fetches: 10,
max_async_io_operations: 10,
version: CURRENT_SETTINGS_FORMAT_VERSION,
disable_analytics: false,
disable_discord: false,
debug_mode: false,
config_dir: Directories::init_settings_dir(),
hide_on_launch: false,
rendering: true,
};
if recovered_corruption {
settings.sync(file).await?;
}
Ok(settings)
}
}
/// Synchronizes the current settings from a file.
#[tracing::instrument(skip(self))]
pub async fn sync(&self, to: &Path) -> crate::Result<()> {
io::write(to, serde_json::to_vec(self)?).await?;
Ok(())
}
}
/// OneLauncher browser list type.
#[cfg_attr(feature = "specta", derive(specta::Type))]
#[derive(Default, Debug, Clone, Copy, Serialize, Deserialize)]
#[serde(rename_all = "snake_case")]
pub enum BrowserListView {
#[default]
Grid,
List,
Preview,
}
/// A OneLauncher theme managed by the GUI.
#[cfg_attr(feature = "specta", derive(specta::Type))]
#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
#[serde(rename_all = "snake_case")]
pub enum Theme {
/// A default Dark theme.
Dark,
/// A default Light theme.
Light,
/// OLED Dark Theme.
Contrast,
/// Cute and colorful theme.
Cat,
}
/// Global memory settings across all clusters.
#[derive(Serialize, Deserialize, Debug, Clone, Copy)]
#[cfg_attr(feature = "specta", derive(specta::Type))]
pub struct Memory {
/// Maximum amount of Java memory available globally.
pub maximum: u32,
/// Minimum amount of Java memory available globally.
pub minimum: u32,
}
impl Default for Memory {
fn default() -> Self {
Self {
maximum: 2048,
minimum: 256,
}
}
}
/// Global Minecraft resolution.
#[derive(Serialize, Deserialize, Debug, Clone, Copy)]
#[cfg_attr(feature = "specta", derive(specta::Type))]
pub struct Resolution(pub u16, pub u16);
impl Default for Resolution {
fn default() -> Self {
Self(854, 480)
}
}
/// Global initialization hooks for all Minecraft clusters.
#[derive(Serialize, Deserialize, Debug, Clone, Default)]
#[serde(default)]
#[cfg_attr(feature = "specta", derive(specta::Type))]
pub struct InitHooks {
/// Pre-launch hook.
#[serde(skip_serializing_if = "Option::is_none")]
pub pre: Option<String>,
/// Wrapper hook for the runtime of the game instance.
#[serde(skip_serializing_if = "Option::is_none")]
pub wrapper: Option<String>,
/// Post-launch hook.
#[serde(skip_serializing_if = "Option::is_none")]
pub post: Option<String>,
}