diff options
Diffstat (limited to 'copypasta/src/x11.rs')
-rw-r--r-- | copypasta/src/x11.rs | 144 |
1 files changed, 0 insertions, 144 deletions
diff --git a/copypasta/src/x11.rs b/copypasta/src/x11.rs deleted file mode 100644 index 0bb769a1..00000000 --- a/copypasta/src/x11.rs +++ /dev/null @@ -1,144 +0,0 @@ -//! X11 Clipboard implementation -//! -//! Note that the x11 implementation is really crap right now - we just depend -//! on xclip being on the user's path. If x11 pasting doesn't work, it's -//! probably because xclip is unavailable. There's currently no non-GPL x11 -//! clipboard library for Rust. Until then, we have this hack. -//! -//! FIXME: Implement actual X11 clipboard API using the ICCCM reference -//! https://tronche.com/gui/x/icccm/ -use std::ffi::OsStr; -use std::io; -use std::process::{Command, Output}; -use std::string::FromUtf8Error; - -use super::{Load, Store}; - -/// The x11 clipboard -pub struct Clipboard; - -#[derive(Debug)] -pub enum Error { - Io(io::Error), - Xclip(String), - Utf8(FromUtf8Error), -} - -impl ::std::error::Error for Error { - fn cause(&self) -> Option<&::std::error::Error> { - match *self { - Error::Io(ref err) => Some(err), - Error::Utf8(ref err) => Some(err), - _ => None, - } - } - - fn description(&self) -> &str { - match *self { - Error::Io(..) => "Error calling xclip", - Error::Xclip(..) => "Error reported by xclip", - Error::Utf8(..) => "Clipboard contents not utf8", - } - } -} - -impl ::std::fmt::Display for Error { - fn fmt(&self, f: &mut ::std::fmt::Formatter) -> ::std::fmt::Result { - match *self { - Error::Io(ref err) => match err.kind() { - io::ErrorKind::NotFound => { - write!(f, "Please install `xclip` to enable clipboard support") - }, - _ => write!(f, "Error calling xclip: {}", err), - }, - Error::Xclip(ref s) => write!(f, "Error from xclip: {}", s), - Error::Utf8(ref err) => write!(f, "Error parsing xclip output: {}", err), - } - } -} - -impl From<io::Error> for Error { - fn from(val: io::Error) -> Error { - Error::Io(val) - } -} - -impl From<FromUtf8Error> for Error { - fn from(val: FromUtf8Error) -> Error { - Error::Utf8(val) - } -} - -impl Load for Clipboard { - type Err = Error; - - fn new() -> Result<Self, Error> { - Ok(Clipboard) - } - - fn load_primary(&self) -> Result<String, Self::Err> { - let output = Command::new("xclip").args(&["-o", "-selection", "clipboard"]).output()?; - - Clipboard::process_xclip_output(output) - } - - fn load_selection(&self) -> Result<String, Self::Err> { - let output = Command::new("xclip").args(&["-o"]).output()?; - - Clipboard::process_xclip_output(output) - } -} - -impl Store for Clipboard { - /// Sets the primary clipboard contents - #[inline] - fn store_primary<S>(&mut self, contents: S) -> Result<(), Self::Err> - where - S: Into<String>, - { - self.store(contents, &["-i", "-selection", "clipboard"]) - } - - /// Sets the secondary clipboard contents - #[inline] - fn store_selection<S>(&mut self, contents: S) -> Result<(), Self::Err> - where - S: Into<String>, - { - self.store(contents, &["-i"]) - } -} - -impl Clipboard { - fn process_xclip_output(output: Output) -> Result<String, Error> { - if output.status.success() { - String::from_utf8(output.stdout).map_err(::std::convert::From::from) - } else { - String::from_utf8(output.stderr).map_err(::std::convert::From::from) - } - } - - fn store<C, S>(&mut self, contents: C, args: &[S]) -> Result<(), Error> - where - C: Into<String>, - S: AsRef<OsStr>, - { - use std::io::Write; - use std::process::Stdio; - - let contents = contents.into(); - let mut child = Command::new("xclip").args(args).stdin(Stdio::piped()).spawn()?; - - if let Some(stdin) = child.stdin.as_mut() { - stdin.write_all(contents.as_bytes())?; - } - - // Return error if didn't exit cleanly - let exit_status = child.wait()?; - if exit_status.success() { - Ok(()) - } else { - Err(Error::Xclip("xclip returned non-zero exit code".into())) - } - } -} |