1
1
mirror of https://github.com/wez/wezterm.git synced 2024-12-25 06:12:16 +03:00

start moving some host functions to guicommon; clipboard first

This commit is contained in:
Wez Furlong 2019-02-24 08:36:59 -08:00
parent 668d456fdf
commit 5b84b6dfc9
4 changed files with 77 additions and 60 deletions

View File

@ -3,13 +3,13 @@
use crate::config::Config;
use crate::failure::Error;
use crate::font::FontConfiguration;
use crate::guicommon::host::{HostHelper, HostImpl};
use crate::guicommon::tabs::{Tab, TabId, Tabs};
use crate::guicommon::window::{Dimensions, TerminalWindow};
use crate::guiloop::glutinloop::GuiEventLoop;
use crate::guiloop::SessionTerminated;
use crate::opengl::render::Renderer;
use crate::{spawn_window_impl, Child, MasterPty};
use clipboard::{ClipboardContext, ClipboardProvider};
use glium;
use glium::glutin::dpi::{LogicalPosition, LogicalSize, PhysicalPosition, PhysicalSize};
use glium::glutin::{self, ElementState, MouseCursor};
@ -29,13 +29,12 @@ use winit::os::macos::WindowExt;
/// other state.
struct TabHost<'a> {
pty: &'a mut MasterPty,
host: &'a mut Host,
host: &'a mut HostImpl<Host>,
}
struct Host {
event_loop: Rc<GuiEventLoop>,
display: glium::Display,
clipboard: Clipboard,
window_position: Option<LogicalPosition>,
/// if is_some, holds position to be restored after exiting
/// fullscreen mode.
@ -44,37 +43,7 @@ struct Host {
fonts: Rc<FontConfiguration>,
}
/// macOS gets unhappy if we set up the clipboard too early,
/// so we use this to defer it until we use it
#[derive(Default)]
struct Clipboard {
clipboard: Option<ClipboardContext>,
}
impl Clipboard {
fn clipboard(&mut self) -> Result<&mut ClipboardContext, Error> {
if self.clipboard.is_none() {
self.clipboard = Some(ClipboardContext::new().map_err(|e| format_err!("{}", e))?);
}
Ok(self.clipboard.as_mut().unwrap())
}
pub fn get_clipboard(&mut self) -> Result<String, Error> {
self.clipboard()?
.get_contents()
.map_err(|e| format_err!("{}", e))
}
pub fn set_clipboard(&mut self, clip: Option<String>) -> Result<(), Error> {
self.clipboard()?
.set_contents(clip.unwrap_or_else(|| "".into()))
.map_err(|e| format_err!("{}", e))?;
// Request the clipboard contents we just set; on some systems
// if we copy and paste in wezterm, the clipboard isn't visible
// to us again until the second call to get_clipboard.
self.get_clipboard().map(|_| ())
}
}
impl HostHelper for Host {}
impl<'a> term::TerminalHost for TabHost<'a> {
fn writer(&mut self) -> &mut Write {
@ -88,11 +57,11 @@ impl<'a> term::TerminalHost for TabHost<'a> {
}
fn get_clipboard(&mut self) -> Result<String, Error> {
self.host.clipboard.get_clipboard()
self.host.get_clipboard()
}
fn set_clipboard(&mut self, clip: Option<String>) -> Result<(), Error> {
self.host.clipboard.set_clipboard(clip)
self.host.set_clipboard(clip)
}
fn set_title(&mut self, _title: &str) {
@ -102,8 +71,8 @@ impl<'a> term::TerminalHost for TabHost<'a> {
}
fn toggle_full_screen(&mut self) {
let window = self.host.display.gl_window();
if let Some(pos) = self.host.is_fullscreen.take() {
let window = self.host.display.gl_window();
// Use simple fullscreen mode on macos, as wez personally
// prefers the faster transition to/from this mode than
// the Lion+ slow transition to a new Space. This could
@ -120,6 +89,7 @@ impl<'a> term::TerminalHost for TabHost<'a> {
// on Linux.
self.host.is_fullscreen = self.host.window_position.take();
let window = self.host.display.gl_window();
#[cfg(target_os = "macos")]
window.set_simple_fullscreen(true);
#[cfg(not(target_os = "macos"))]
@ -196,7 +166,7 @@ impl<'a> term::TerminalHost for TabHost<'a> {
}
pub struct GliumTerminalWindow {
host: Host,
host: HostImpl<Host>,
event_loop: Rc<GuiEventLoop>,
config: Rc<Config>,
fonts: Rc<FontConfiguration>,
@ -336,15 +306,14 @@ impl GliumTerminalWindow {
};
let window_position = display.gl_window().get_position();
let host = Host {
let host = HostImpl::new(Host {
event_loop: Rc::clone(event_loop),
display,
clipboard: Clipboard::default(),
window_position,
is_fullscreen: None,
config: Rc::clone(config),
fonts: Rc::clone(fonts),
};
});
host.display.gl_window().set_cursor(MouseCursor::Text);

57
src/guicommon/host.rs Normal file
View File

@ -0,0 +1,57 @@
use clipboard::{ClipboardContext, ClipboardProvider};
use failure::Error;
use std::ops::{Deref, DerefMut};
pub trait HostHelper {
}
pub struct HostImpl<H: HostHelper> {
helper: H,
/// macOS gets unhappy if we set up the clipboard too early,
/// so we use an Option to defer it until we use it
clipboard: Option<ClipboardContext>,
}
impl<H: HostHelper> HostImpl<H> {
pub fn new(helper: H) -> Self {
Self {
helper,
clipboard: None,
}
}
fn clipboard(&mut self) -> Result<&mut ClipboardContext, Error> {
if self.clipboard.is_none() {
self.clipboard = Some(ClipboardContext::new().map_err(|e| format_err!("{}", e))?);
}
Ok(self.clipboard.as_mut().unwrap())
}
pub fn get_clipboard(&mut self) -> Result<String, Error> {
self.clipboard()?
.get_contents()
.map_err(|e| format_err!("{}", e))
}
pub fn set_clipboard(&mut self, clip: Option<String>) -> Result<(), Error> {
self.clipboard()?
.set_contents(clip.unwrap_or_else(|| "".into()))
.map_err(|e| format_err!("{}", e))?;
// Request the clipboard contents we just set; on some systems
// if we copy and paste in wezterm, the clipboard isn't visible
// to us again until the second call to get_clipboard.
self.get_clipboard().map(|_| ())
}
}
impl<H: HostHelper> Deref for HostImpl<H> {
type Target = H;
fn deref(&self) -> &H {
&self.helper
}
}
impl<H: HostHelper> DerefMut for HostImpl<H> {
fn deref_mut(&mut self) -> &mut H {
&mut self.helper
}
}

View File

@ -1,2 +1,3 @@
pub mod host;
pub mod tabs;
pub mod window;

View File

@ -4,12 +4,12 @@ use super::xkeysyms;
use super::{Connection, Window};
use crate::config::Config;
use crate::font::FontConfiguration;
use crate::guicommon::host::{HostHelper, HostImpl};
use crate::guicommon::tabs::{Tab, TabId, Tabs};
use crate::guicommon::window::{Dimensions, TerminalWindow};
use crate::guiloop::x11::{GuiEventLoop, WindowId};
use crate::guiloop::SessionTerminated;
use crate::MasterPty;
use clipboard::{ClipboardContext, ClipboardProvider};
use failure::Error;
use futures;
use std::cell::RefMut;
@ -24,20 +24,21 @@ use xcb;
/// other state.
struct TabHost<'a> {
pty: &'a mut MasterPty,
host: &'a mut Host,
host: &'a mut HostImpl<Host>,
}
/// Holds most of the information we need to implement `TerminalHost`
struct Host {
window: Window,
clipboard: ClipboardContext,
event_loop: Rc<GuiEventLoop>,
fonts: Rc<FontConfiguration>,
config: Rc<Config>,
}
impl HostHelper for Host {}
pub struct X11TerminalWindow {
host: Host,
host: HostImpl<Host>,
conn: Rc<Connection>,
fonts: Rc<FontConfiguration>,
renderer: Renderer,
@ -78,21 +79,11 @@ impl<'a> term::TerminalHost for TabHost<'a> {
}
fn get_clipboard(&mut self) -> Result<String, Error> {
self.host
.clipboard
.get_contents()
.map_err(|e| format_err!("{}", e))
self.host.get_clipboard()
}
fn set_clipboard(&mut self, clip: Option<String>) -> Result<(), Error> {
self.host
.clipboard
.set_contents(clip.unwrap_or_else(|| "".into()))
.map_err(|e| format_err!("{}", e))
// Request the clipboard contents we just set; on some systems
// if we copy and paste in wezterm, the clipboard isn't visible
// to us again until the second call to get_clipboard.
.and_then(|_| self.get_clipboard().map(|_| ()))
self.host.set_clipboard(clip)
}
fn set_title(&mut self, _title: &str) {
@ -266,13 +257,12 @@ impl X11TerminalWindow {
let window = Window::new(&event_loop.conn, width, height)?;
window.set_title("wezterm");
let host = Host {
let host = HostImpl::new(Host {
window,
clipboard: ClipboardContext::new().map_err(|e| format_err!("{}", e))?,
event_loop: Rc::clone(event_loop),
config: Rc::clone(config),
fonts: Rc::clone(fonts),
};
});
let renderer = Renderer::new(&host.window, width, height, fonts, palette)?;
let cell_height = cell_height.ceil() as usize;