Add general nvim start error message (fix #8)
This commit is contained in:
		
							parent
							
								
									5260d78418
								
							
						
					
					
						commit
						62a996f7db
					
				
							
								
								
									
										52
									
								
								src/error.rs
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										52
									
								
								src/error.rs
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,52 @@ | |||||||
|  | use std::ops::Deref; | ||||||
|  | 
 | ||||||
|  | use htmlescape::encode_minimal; | ||||||
|  | 
 | ||||||
|  | use gtk; | ||||||
|  | use gtk::prelude::*; | ||||||
|  | 
 | ||||||
|  | use gtk_sys; | ||||||
|  | 
 | ||||||
|  | use shell; | ||||||
|  | 
 | ||||||
|  | pub struct ErrorArea { | ||||||
|  |     base: gtk::Box, | ||||||
|  |     label: gtk::Label, | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl ErrorArea { | ||||||
|  |     pub fn new() -> Self { | ||||||
|  |         let base = gtk::Box::new(gtk::Orientation::Horizontal, 0); | ||||||
|  | 
 | ||||||
|  |         let label = gtk::Label::new(None); | ||||||
|  |         label.set_line_wrap(true); | ||||||
|  |         let error_image = gtk::Image::new_from_icon_name("dialog-error", | ||||||
|  |                                                          gtk_sys::GTK_ICON_SIZE_DIALOG as i32); | ||||||
|  |         base.pack_start(&error_image, false, true, 10); | ||||||
|  |         base.pack_start(&label, true, true, 1); | ||||||
|  | 
 | ||||||
|  |         ErrorArea { base, label } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn show_nvim_start_error(&self, err: &str, cmd: &str) { | ||||||
|  |         error!("Can't start nvim: {}\nCommand line: {}", err, cmd); | ||||||
|  |         self.label.set_markup(&format!("<big>Can't start nvim instance:</big>\n\ | ||||||
|  |                                        <i>{}</i>\n\ | ||||||
|  |                                        <span foreground=\"red\"><i>{}</i></span>\n\n\ | ||||||
|  |                                        <big>Possible error reasons:</big>\n\ | ||||||
|  |                                        ● Not supported nvim version (minimum supported version is <b>{}</b>)\n\ | ||||||
|  |                                        ● Error in configuration file (init.vim or ginit.vim)\n\ | ||||||
|  |                                        ● Wrong nvim binary path \ | ||||||
|  |                                        (right path can be passed with <i>--nvim-bin-path=path_here</i> option)", 
 | ||||||
|  |                                        encode_minimal(cmd), encode_minimal(err), shell::MINIMUM_SUPPORTED_NVIM_VERSION)); | ||||||
|  |         self.base.show_all(); | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl Deref for ErrorArea { | ||||||
|  |     type Target = gtk::Box; | ||||||
|  | 
 | ||||||
|  |     fn deref(&self) -> >k::Box { | ||||||
|  |         &self.base | ||||||
|  |     } | ||||||
|  | } | ||||||
| @ -31,6 +31,7 @@ mod shell_dlg; | |||||||
| mod popup_menu; | mod popup_menu; | ||||||
| mod project; | mod project; | ||||||
| mod tabline; | mod tabline; | ||||||
|  | mod error; | ||||||
| 
 | 
 | ||||||
| use std::env; | use std::env; | ||||||
| use gio::ApplicationExt; | use gio::ApplicationExt; | ||||||
|  | |||||||
							
								
								
									
										145
									
								
								src/nvim.rs
									
									
									
									
									
								
							
							
						
						
									
										145
									
								
								src/nvim.rs
									
									
									
									
									
								
							| @ -1,8 +1,10 @@ | |||||||
| use std::io::{Result, Error, ErrorKind}; | use std::error; | ||||||
|  | use std::fmt; | ||||||
| use std::env; | use std::env; | ||||||
| use std::process::{Stdio, Command}; | use std::process::{Stdio, Command}; | ||||||
| use std::result; | use std::result; | ||||||
| use std::sync::Arc; | use std::sync::Arc; | ||||||
|  | use std::ops::{Deref, DerefMut}; | ||||||
| 
 | 
 | ||||||
| use neovim_lib::{Handler, Neovim, NeovimApi, Session, Value, UiAttachOptions, CallError, UiOption}; | use neovim_lib::{Handler, Neovim, NeovimApi, Session, Value, UiAttachOptions, CallError, UiOption}; | ||||||
| use neovim_lib::neovim_api::Tabpage; | use neovim_lib::neovim_api::Tabpage; | ||||||
| @ -76,11 +78,52 @@ macro_rules! try_uint { | |||||||
|     ($exp:expr) => ($exp.as_u64().ok_or("Can't convert argument to u64".to_owned())?) |     ($exp:expr) => ($exp.as_u64().ok_or("Can't convert argument to u64".to_owned())?) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | #[derive(Debug)] | ||||||
|  | pub struct NvimInitError { | ||||||
|  |     source: Box<error::Error>, | ||||||
|  |     cmd: String, | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl NvimInitError { | ||||||
|  |     pub fn new<E>(cmd: &Command, error: E) -> NvimInitError | ||||||
|  |         where E: Into<Box<error::Error>> | ||||||
|  |     { | ||||||
|  |         NvimInitError { | ||||||
|  |             cmd: format!("{:?}", cmd), | ||||||
|  |             source: error.into(), | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn source(&self) -> String { | ||||||
|  |         format!("{}", self.source) | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn cmd(&self) -> &str { | ||||||
|  |         &self.cmd | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl fmt::Display for NvimInitError { | ||||||
|  |     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {        
 | ||||||
|  |         write!(f, "{:?}", self.source) | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl error::Error for NvimInitError { | ||||||
|  |     fn description(&self) -> &str { | ||||||
|  |         "Can't start nvim instance" | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     fn cause(&self) -> Option<&error::Error> { | ||||||
|  |         Some(&*self.source) | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
| pub fn initialize(shell: Arc<UiMutex<shell::State>>, | pub fn initialize(shell: Arc<UiMutex<shell::State>>, | ||||||
|                   nvim_bin_path: Option<&String>, |                   nvim_bin_path: Option<&String>, | ||||||
|                   cols: u64, |                   cols: u64, | ||||||
|                   rows: u64) |                   rows: u64) | ||||||
|                   -> Result<Neovim> { |                   -> result::Result<Neovim, NvimInitError> { | ||||||
|     let mut cmd = if let Some(path) = nvim_bin_path { |     let mut cmd = if let Some(path) = nvim_bin_path { | ||||||
|         Command::new(path) |         Command::new(path) | ||||||
|     } else { |     } else { | ||||||
| @ -108,10 +151,7 @@ pub fn initialize(shell: Arc<UiMutex<shell::State>>, | |||||||
|     let session = Session::new_child_cmd(&mut cmd); |     let session = Session::new_child_cmd(&mut cmd); | ||||||
| 
 | 
 | ||||||
|     let session = match session { |     let session = match session { | ||||||
|         Err(e) => { |         Err(e) => return Err(NvimInitError::new(&cmd, e)), | ||||||
|             println!("Error execute: {:?}", cmd); |  | ||||||
|             return Err(From::from(e)); |  | ||||||
|         } |  | ||||||
|         Ok(s) => s, |         Ok(s) => s, | ||||||
|     }; |     }; | ||||||
| 
 | 
 | ||||||
| @ -123,9 +163,9 @@ pub fn initialize(shell: Arc<UiMutex<shell::State>>, | |||||||
|     opts.set_popupmenu_external(false); |     opts.set_popupmenu_external(false); | ||||||
|     opts.set_tabline_external(true); |     opts.set_tabline_external(true); | ||||||
|     nvim.ui_attach(cols, rows, opts) |     nvim.ui_attach(cols, rows, opts) | ||||||
|         .map_err(|e| Error::new(ErrorKind::Other, e))?; |         .map_err(|e| NvimInitError::new(&cmd, e))?; | ||||||
|     nvim.command("runtime! ginit.vim") |     nvim.command("runtime! ginit.vim") | ||||||
|         .map_err(|e| Error::new(ErrorKind::Other, e))?; |         .map_err(|e| NvimInitError::new(&cmd, e))?; | ||||||
| 
 | 
 | ||||||
|     Ok(nvim) |     Ok(nvim) | ||||||
| } | } | ||||||
| @ -372,6 +412,95 @@ impl RepaintMode { | |||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | 
 | ||||||
|  | enum NeovimClientWrapper { | ||||||
|  |     Uninitialized, | ||||||
|  |     Initialized(Neovim), | ||||||
|  |     Error, | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl NeovimClientWrapper { | ||||||
|  |     pub fn is_initialized(&self) -> bool { | ||||||
|  |         match *self { | ||||||
|  |             NeovimClientWrapper::Initialized(_) => true, | ||||||
|  |             _ => false, | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn is_error(&self) -> bool { | ||||||
|  |         match *self { | ||||||
|  |             NeovimClientWrapper::Error => true, | ||||||
|  |             _ => false, | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn nvim(&self) -> &Neovim { | ||||||
|  |         match *self { | ||||||
|  |             NeovimClientWrapper::Initialized(ref nvim) => nvim, | ||||||
|  |             NeovimClientWrapper::Uninitialized => panic!("Access to uninitialized neovim client"), | ||||||
|  |             NeovimClientWrapper::Error => panic!("Access to neovim client that is not started due to some error"), | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn nvim_mut(&mut self) -> &mut Neovim { | ||||||
|  |         match *self { | ||||||
|  |             NeovimClientWrapper::Initialized(ref mut nvim) => nvim, | ||||||
|  |             NeovimClientWrapper::Uninitialized => panic!("Access to uninitialized neovim client"), | ||||||
|  |             NeovimClientWrapper::Error => panic!("Access to neovim client that is not started due to some error"), | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | pub struct NeovimClient { | ||||||
|  |     nvim: NeovimClientWrapper | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl NeovimClient { | ||||||
|  |     pub fn new() -> Self { | ||||||
|  |         NeovimClient { 
 | ||||||
|  |             nvim: NeovimClientWrapper::Uninitialized, | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn set_nvim(&mut self, nvim: Neovim) { | ||||||
|  |         self.nvim = NeovimClientWrapper::Initialized(nvim); | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn set_error(&mut self) { | ||||||
|  |         self.nvim = NeovimClientWrapper::Error; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn is_initialized(&self) -> bool { | ||||||
|  |         self.nvim.is_initialized() | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn is_error(&self) -> bool { | ||||||
|  |         self.nvim.is_error() | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn nvim(&self) -> &Neovim { | ||||||
|  |         self.nvim.nvim() | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     pub fn nvim_mut(&mut self) -> &mut Neovim { | ||||||
|  |         self.nvim.nvim_mut() | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl Deref for NeovimClient { | ||||||
|  |     type Target = Neovim; | ||||||
|  | 
 | ||||||
|  |     fn deref(&self) -> &Neovim { | ||||||
|  |         self.nvim() | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl DerefMut for NeovimClient { | ||||||
|  |     fn deref_mut(&mut self) -> &mut Neovim { | ||||||
|  |         self.nvim_mut() | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
| #[cfg(test)] | #[cfg(test)] | ||||||
| mod tests { | mod tests { | ||||||
|     use super::*; |     use super::*; | ||||||
|  | |||||||
| @ -9,6 +9,7 @@ use gdk::{EventButton, EventType}; | |||||||
| 
 | 
 | ||||||
| use neovim_lib::{Neovim, NeovimApi}; | use neovim_lib::{Neovim, NeovimApi}; | ||||||
| 
 | 
 | ||||||
|  | use nvim; | ||||||
| use nvim::ErrorReport; | use nvim::ErrorReport; | ||||||
| use shell; | use shell; | ||||||
| use input; | use input; | ||||||
| @ -16,7 +17,7 @@ use input; | |||||||
| const MAX_VISIBLE_ROWS: i32 = 10; | const MAX_VISIBLE_ROWS: i32 = 10; | ||||||
| 
 | 
 | ||||||
| struct State { | struct State { | ||||||
|     nvim: Option<Rc<RefCell<Neovim>>>, |     nvim: Option<Rc<RefCell<nvim::NeovimClient>>>, | ||||||
|     renderer: gtk::CellRendererText, |     renderer: gtk::CellRendererText, | ||||||
|     tree: gtk::TreeView, |     tree: gtk::TreeView, | ||||||
|     scroll: gtk::ScrolledWindow, |     scroll: gtk::ScrolledWindow, | ||||||
|  | |||||||
							
								
								
									
										87
									
								
								src/shell.rs
									
									
									
									
									
								
							
							
						
						
									
										87
									
								
								src/shell.rs
									
									
									
									
									
								
							| @ -20,19 +20,21 @@ use neovim_lib::neovim_api::Tabpage; | |||||||
| use settings::{Settings, FontSource}; | use settings::{Settings, FontSource}; | ||||||
| use ui_model::{UiModel, Cell, Attrs, Color, ModelRect, COLOR_BLACK, COLOR_WHITE, COLOR_RED}; | use ui_model::{UiModel, Cell, Attrs, Color, ModelRect, COLOR_BLACK, COLOR_WHITE, COLOR_RED}; | ||||||
| use nvim; | use nvim; | ||||||
| use nvim::{RedrawEvents, GuiApi, RepaintMode, ErrorReport}; | use nvim::{RedrawEvents, GuiApi, RepaintMode, ErrorReport, NeovimClient}; | ||||||
| use input; | use input; | ||||||
| use input::keyval_to_input_string; | use input::keyval_to_input_string; | ||||||
| use cursor::Cursor; | use cursor::Cursor; | ||||||
| use ui::UiMutex; | use ui::UiMutex; | ||||||
| use popup_menu::PopupMenu; | use popup_menu::PopupMenu; | ||||||
| use tabline::Tabline; | use tabline::Tabline; | ||||||
|  | use error; | ||||||
| 
 | 
 | ||||||
| const DEFAULT_FONT_NAME: &'static str = "DejaVu Sans Mono 12"; | const DEFAULT_FONT_NAME: &str = "DejaVu Sans Mono 12"; | ||||||
|  | pub const MINIMUM_SUPPORTED_NVIM_VERSION: &str = "0.2"; | ||||||
| 
 | 
 | ||||||
| macro_rules! idle_cb_call { | macro_rules! idle_cb_call { | ||||||
|     ($state:ident.$cb:ident($( $x:expr ),*)) => ( |     ($state:ident.$cb:ident($( $x:expr ),*)) => ( | ||||||
|             glib::idle_add(move || { |             gtk::idle_add(move || { | ||||||
|                                if let Some(ref cb) = $state.borrow().$cb { |                                if let Some(ref cb) = $state.borrow().$cb { | ||||||
|                                    (&mut *cb.borrow_mut())($($x),*); |                                    (&mut *cb.borrow_mut())($($x),*); | ||||||
|                                } |                                } | ||||||
| @ -58,14 +60,16 @@ pub struct State { | |||||||
|     cur_attrs: Option<Attrs>, |     cur_attrs: Option<Attrs>, | ||||||
|     pub mode: NvimMode, |     pub mode: NvimMode, | ||||||
|     mouse_enabled: bool, |     mouse_enabled: bool, | ||||||
|     nvim: Option<Rc<RefCell<Neovim>>>, |     nvim: Rc<RefCell<NeovimClient>>, | ||||||
|     font_desc: FontDescription, |     font_desc: FontDescription, | ||||||
|     cursor: Option<Cursor>, |     cursor: Option<Cursor>, | ||||||
|     popup_menu: RefCell<PopupMenu>, |     popup_menu: RefCell<PopupMenu>, | ||||||
|     settings: Rc<RefCell<Settings>>, |     settings: Rc<RefCell<Settings>>, | ||||||
| 
 | 
 | ||||||
|  |     stack: gtk::Stack, | ||||||
|     drawing_area: gtk::DrawingArea, |     drawing_area: gtk::DrawingArea, | ||||||
|     tabs: Tabline, |     tabs: Tabline, | ||||||
|  |     error_area: error::ErrorArea, | ||||||
| 
 | 
 | ||||||
|     line_height: Option<f64>, |     line_height: Option<f64>, | ||||||
|     char_width: Option<f64>, |     char_width: Option<f64>, | ||||||
| @ -84,7 +88,7 @@ impl State { | |||||||
| 
 | 
 | ||||||
|         State { |         State { | ||||||
|             model: UiModel::new(1, 1), |             model: UiModel::new(1, 1), | ||||||
|             nvim: None, |             nvim: Rc::new(RefCell::new(NeovimClient::new())), | ||||||
|             cur_attrs: None, |             cur_attrs: None, | ||||||
|             bg_color: COLOR_BLACK, |             bg_color: COLOR_BLACK, | ||||||
|             fg_color: COLOR_WHITE, |             fg_color: COLOR_WHITE, | ||||||
| @ -96,8 +100,10 @@ impl State { | |||||||
|             popup_menu, |             popup_menu, | ||||||
|             settings: settings, |             settings: settings, | ||||||
| 
 | 
 | ||||||
|  |             stack: gtk::Stack::new(), | ||||||
|             drawing_area, |             drawing_area, | ||||||
|             tabs: Tabline::new(), |             tabs: Tabline::new(), | ||||||
|  |             error_area: error::ErrorArea::new(), | ||||||
| 
 | 
 | ||||||
|             line_height: None, |             line_height: None, | ||||||
|             char_width: None, |             char_width: None, | ||||||
| @ -119,11 +125,11 @@ impl State { | |||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     pub fn nvim(&self) -> RefMut<Neovim> { |     pub fn nvim(&self) -> RefMut<Neovim> { | ||||||
|         self.nvim.as_ref().unwrap().borrow_mut() |         RefMut::map(self.nvim.borrow_mut(), |n| n.nvim_mut()) | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     pub fn nvim_clone(&self) -> Rc<RefCell<Neovim>> { |     pub fn nvim_clone(&self) -> Rc<RefCell<NeovimClient>> { | ||||||
|         self.nvim.as_ref().unwrap().clone() |         self.nvim.clone() | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     pub fn set_detach_cb<F>(&mut self, cb: Option<F>) |     pub fn set_detach_cb<F>(&mut self, cb: Option<F>) | ||||||
| @ -284,14 +290,27 @@ impl Shell { | |||||||
|         shell |         shell | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|  |     pub fn is_nvim_initialized(&self) -> bool { | ||||||
|  |         let state = self.state.borrow(); | ||||||
|  |         let nvim = state.nvim.borrow(); | ||||||
|  |         nvim.is_initialized() | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     pub fn init(&mut self) { |     pub fn init(&mut self) { | ||||||
|         let mut state = self.state.borrow_mut(); |         let mut state = self.state.borrow_mut(); | ||||||
|         state.drawing_area.set_hexpand(true); |         state.drawing_area.set_hexpand(true); | ||||||
|         state.drawing_area.set_vexpand(true); |         state.drawing_area.set_vexpand(true); | ||||||
|         state.drawing_area.set_can_focus(true); |         state.drawing_area.set_can_focus(true); | ||||||
| 
 | 
 | ||||||
|         self.widget.pack_start(&*state.tabs, false, true, 0); |         let nvim_box = gtk::Box::new(gtk::Orientation::Vertical, 0); | ||||||
|         self.widget.pack_start(&state.drawing_area, true, true, 0); | 
 | ||||||
|  |         nvim_box.pack_start(&*state.tabs, false, true, 0); | ||||||
|  |         nvim_box.pack_start(&state.drawing_area, true, true, 0); | ||||||
|  | 
 | ||||||
|  |         state.stack.add_named(&nvim_box, "Nvim"); | ||||||
|  |         state.stack.add_named(&*state.error_area, "Error"); | ||||||
|  | 
 | ||||||
|  |         self.widget.pack_start(&state.stack, true, true, 0); | ||||||
| 
 | 
 | ||||||
|         state |         state | ||||||
|             .drawing_area |             .drawing_area | ||||||
| @ -516,27 +535,45 @@ fn update_line_metrics(state_arc: &Arc<UiMutex<State>>, ctx: &cairo::Context) { | |||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn gtk_draw(state: &Arc<UiMutex<State>>, ctx: &cairo::Context) -> Inhibit { | fn gtk_draw(state_arc: &Arc<UiMutex<State>>, ctx: &cairo::Context) -> Inhibit { | ||||||
|     update_line_metrics(state, ctx); |     update_line_metrics(state_arc, ctx); | ||||||
|     init_nvim(state); |     init_nvim(state_arc); | ||||||
| 
 | 
 | ||||||
|     draw(&*state.borrow(), ctx); |     let mut state = state_arc.borrow_mut(); | ||||||
|     request_window_resize(&mut *state.borrow_mut()); |     // in case nvim not initialized
 | ||||||
|  |     if !state.nvim.borrow().is_error() { | ||||||
|  |         draw(&*state, ctx); | ||||||
|  |         request_window_resize(&mut *state); | ||||||
|  |     } | ||||||
| 
 | 
 | ||||||
|     Inhibit(false) |     Inhibit(false) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| 
 | 
 | ||||||
| fn init_nvim(state_arc: &Arc<UiMutex<State>>) { | fn init_nvim(state_arc: &Arc<UiMutex<State>>) { | ||||||
|     let mut state = state_arc.borrow_mut(); |     let state = state_arc.borrow(); | ||||||
| 
 | 
 | ||||||
|     if state.nvim.is_none() { |     let mut nvim_client = state.nvim.borrow_mut(); | ||||||
|  |     if !nvim_client.is_initialized() && !nvim_client.is_error() { | ||||||
|         let (cols, rows) = state.calc_nvim_size().unwrap(); |         let (cols, rows) = state.calc_nvim_size().unwrap(); | ||||||
|         let mut nvim = nvim::initialize(state_arc.clone(), |         let mut nvim = match nvim::initialize(state_arc.clone(), | ||||||
|                                               state.options.nvim_bin_path.as_ref(), |                                               state.options.nvim_bin_path.as_ref(), | ||||||
|                                               cols as u64, |                                               cols as u64, | ||||||
|                                         rows as u64) |                                               rows as u64) { | ||||||
|                 .expect("Can't start nvim instance"); |             Ok(nvim) => nvim, | ||||||
|  |             Err(err) => { | ||||||
|  |                 nvim_client.set_error(); | ||||||
|  |                 state.error_area.show_nvim_start_error(&err.source(), err.cmd()); | ||||||
|  | 
 | ||||||
|  |                 let stack = state.stack.clone(); | ||||||
|  |                 gtk::idle_add(move || { | ||||||
|  |                                   stack.set_visible_child_name("Error"); | ||||||
|  |                                   Continue(false) | ||||||
|  |                               }); | ||||||
|  | 
 | ||||||
|  |                 return; | ||||||
|  |             } | ||||||
|  |         }; | ||||||
| 
 | 
 | ||||||
|         if let Some(ref path) = state.options.open_path { |         if let Some(ref path) = state.options.open_path { | ||||||
|             nvim.command(&format!("e {}", path)).report_err(&mut nvim); |             nvim.command(&format!("e {}", path)).report_err(&mut nvim); | ||||||
| @ -551,7 +588,7 @@ fn init_nvim(state_arc: &Arc<UiMutex<State>>) { | |||||||
|                           idle_cb_call!(state_ref.detach_cb()); |                           idle_cb_call!(state_ref.detach_cb()); | ||||||
|                       }); |                       }); | ||||||
| 
 | 
 | ||||||
|         state.nvim = Some(Rc::new(RefCell::new(nvim))); |         nvim_client.set_nvim(nvim); | ||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -783,6 +820,11 @@ fn gtk_configure_event(state: &Arc<UiMutex<State>>, _: &EventConfigure) -> bool | |||||||
|     if let Some(timer) = state_ref.resize_timer { |     if let Some(timer) = state_ref.resize_timer { | ||||||
|         glib::source_remove(timer); |         glib::source_remove(timer); | ||||||
|     } |     } | ||||||
|  | 
 | ||||||
|  |     if !state_ref.nvim.borrow().is_initialized() { | ||||||
|  |         return false; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     if let Some((columns, rows)) = state_ref.calc_nvim_size() { |     if let Some((columns, rows)) = state_ref.calc_nvim_size() { | ||||||
|         let state = state.clone(); |         let state = state.clone(); | ||||||
|         state_ref.resize_timer = Some(glib::timeout_add(250, move || { |         state_ref.resize_timer = Some(glib::timeout_add(250, move || { | ||||||
| @ -967,8 +1009,7 @@ impl RedrawEvents for State { | |||||||
|                       selected: Tabpage, |                       selected: Tabpage, | ||||||
|                       tabs: Vec<(Tabpage, Option<&str>)>) |                       tabs: Vec<(Tabpage, Option<&str>)>) | ||||||
|                       -> RepaintMode { |                       -> RepaintMode { | ||||||
|         self.tabs |         self.tabs.update_tabs(&self.nvim, &selected, &tabs); | ||||||
|             .update_tabs(&self.nvim.as_ref().unwrap(), &selected, &tabs); |  | ||||||
| 
 | 
 | ||||||
|         RepaintMode::Nothing |         RepaintMode::Nothing | ||||||
|     } |     } | ||||||
|  | |||||||
| @ -7,15 +7,16 @@ use gtk::prelude::*; | |||||||
| 
 | 
 | ||||||
| use glib::signal; | use glib::signal; | ||||||
| 
 | 
 | ||||||
| use neovim_lib::{Neovim, NeovimApi}; | use neovim_lib::NeovimApi; | ||||||
| use neovim_lib::neovim_api::Tabpage; | use neovim_lib::neovim_api::Tabpage; | ||||||
| 
 | 
 | ||||||
|  | use nvim; | ||||||
| use nvim::ErrorReport; | use nvim::ErrorReport; | ||||||
| 
 | 
 | ||||||
| struct State { | struct State { | ||||||
|     data: Vec<Tabpage>, |     data: Vec<Tabpage>, | ||||||
|     selected: Option<Tabpage>, |     selected: Option<Tabpage>, | ||||||
|     nvim: Option<Rc<RefCell<Neovim>>>, |     nvim: Option<Rc<RefCell<nvim::NeovimClient>>>, | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| impl State { | impl State { | ||||||
| @ -31,7 +32,7 @@ impl State { | |||||||
|         let target = &self.data[idx as usize]; |         let target = &self.data[idx as usize]; | ||||||
|         if Some(target) != self.selected.as_ref() { |         if Some(target) != self.selected.as_ref() { | ||||||
|             let mut nvim = self.nvim.as_ref().unwrap().borrow_mut(); |             let mut nvim = self.nvim.as_ref().unwrap().borrow_mut(); | ||||||
|             nvim.set_current_tabpage(&target).report_err(&mut *nvim); |             nvim.set_current_tabpage(&target).report_err(&mut **nvim); | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| } | } | ||||||
| @ -66,7 +67,7 @@ impl Tabline { | |||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     fn update_state(&self, |     fn update_state(&self, | ||||||
|                     nvim: &Rc<RefCell<Neovim>>, |                     nvim: &Rc<RefCell<nvim::NeovimClient>>, | ||||||
|                     selected: &Tabpage, |                     selected: &Tabpage, | ||||||
|                     tabs: &Vec<(Tabpage, Option<&str>)>) { |                     tabs: &Vec<(Tabpage, Option<&str>)>) { | ||||||
|         let mut state = self.state.borrow_mut(); |         let mut state = self.state.borrow_mut(); | ||||||
| @ -81,7 +82,7 @@ impl Tabline { | |||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     pub fn update_tabs(&self, |     pub fn update_tabs(&self, | ||||||
|                        nvim: &Rc<RefCell<Neovim>>, |                        nvim: &Rc<RefCell<nvim::NeovimClient>>, | ||||||
|                        selected: &Tabpage, |                        selected: &Tabpage, | ||||||
|                        tabs: &Vec<(Tabpage, Option<&str>)>) { |                        tabs: &Vec<(Tabpage, Option<&str>)>) { | ||||||
|         if tabs.len() <= 1 { |         if tabs.len() <= 1 { | ||||||
|  | |||||||
| @ -159,6 +159,10 @@ fn on_help_about(comps: &Components) { | |||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn gtk_delete(comps: &UiMutex<Components>, shell: &RefCell<Shell>) -> Inhibit { | fn gtk_delete(comps: &UiMutex<Components>, shell: &RefCell<Shell>) -> Inhibit { | ||||||
|  |     if !shell.borrow().is_nvim_initialized() { | ||||||
|  |         return Inhibit(false); | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     Inhibit(if shell_dlg::can_close_window(comps, shell) { |     Inhibit(if shell_dlg::can_close_window(comps, shell) { | ||||||
|                 let comps = comps.borrow(); |                 let comps = comps.borrow(); | ||||||
|                 comps.close_window(); |                 comps.close_window(); | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user
	 daa84
						daa84