Skip to content

Commit

Permalink
input and output file pickers, remove alert button
Browse files Browse the repository at this point in the history
  • Loading branch information
brevalferrari committed Jul 22, 2024
1 parent 7106e3b commit 5d6733c
Show file tree
Hide file tree
Showing 3 changed files with 152 additions and 55 deletions.
29 changes: 29 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ rfd = "0.14.1"
thiserror = "1.0.63"
dirs = "5.0.1"
serde_json = "1.0.120"
strum = { version = "0.26.3", features = ["derive"] }

# native:
[target.'cfg(not(target_arch = "wasm32"))'.dependencies]
Expand Down
177 changes: 122 additions & 55 deletions src/app.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@ mod files;
mod files_wasm;
#[cfg(target_arch = "wasm32")]
use files_wasm as files;
use strum::{Display, EnumIter, IntoEnumIterator};

#[cfg(target_arch = "wasm32")]
type FilePickerSharedResult = Arc<Mutex<Option<thread::Result<Option<String>>>>>;
Expand All @@ -34,6 +35,12 @@ fn input_file() -> &'static FilePickerSharedResult {
INPUT_FILE.get_or_init(Default::default)
}

#[cfg(target_arch = "wasm32")]
fn output_file() -> &'static FilePickerSharedResult {
static OUTPUT_FILE: OnceLock<FilePickerSharedResult> = OnceLock::new();
OUTPUT_FILE.get_or_init(Default::default)
}

/// We derive Deserialize/Serialize so we can persist app state on shutdown.
#[derive(Default, Deserialize, Serialize)]
#[serde(default)] // if we add new fields, give them default values when deserializing old state
Expand All @@ -46,6 +53,8 @@ pub struct TemplateApp {
#[cfg(target_arch = "wasm32")]
#[serde(skip)]
input_file_asked: bool,
#[serde(skip)]
output_file_asked: bool,
}

impl TemplateApp {
Expand Down Expand Up @@ -115,16 +124,18 @@ impl eframe::App for TemplateApp {
ui.heading("Bent");
ui.separator();

ui.label("Input file:");
self.browse(ui);

ui.horizontal(|ui| {
if ui.button("Alert").clicked() {
self.toasts.warning("Warning!");
}
FileDirection::iter().for_each(|direction| {
ui.label(format!("{direction} file:"));
self.browse(ui, direction);
});

ui.separator();
// ui.horizontal(|ui| {
// if ui.button("Alert").clicked() {
// self.toasts.warning("Warning!");
// }
// });

// ui.separator();

ui.with_layout(egui::Layout::bottom_up(egui::Align::LEFT), |ui| {
ui.add(egui::github_link_file!(
Expand Down Expand Up @@ -177,31 +188,62 @@ pub fn spawn_and_collect<F: 'static + Future<Output = Option<String>> + UnwindSa
});
}

#[derive(Display, Clone, Copy, EnumIter)]
enum FileDirection {
Input,
Output,
}

impl TemplateApp {
#[cfg(target_arch = "wasm32")]
fn browse(&mut self, ui: &mut egui::Ui) {
fn browse(&mut self, ui: &mut egui::Ui, direction: FileDirection) {
ui.horizontal(|ui| {
if ui.button("Browse").clicked() {
debug!("user asked to open a file");
TemplateApp::prompt();
self.input_file_asked = true;
debug!("user asked to open a file for {direction}");
TemplateApp::prompt(direction);
match direction {
FileDirection::Input => {
self.input_file_asked = true;
}
FileDirection::Output => {
self.output_file_asked = true;
}
}
}
if self.input_file_asked {
let mut guard = input_file().lock();
if match direction {
FileDirection::Input => self.input_file_asked,
FileDirection::Output => self.output_file_asked,
} {
let mut guard = match direction {
FileDirection::Input => input_file(),
FileDirection::Output => output_file(),
}
.lock();
if guard.as_ref().is_some() {
self.input_file_asked = false;
match direction {
FileDirection::Input => {
self.input_file_asked = false;
}
FileDirection::Output => {
self.output_file_asked = false;
}
}
trace!("just got the file picker result");
match {
let res = {
let guard = guard.as_ref();
unsafe { guard.unwrap_unchecked() }
} {
};
match res {
Ok(maybe_path) => {
trace!("it performed successfuly");
if let Some(path) = maybe_path {
match ImageFile::try_new(path) {
Ok(file) => {
trace!("file is correct");
self.files[0] = Some(file);
self.files[match direction {
FileDirection::Input => 0,
FileDirection::Output => 1,
}] = Some(file);
}
Err(e) => {
trace!("file is incorrect, reason: {e}");
Expand All @@ -224,56 +266,78 @@ impl TemplateApp {
}
}
ui.label(
self.files[0]
.as_ref()
.map(|file| file.to_string())
.unwrap_or_default(),
self.files[match direction {
FileDirection::Input => 0,
FileDirection::Output => 1,
}]
.as_ref()
.map(|file| file.to_string())
.unwrap_or_default(),
);
});
}
#[cfg(target_arch = "wasm32")]
fn prompt() {
fn prompt(direction: FileDirection) {
use std::panic::AssertUnwindSafe;

use rfd::AsyncFileDialog;

spawn_and_collect(
AssertUnwindSafe(
AsyncFileDialog::new()
.set_title("Input image")
.set_directory(working_dir())
.add_filter(
"images",
&ImageFormat::all()
.flat_map(ImageFormat::extensions_str)
.collect::<Vec<&'static &'static str>>(),
)
.pick_file()
.map(|x| x.map(|file| file.file_name())),
let fd = AsyncFileDialog::new()
.set_title(format!("{direction} image"))
.set_directory(working_dir())
.add_filter(
"images",
&ImageFormat::all()
.flat_map(ImageFormat::extensions_str)
.collect::<Vec<&'static &'static str>>(),
);

match direction {
FileDirection::Input => spawn_and_collect(
AssertUnwindSafe(fd.pick_file().map(|x| x.map(|file| file.file_name()))),
Arc::downgrade(match direction {
FileDirection::Input => input_file(),
FileDirection::Output => output_file(),
}),
),
Arc::downgrade(input_file()),
);
FileDirection::Output => {
spawn_and_collect(
AssertUnwindSafe(fd.save_file().map(|x| x.map(|file| file.file_name()))),
Arc::downgrade(match direction {
FileDirection::Input => input_file(),
FileDirection::Output => output_file(),
}),
);
}
}
}
#[cfg(not(target_arch = "wasm32"))]
fn browse(&mut self, ui: &mut egui::Ui) {
fn browse(&mut self, ui: &mut egui::Ui, direction: FileDirection) {
use rfd::FileDialog;

ui.horizontal(|ui| {
if ui.button("Browse").clicked() {
if let Some(path) = FileDialog::new()
.set_title("Input image")
.set_directory(working_dir())
.add_filter(
"images",
&ImageFormat::all()
.flat_map(ImageFormat::extensions_str)
.collect::<Vec<&'static &'static str>>(),
)
.pick_file()
{
if let Some(path) = {
let fd = FileDialog::new()
.set_title(format!("{direction} image"))
.set_directory(working_dir())
.add_filter(
"images",
&ImageFormat::all()
.flat_map(ImageFormat::extensions_str)
.collect::<Vec<&'static &'static str>>(),
);
match direction {
FileDirection::Input => fd.pick_file(),
FileDirection::Output => fd.save_file(),
}
} {
match ImageFile::try_new(&path) {
Ok(file) => {
self.files[0] = Some(file);
self.files[match direction {
FileDirection::Input => 0,
FileDirection::Output => 1,
}] = Some(file);
}
Err(e) => {
self.toasts.error(e.to_string());
Expand All @@ -282,10 +346,13 @@ impl TemplateApp {
}
}
ui.label(
self.files[0]
.clone()
.map(|file| file.display().to_string())
.unwrap_or_default(),
self.files[match direction {
FileDirection::Input => 0,
FileDirection::Output => 1,
}]
.clone()
.map(|file| file.display().to_string())
.unwrap_or_default(),
);
});
}
Expand Down

0 comments on commit 5d6733c

Please sign in to comment.