Skip to content

Commit

Permalink
Merge pull request #77 from Umatriz/dev
Browse files Browse the repository at this point in the history
Use `javaw` on Windows and refactor settings
  • Loading branch information
Umatriz authored Aug 21, 2024
2 parents 993f144 + 5c9e859 commit 7285285
Show file tree
Hide file tree
Showing 7 changed files with 72 additions and 52 deletions.
8 changes: 5 additions & 3 deletions crates/client/src/collections.rs
Original file line number Diff line number Diff line change
Expand Up @@ -53,9 +53,9 @@ impl<'c> TasksCollection<'c> for AssetsCollection {
}
}

pub struct JavaCollection;
pub struct JavaDownloadingCollection;

impl<'c> TasksCollection<'c> for JavaCollection {
impl<'c> TasksCollection<'c> for JavaDownloadingCollection {
type Context = ();

type Target = ();
Expand All @@ -67,7 +67,9 @@ impl<'c> TasksCollection<'c> for JavaCollection {
}

fn handle(_context: Self::Context) -> Handler<'c, Self::Target> {
Handler::new(|()| ())
Handler::new(|()| {
toasts::add(|toasts| toasts.success("Successfully downloaded Java"));
})
}
}

Expand Down
38 changes: 34 additions & 4 deletions crates/client/src/main.rs
Original file line number Diff line number Diff line change
@@ -1,15 +1,16 @@
// Remove console window in release builds
#![cfg_attr(not(debug_assertions), windows_subsystem = "windows")]

use collections::{AssetsCollection, GameDownloadingCollection, GameRunnerCollection, JavaCollection};
use collections::{AssetsCollection, GameDownloadingCollection, GameRunnerCollection, JavaDownloadingCollection};
use context::MyContext;
use eframe::{
egui::{self, Align, Button, Frame, Id, Layout, RichText, ScrollArea, ViewportBuilder},
epaint::Vec2,
};
use egui_dock::{DockArea, DockState, NodeIndex, Style};
use open_directory::open_directory_native;
use std::path::Path;
use states::download_java_and_update_config;
use std::path::{Path, PathBuf};
use subscriber::EguiLayer;
use ui_ext::UiExt;
use views::{add_tab_menu::AddTab, AddProfileMenu, CreateInstanceMenu, View};
Expand Down Expand Up @@ -135,7 +136,7 @@ impl eframe::App for MyTabs {
.add_collection::<collections::GameDeletionCollection>(&self.context.states.instances.instances)
.add_collection::<collections::InstanceDeletionCollection>(&mut self.context.states.instances.instances)
.add_collection::<collections::GameDownloadingCollection>(&self.context.states.instances.instances)
.add_collection::<collections::JavaCollection>(())
.add_collection::<collections::JavaDownloadingCollection>(())
.add_collection::<collections::ProjectCollection>(&mut self.context.states.mod_manager.current_project)
.add_collection::<collections::ProjectVersionsCollection>(&mut self.context.states.mod_manager.current_versions)
.add_collection::<collections::DependenciesCollection>((
Expand Down Expand Up @@ -183,6 +184,35 @@ impl eframe::App for MyTabs {
}
});

ui.menu_button("Download", |ui| {
if ui
.add_enabled(
self.context.manager.get_collection::<JavaDownloadingCollection>().tasks().is_empty(),
egui::Button::new("Download Java"),
)
.clicked()
{
download_java_and_update_config(
ui,
&mut self.context.manager,
&mut self.context.states.java,
&mut self.context.states.settings,
);
}
});

ui.menu_button("Utils", |ui| {
let launcher_path = PathBuf::from(DOT_NOMI_LOGS_DIR);

if launcher_path.exists() {
if ui.button("Delete launcher's logs").clicked() {
let _ = std::fs::remove_dir_all(launcher_path);
}
} else {
ui.warn_label("The launcher log's directory is already deleted");
}
});

AddTab {
dock_state: &self.dock_state,
tabs_state: &mut self.context.states.tabs,
Expand Down Expand Up @@ -308,7 +338,7 @@ impl eframe::App for MyTabs {

self.context.is_allowed_to_take_action = [
manager.get_collection::<AssetsCollection>(),
manager.get_collection::<JavaCollection>(),
manager.get_collection::<JavaDownloadingCollection>(),
manager.get_collection::<GameDownloadingCollection>(),
manager.get_collection::<GameRunnerCollection>(),
]
Expand Down
13 changes: 10 additions & 3 deletions crates/client/src/states.rs
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
use std::path::PathBuf;

use eframe::egui::Context;
use eframe::egui::{Context, Ui};
use egui_task_manager::{Caller, Task, TaskManager};
use nomi_core::{
downloads::{java::JavaDownloader, progress::MappedSender, traits::Downloader},
fs::read_toml_config_sync,
repository::java_runner::JavaRunner,
DOT_NOMI_JAVA_DIR, DOT_NOMI_JAVA_EXECUTABLE, DOT_NOMI_SETTINGS_CONFIG,
};
use tracing::info;

use crate::{
collections::JavaCollection,
collections::JavaDownloadingCollection,
errors_pool::ErrorPoolExt,
views::{
add_tab_menu::TabsState,
Expand Down Expand Up @@ -92,6 +93,12 @@ impl JavaState {
});

let task = Task::new("Java downloading", caller);
manager.push_task::<JavaCollection>(task);
manager.push_task::<JavaDownloadingCollection>(task);
}
}

pub fn download_java_and_update_config(ui: &mut Ui, manager: &mut TaskManager, java_state: &mut JavaState, settings_state: &mut SettingsState) {
java_state.download_java(manager, ui.ctx().clone());
settings_state.java = JavaRunner::path(PathBuf::from(DOT_NOMI_JAVA_EXECUTABLE));
settings_state.update_config();
}
52 changes: 13 additions & 39 deletions crates/client/src/views/settings.rs
Original file line number Diff line number Diff line change
@@ -1,17 +1,18 @@
use std::path::PathBuf;
use std::{path::PathBuf, sync::LazyLock};

use eframe::egui::{self};
use egui_file_dialog::FileDialog;
use egui_form::{garde::field_path, Form, FormField};
use egui_task_manager::TaskManager;
use garde::{Error, Validate};
use nomi_core::{
fs::write_toml_config_sync, regex::Regex, repository::java_runner::JavaRunner, Uuid, DOT_NOMI_JAVA_EXECUTABLE, DOT_NOMI_LOGS_DIR,
DOT_NOMI_SETTINGS_CONFIG,
};
use nomi_core::{fs::write_toml_config_sync, regex::Regex, repository::java_runner::JavaRunner, Uuid, DOT_NOMI_SETTINGS_CONFIG};
use serde::{Deserialize, Serialize};

use crate::{collections::JavaCollection, errors_pool::ErrorPoolExt, states::JavaState, ui_ext::UiExt};
use crate::{
collections::JavaDownloadingCollection,
errors_pool::ErrorPoolExt,
states::{download_java_and_update_config, JavaState},
};

use super::View;

Expand Down Expand Up @@ -66,10 +67,9 @@ impl Default for ClientSettingsState {
}

fn check_username(value: &str, _context: &()) -> garde::Result {
let regex =
Regex::new(r"^[a-zA-Z0-9_]{3,16}$").map_err(|_| Error::new("Cannot create regex (this is a bug, please create an issue on the github)"))?;
static REGEX: LazyLock<Regex> = LazyLock::new(|| Regex::new(r"^[a-zA-Z0-9_]{3,16}$").unwrap());

regex.captures(value).map_or_else(
REGEX.captures(value).map_or_else(
|| {
Err(Error::new(
"
Expand All @@ -85,36 +85,12 @@ A-Z characters, a-z characters, 0-9 numbers, `_` (underscore) symbol
}

fn check_uuid(value: &str, _context: &()) -> garde::Result {
let regex = Regex::new(r"^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$")
.map_err(|_| Error::new("Cannot create regex (this is a bug, please create an issue on the github)"))?;

regex.captures(value).map_or_else(|| Err(Error::new("Invalid UUID")), |_| Ok(()))
static REGEX: LazyLock<Regex> = LazyLock::new(|| Regex::new(r"^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$").unwrap());
REGEX.captures(value).map_or_else(|| Err(Error::new("Invalid UUID")), |_| Ok(()))
}

impl View for SettingsPage<'_> {
fn ui(self, ui: &mut eframe::egui::Ui) {
ui.heading("Utils");

let launcher_path = PathBuf::from(DOT_NOMI_LOGS_DIR);

if launcher_path.exists() {
if ui.button("Delete launcher's logs").clicked() {
let _ = std::fs::remove_dir_all(launcher_path);
}
} else {
ui.warn_label("The launcher log's directory is already deleted");
}

let game_path = PathBuf::from("./logs");

if game_path.exists() {
if ui.button("Delete game's logs").clicked() {
let _ = std::fs::remove_dir_all(game_path);
}
} else {
ui.warn_label("The games log's directory is already deleted");
}

let settings_data = self.settings_state.clone();

let mut form = Form::new().add_report(egui_form::garde::GardeReport::new(settings_data.validate(&())));
Expand Down Expand Up @@ -142,15 +118,13 @@ impl View for SettingsPage<'_> {

if ui
.add_enabled(
self.manager.get_collection::<JavaCollection>().tasks().is_empty(),
self.manager.get_collection::<JavaDownloadingCollection>().tasks().is_empty(),
egui::Button::new("Download Java"),
)
.on_hover_text("Pressing this button will start the Java downloading process and add the downloaded binary as the selected one")
.clicked()
{
self.java_state.download_java(self.manager, ui.ctx().clone());
self.settings_state.java = JavaRunner::path(PathBuf::from(DOT_NOMI_JAVA_EXECUTABLE));
self.settings_state.update_config();
download_java_and_update_config(ui, self.manager, self.java_state, self.settings_state);
}

FormField::new(&mut form, field_path!("java")).label("Java").ui(ui, |ui: &mut egui::Ui| {
Expand Down
3 changes: 3 additions & 0 deletions crates/nomi-core/src/consts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,10 @@ pub const DOT_NOMI_CONFIGS_DIR: &str = "./.nomi/configs";
pub const DOT_NOMI_SETTINGS_CONFIG: &str = "./.nomi/configs/Settings.toml";
pub const DOT_NOMI_LOGS_DIR: &str = "./.nomi/logs";
pub const DOT_NOMI_JAVA_DIR: &str = "./.nomi/java";
#[cfg(not(windows))]
pub const DOT_NOMI_JAVA_EXECUTABLE: &str = "./.nomi/java/jdk-22.0.1/bin/java";
#[cfg(windows)]
pub const DOT_NOMI_JAVA_EXECUTABLE: &str = "./.nomi/java/jdk-22.0.1/bin/javaw.exe";
pub const DOT_NOMI_DATA_PACKS_DIR: &str = "./.nomi/datapacks";

pub const LIBRARIES_DIR: &str = "./libraries";
Expand Down
3 changes: 2 additions & 1 deletion crates/nomi-core/src/repository/java_runner.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,8 @@ pub enum JavaRunner {
impl JavaRunner {
pub fn from_environment() -> Self {
if std::env::var("PATH").is_ok_and(|path| path.contains("java")) {
Self::command("java")
let command = if cfg!(windows) { "javaw" } else { "java" };
Self::command(command)
} else {
Self::path(DOT_NOMI_JAVA_EXECUTABLE.into())
}
Expand Down
7 changes: 5 additions & 2 deletions crates/nomi-core/src/repository/username.rs
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
use std::sync::LazyLock;

use regex::Regex;
use serde::{de::Visitor, Deserialize, Serialize};
use thiserror::Error;
Expand Down Expand Up @@ -62,9 +64,10 @@ pub enum ValidationError {

impl Username {
pub fn new(s: impl Into<String>) -> anyhow::Result<Self> {
static REGEX: LazyLock<Regex> = LazyLock::new(|| Regex::new(r"^[a-zA-Z0-9_]{3,16}$").unwrap());

let s = s.into();
let re = Regex::new(r"^[a-zA-Z0-9_]{3,16}$")?;
match re.captures(&s) {
match REGEX.captures(&s) {
Some(_) => Ok(Username(s)),
None => Err(ValidationError::InvalidUsername.into()),
}
Expand Down

0 comments on commit 7285285

Please sign in to comment.