aboutsummaryrefslogtreecommitdiff
path: root/alacritty/src/event.rs
diff options
context:
space:
mode:
Diffstat (limited to 'alacritty/src/event.rs')
-rw-r--r--alacritty/src/event.rs134
1 files changed, 79 insertions, 55 deletions
diff --git a/alacritty/src/event.rs b/alacritty/src/event.rs
index 09e74a9d..4af372c9 100644
--- a/alacritty/src/event.rs
+++ b/alacritty/src/event.rs
@@ -5,8 +5,6 @@ use std::cmp::{max, min};
use std::collections::{HashMap, VecDeque};
use std::error::Error;
use std::fmt::Debug;
-#[cfg(not(any(target_os = "macos", windows)))]
-use std::fs;
use std::path::PathBuf;
use std::time::{Duration, Instant};
use std::{env, f32, mem};
@@ -35,10 +33,10 @@ use alacritty_terminal::term::{ClipboardType, SizeInfo, Term, TermMode};
#[cfg(not(windows))]
use alacritty_terminal::tty;
-use crate::cli::Options as CliOptions;
+use crate::cli::{Options as CliOptions, TerminalOptions as TerminalCliOptions};
use crate::clipboard::Clipboard;
use crate::config::ui_config::{HintAction, HintInternalAction};
-use crate::config::{self, Config};
+use crate::config::{self, UiConfig};
use crate::daemon::start_daemon;
use crate::display::hint::HintMatch;
use crate::display::window::Window;
@@ -89,7 +87,7 @@ pub enum EventType {
ConfigReload(PathBuf),
Message(Message),
Scroll(Scroll),
- CreateWindow,
+ CreateWindow(Option<TerminalCliOptions>),
BlinkCursor,
SearchNext,
}
@@ -180,7 +178,7 @@ pub struct ActionContext<'a, N, T> {
pub modifiers: &'a mut ModifiersState,
pub display: &'a mut Display,
pub message_buffer: &'a mut MessageBuffer,
- pub config: &'a mut Config,
+ pub config: &'a mut UiConfig,
pub event_loop: &'a EventLoopWindowTarget<Event>,
pub event_proxy: &'a EventLoopProxy<Event>,
pub scheduler: &'a mut Scheduler,
@@ -241,7 +239,8 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
None => return,
};
- if ty == ClipboardType::Selection && self.config.selection.save_to_clipboard {
+ if ty == ClipboardType::Selection && self.config.terminal_config.selection.save_to_clipboard
+ {
self.clipboard.store(ClipboardType::Clipboard, text.clone());
}
self.clipboard.store(ty, text);
@@ -318,17 +317,17 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
#[inline]
fn received_count(&mut self) -> &mut usize {
- &mut self.received_count
+ self.received_count
}
#[inline]
fn suppress_chars(&mut self) -> &mut bool {
- &mut self.suppress_chars
+ self.suppress_chars
}
#[inline]
fn modifiers(&mut self) -> &mut ModifiersState {
- &mut self.modifiers
+ self.modifiers
}
#[inline]
@@ -338,7 +337,7 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
#[inline]
fn display(&mut self) -> &mut Display {
- &mut self.display
+ self.display
}
#[inline]
@@ -355,26 +354,12 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
let mut env_args = env::args();
let alacritty = env_args.next().unwrap();
+ // Use working directory of controlling process, or fallback to initial shell, then add it
+ // as working-directory parameter.
#[cfg(unix)]
- let mut args = {
- // Use working directory of controlling process, or fallback to initial shell.
- let mut pid = unsafe { libc::tcgetpgrp(tty::master_fd()) };
- if pid < 0 {
- pid = tty::child_pid();
- }
-
- #[cfg(not(any(target_os = "macos", target_os = "freebsd")))]
- let link_path = format!("/proc/{}/cwd", pid);
- #[cfg(target_os = "freebsd")]
- let link_path = format!("/compat/linux/proc/{}/cwd", pid);
- #[cfg(not(target_os = "macos"))]
- let cwd = fs::read_link(link_path);
- #[cfg(target_os = "macos")]
- let cwd = macos::proc::cwd(pid);
-
- // Add the current working directory as parameter.
- cwd.map(|path| vec!["--working-directory".into(), path]).unwrap_or_default()
- };
+ let mut args = foreground_process_path()
+ .map(|path| vec!["--working-directory".into(), path])
+ .unwrap_or_default();
#[cfg(not(unix))]
let mut args: Vec<PathBuf> = Vec::new();
@@ -395,20 +380,34 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
start_daemon(&alacritty, &args);
}
+ #[cfg(not(windows))]
+ fn create_new_window(&mut self) {
+ let options = if let Ok(working_directory) = foreground_process_path() {
+ let mut options = TerminalCliOptions::new();
+ options.working_directory = Some(working_directory);
+ Some(options)
+ } else {
+ None
+ };
+
+ let _ = self.event_proxy.send_event(Event::new(EventType::CreateWindow(options), None));
+ }
+
+ #[cfg(windows)]
fn create_new_window(&mut self) {
- let _ = self.event_proxy.send_event(Event::new(EventType::CreateWindow, None));
+ let _ = self.event_proxy.send_event(Event::new(EventType::CreateWindow(None), None));
}
fn change_font_size(&mut self, delta: f32) {
*self.font_size = max(*self.font_size + delta, Size::new(FONT_SIZE_STEP));
- let font = self.config.ui_config.font.clone().with_size(*self.font_size);
+ let font = self.config.font.clone().with_size(*self.font_size);
self.display.pending_update.set_font(font);
*self.dirty = true;
}
fn reset_font_size(&mut self) {
- *self.font_size = self.config.ui_config.font.size();
- self.display.pending_update.set_font(self.config.ui_config.font.clone());
+ *self.font_size = self.config.font.size();
+ self.display.pending_update.set_font(self.config.font.clone());
*self.dirty = true;
}
@@ -632,14 +631,15 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
// Disable cursor blinking.
let timer_id = TimerId::new(Topic::BlinkCursor, self.display.window.id());
if let Some(timer) = self.scheduler.unschedule(timer_id) {
- let interval = Duration::from_millis(self.config.cursor.blink_interval());
+ let interval =
+ Duration::from_millis(self.config.terminal_config.cursor.blink_interval());
self.scheduler.schedule(timer.event, interval, true, timer.id);
self.display.cursor_hidden = false;
*self.dirty = true;
}
// Hide mouse cursor.
- if self.config.ui_config.mouse.hide_when_typing {
+ if self.config.mouse.hide_when_typing {
self.display.window.set_mouse_visible(false);
}
}
@@ -769,7 +769,7 @@ impl<'a, N: Notify + 'a, T: EventListener> input::ActionContext<T> for ActionCon
self.message_buffer.message()
}
- fn config(&self) -> &Config {
+ fn config(&self) -> &UiConfig {
self.config
}
@@ -794,7 +794,7 @@ impl<'a, N: Notify + 'a, T: EventListener> ActionContext<'a, N, T> {
};
// Hide cursor while typing into the search bar.
- if self.config.ui_config.mouse.hide_when_typing {
+ if self.config.mouse.hide_when_typing {
self.display.window.set_mouse_visible(false);
}
@@ -905,9 +905,9 @@ impl<'a, N: Notify + 'a, T: EventListener> ActionContext<'a, N, T> {
/// Update the cursor blinking state.
fn update_cursor_blinking(&mut self) {
// Get config cursor style.
- let mut cursor_style = self.config.cursor.style;
+ let mut cursor_style = self.config.terminal_config.cursor.style;
if self.terminal.mode().contains(TermMode::VI) {
- cursor_style = self.config.cursor.vi_mode_style.unwrap_or(cursor_style);
+ cursor_style = self.config.terminal_config.cursor.vi_mode_style.unwrap_or(cursor_style);
};
// Check terminal cursor style.
@@ -919,7 +919,8 @@ impl<'a, N: Notify + 'a, T: EventListener> ActionContext<'a, N, T> {
self.scheduler.unschedule(timer_id);
if blinking && self.terminal.is_focused {
let event = Event::new(EventType::BlinkCursor, self.display.window.id());
- let interval = Duration::from_millis(self.config.cursor.blink_interval());
+ let interval =
+ Duration::from_millis(self.config.terminal_config.cursor.blink_interval());
self.scheduler.schedule(event, interval, true, timer_id);
} else {
self.display.cursor_hidden = false;
@@ -1004,7 +1005,7 @@ impl input::Processor<EventProxy, ActionContext<'_, Notifier, EventProxy>> {
let display_update_pending = &mut self.ctx.display.pending_update;
// Push current font to update its DPR.
- let font = self.ctx.config.ui_config.font.clone();
+ let font = self.ctx.config.font.clone();
display_update_pending.set_font(font.with_size(*self.ctx.font_size));
// Resize to event's dimensions, since no resize event is emitted on Wayland.
@@ -1026,15 +1027,13 @@ impl input::Processor<EventProxy, ActionContext<'_, Notifier, EventProxy>> {
},
EventType::Terminal(event) => match event {
TerminalEvent::Title(title) => {
- let ui_config = &self.ctx.config.ui_config;
- if ui_config.window.dynamic_title {
+ if self.ctx.config.window.dynamic_title {
self.ctx.window().set_title(&title);
}
},
TerminalEvent::ResetTitle => {
- let ui_config = &self.ctx.config.ui_config;
- if ui_config.window.dynamic_title {
- self.ctx.display.window.set_title(&ui_config.window.title);
+ if self.ctx.config.window.dynamic_title {
+ self.ctx.display.window.set_title(&self.ctx.config.window.title);
}
},
TerminalEvent::Wakeup => *self.ctx.dirty = true,
@@ -1049,7 +1048,7 @@ impl input::Processor<EventProxy, ActionContext<'_, Notifier, EventProxy>> {
self.ctx.display.visual_bell.ring();
// Execute bell command.
- if let Some(bell_command) = &self.ctx.config.ui_config.bell.command {
+ if let Some(bell_command) = &self.ctx.config.bell.command {
start_daemon(bell_command.program(), bell_command.args());
}
},
@@ -1069,7 +1068,7 @@ impl input::Processor<EventProxy, ActionContext<'_, Notifier, EventProxy>> {
TerminalEvent::Exit => (),
TerminalEvent::CursorBlinkingChange => self.ctx.update_cursor_blinking(),
},
- EventType::ConfigReload(_) | EventType::CreateWindow => (),
+ EventType::ConfigReload(_) | EventType::CreateWindow(_) => (),
},
GlutinEvent::RedrawRequested(_) => *self.ctx.dirty = true,
GlutinEvent::WindowEvent { event, .. } => {
@@ -1162,7 +1161,7 @@ pub struct Processor {
wayland_event_queue: Option<EventQueue>,
windows: HashMap<WindowId, WindowContext>,
cli_options: CliOptions,
- config: Config,
+ config: UiConfig,
}
impl Processor {
@@ -1170,7 +1169,7 @@ impl Processor {
///
/// Takes a writer which is expected to be hooked up to the write end of a PTY.
pub fn new(
- config: Config,
+ config: UiConfig,
cli_options: CliOptions,
_event_loop: &EventLoop<Event>,
) -> Processor {
@@ -1194,10 +1193,12 @@ impl Processor {
pub fn create_window(
&mut self,
event_loop: &EventLoopWindowTarget<Event>,
+ options: Option<TerminalCliOptions>,
proxy: EventLoopProxy<Event>,
) -> Result<(), Box<dyn Error>> {
let window_context = WindowContext::new(
&self.config,
+ options,
event_loop,
proxy,
#[cfg(all(feature = "wayland", not(any(target_os = "macos", windows))))]
@@ -1219,7 +1220,7 @@ impl Processor {
let mut clipboard = Clipboard::new();
event_loop.run_return(|event, event_loop, control_flow| {
- if self.config.ui_config.debug.print_events {
+ if self.config.debug.print_events {
info!("glutin event: {:?}", event);
}
@@ -1246,7 +1247,7 @@ impl Processor {
// Shutdown if no more terminals are open.
if self.windows.is_empty() {
// Write ref tests of last window to disk.
- if self.config.ui_config.debug.ref_test {
+ if self.config.debug.ref_test {
window_context.write_ref_test_results();
}
@@ -1302,8 +1303,10 @@ impl Processor {
}
},
// Create a new terminal window.
- GlutinEvent::UserEvent(Event { payload: EventType::CreateWindow, .. }) => {
- if let Err(err) = self.create_window(event_loop, proxy.clone()) {
+ GlutinEvent::UserEvent(Event {
+ payload: EventType::CreateWindow(options), ..
+ }) => {
+ if let Err(err) = self.create_window(event_loop, options, proxy.clone()) {
error!("Could not open window: {:?}", err);
}
},
@@ -1386,3 +1389,24 @@ impl EventListener for EventProxy {
let _ = self.proxy.send_event(Event::new(event.into(), self.window_id));
}
}
+
+#[cfg(not(windows))]
+pub fn foreground_process_path() -> Result<PathBuf, Box<dyn Error>> {
+ let mut pid = unsafe { libc::tcgetpgrp(tty::master_fd()) };
+ if pid < 0 {
+ pid = tty::child_pid();
+ }
+
+ #[cfg(not(any(target_os = "macos", target_os = "freebsd")))]
+ let link_path = format!("/proc/{}/cwd", pid);
+ #[cfg(target_os = "freebsd")]
+ let link_path = format!("/compat/linux/proc/{}/cwd", pid);
+
+ #[cfg(not(target_os = "macos"))]
+ let cwd = std::fs::read_link(link_path)?;
+
+ #[cfg(target_os = "macos")]
+ let cwd = macos::proc::cwd(pid)?;
+
+ Ok(cwd)
+}