feat: saving image

dialog is missing!!
This commit is contained in:
electria 2026-06-29 08:46:45 -07:00
commit 68964f24fd
Signed by: electria
SSH key fingerprint: SHA256:8LlB3ucPbBHqozqkhsNbaV5oG3SlzzqUj8FZDL6IPQs
3 changed files with 71 additions and 2 deletions

36
Cargo.lock generated
View file

@ -812,6 +812,8 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "1e0e367e4e7da84520dedcac1901e4da967309406d1e51017ae1abfb97adbd38"
dependencies = [
"bitflags 2.13.0",
"block2 0.6.2",
"libc",
"objc2 0.6.4",
]
@ -1647,6 +1649,7 @@ dependencies = [
"dirs",
"iced",
"image",
"rfd",
]
[[package]]
@ -2719,6 +2722,12 @@ dependencies = [
"windows-sys 0.61.2",
]
[[package]]
name = "pollster"
version = "0.4.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2f3a9f18d041e6d0e102a0a46750538147e5e8992d3b4873aaafee2520b00ce3"
[[package]]
name = "portable-atomic"
version = "1.13.1"
@ -3019,6 +3028,33 @@ version = "1.1.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "19b30a45b0cd0bcca8037f3d0dc3421eaf95327a17cad11964fb8179b4fc4832"
[[package]]
name = "rfd"
version = "0.17.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "20dafead71c16a34e1ff357ddefc8afc11e7d51d6d2b9fbd07eaa48e3e540220"
dependencies = [
"block2 0.6.2",
"dispatch2",
"js-sys",
"libc",
"log",
"objc2 0.6.4",
"objc2-app-kit 0.3.2",
"objc2-core-foundation",
"objc2-foundation 0.3.2",
"percent-encoding",
"pollster",
"raw-window-handle",
"wasm-bindgen",
"wasm-bindgen-futures",
"wayland-backend",
"wayland-client",
"wayland-protocols",
"web-sys",
"windows-sys 0.61.2",
]
[[package]]
name = "rgb"
version = "0.8.53"

View file

@ -7,3 +7,4 @@ edition = "2024"
iced = { version = "0.14.0", features = [ "image" ] }
dirs = "6.0.0"
image = "0.25.10"
rfd = "0.17.2"

View file

@ -1,11 +1,14 @@
use std::env;
use std::{env, ffi::OsStr, fs};
use iced::{
Color, Element, Renderer, Subscription, Task, Theme, color, event,
keyboard::{self, Key, key},
theme, widget, window,
};
use image::{EncodableLayout, ImageReader, Pixel, Rgba, RgbaImage, imageops};
use image::{
EncodableLayout, ImageReader, Pixel, Rgba, RgbaImage, codecs::webp::WebPEncoder, imageops,
};
use rfd::FileDialog;
#[derive(Clone, Debug)]
enum Message {
@ -85,6 +88,35 @@ impl State {
return self.allocate_image();
}
Key::Character("s") => {
let Some(path) = FileDialog::new().save_file() else {
eprintln!("no path to save provided");
return Task::none();
};
let Ok(file) = fs::File::create(&path)
.inspect_err(|e| eprintln!("failed to create file: {e}"))
else {
return Task::none();
};
let maybe_encoder =
match path.extension().map(OsStr::to_string_lossy).as_deref() {
Some("webp") => Some(WebPEncoder::new_lossless(file)),
None | Some(_) => None,
};
let result = if let Some(encoder) = maybe_encoder {
self.image.write_with_encoder(encoder)
} else {
self.image.save(path)
};
#[allow(unused_must_use)]
result.inspect_err(|e| eprintln!("failed to save image: {e}"));
}
// ignore unused keys
_ => {}
},