reedline/core_editor/
clip_buffer.rs1pub trait Clipboard: Send {
5 fn set(&mut self, content: &str, mode: ClipboardMode);
6
7 fn get(&mut self) -> (String, ClipboardMode);
8
9 fn clear(&mut self) {
10 self.set("", ClipboardMode::Normal);
11 }
12
13 fn len(&mut self) -> usize {
14 self.get().0.len()
15 }
16}
17
18#[derive(Copy, Clone, Debug, Default)]
20pub enum ClipboardMode {
21 #[default]
23 Normal,
24 Lines,
26}
27
28#[derive(Default)]
30pub struct LocalClipboard {
31 content: String,
32 mode: ClipboardMode,
33}
34
35impl LocalClipboard {
36 #[allow(dead_code)]
37 pub fn new() -> Self {
38 Self::default()
39 }
40}
41
42impl Clipboard for LocalClipboard {
43 fn set(&mut self, content: &str, mode: ClipboardMode) {
44 self.content = content.to_owned();
45 self.mode = mode;
46 }
47
48 fn get(&mut self) -> (String, ClipboardMode) {
49 (self.content.clone(), self.mode)
50 }
51}
52
53#[cfg(feature = "system_clipboard")]
54pub use system_clipboard::SystemClipboard;
55
56#[cfg(feature = "system_clipboard")]
57pub fn get_default_clipboard() -> SystemClipboard {
63 SystemClipboard::new()
64}
65
66#[cfg(not(feature = "system_clipboard"))]
67pub fn get_default_clipboard() -> LocalClipboard {
73 LocalClipboard::new()
74}
75
76#[cfg(feature = "system_clipboard")]
77mod system_clipboard {
78 use super::*;
79 use clipboard::{ClipboardContext, ClipboardProvider};
80
81 pub struct SystemClipboard {
85 cb: ClipboardContext,
86 local_copy: String,
87 mode: ClipboardMode,
88 }
89
90 impl SystemClipboard {
91 pub fn new() -> Self {
92 let cb = ClipboardProvider::new().unwrap();
93 SystemClipboard {
94 cb,
95 local_copy: String::new(),
96 mode: ClipboardMode::Normal,
97 }
98 }
99 }
100
101 impl Clipboard for SystemClipboard {
102 fn set(&mut self, content: &str, mode: ClipboardMode) {
103 self.local_copy = content.to_owned();
104 let _ = self.cb.set_contents(content.to_owned());
105 self.mode = mode;
106 }
107
108 fn get(&mut self) -> (String, ClipboardMode) {
109 let system_content = self.cb.get_contents().unwrap_or_default();
110 if system_content == self.local_copy {
111 (system_content, self.mode)
113 } else {
114 (system_content, ClipboardMode::Normal)
116 }
117 }
118 }
119}
120
121#[cfg(test)]
122mod tests {
123 use super::{get_default_clipboard, Clipboard, ClipboardMode};
124 #[test]
125 fn reads_back() {
126 let mut cb = get_default_clipboard();
127 let previous_state = cb.get().0;
129
130 cb.set("test", ClipboardMode::Normal);
132 assert_eq!(cb.len(), 4);
133 assert_eq!(cb.get().0, "test".to_owned());
134 cb.clear();
135 assert_eq!(cb.get().0, String::new());
136
137 cb.set(&previous_state, ClipboardMode::Normal);
140 }
141}