use std::sync::Mutex;
use services_core::Clipboard;
pub struct DesktopClipboard(Mutex<Option<arboard::Clipboard>>);
impl DesktopClipboard {
pub fn new() -> Result<Self, arboard::Error> {
Ok(Self(Mutex::new(Some(arboard::Clipboard::new()?))))
}
pub fn install() {
match Self::new() {
Ok(clipboard) => services_core::set_clipboard(std::sync::Arc::new(clipboard)),
Err(e) => tracing::warn!("no system clipboard: {e}"),
}
}
fn with<R>(&self, f: impl FnOnce(&mut arboard::Clipboard) -> R) -> Option<R> {
self.0.lock().ok()?.as_mut().map(f)
}
}
impl Clipboard for DesktopClipboard {
fn text(&self) -> Option<String> {
self.with(|c| c.get_text().ok())?
}
fn set_text(&self, text: &str) {
if let Some(Err(e)) = self.with(|c| c.set_text(text.to_owned())) {
tracing::warn!("could not set the clipboard: {e}");
}
}
}