Set cursor color from theme and xor it with text
This commit is contained in:
		
							parent
							
								
									bda35efe88
								
							
						
					
					
						commit
						8216cfb2b1
					
				| @ -536,7 +536,7 @@ fn gtk_draw(ctx: &cairo::Context, state: &Arc<UiMutex<State>>) -> Inhibit { | |||||||
|         ctx.translate(0.0, (gap / 2) as f64); |         ctx.translate(0.0, (gap / 2) as f64); | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     render::clear(ctx, &render_state.color_model); |     render::clear(ctx); | ||||||
| 
 | 
 | ||||||
|     if let Some(block) = block { |     if let Some(block) = block { | ||||||
|         render::render( |         render::render( | ||||||
| @ -559,6 +559,9 @@ fn gtk_draw(ctx: &cairo::Context, state: &Arc<UiMutex<State>>) -> Inhibit { | |||||||
|             &render_state.color_model, |             &render_state.color_model, | ||||||
|         ); |         ); | ||||||
|     } |     } | ||||||
|  | 
 | ||||||
|  |     render::fill_background(ctx, &render_state.color_model); | ||||||
|  | 
 | ||||||
|     Inhibit(false) |     Inhibit(false) | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | |||||||
							
								
								
									
										16
									
								
								src/color.rs
									
									
									
									
									
								
							
							
						
						
									
										16
									
								
								src/color.rs
									
									
									
									
									
								
							| @ -90,14 +90,6 @@ impl ColorModel { | |||||||
|         } |         } | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     pub fn actual_cell_bg<'a>(&'a self, cell: &'a Cell) -> &'a Color { |  | ||||||
|         if !cell.attrs.reverse { |  | ||||||
|             cell.attrs.background.as_ref().unwrap_or(&self.bg_color) |  | ||||||
|         } else { |  | ||||||
|             cell.attrs.foreground.as_ref().unwrap_or(&self.fg_color) |  | ||||||
|         } |  | ||||||
|     } |  | ||||||
| 
 |  | ||||||
|     #[inline] |     #[inline] | ||||||
|     pub fn actual_cell_sp<'a>(&'a self, cell: &'a Cell) -> &'a Color { |     pub fn actual_cell_sp<'a>(&'a self, cell: &'a Cell) -> &'a Color { | ||||||
|         cell.attrs.special.as_ref().unwrap_or(&self.sp_color) |         cell.attrs.special.as_ref().unwrap_or(&self.sp_color) | ||||||
| @ -134,6 +126,14 @@ impl ColorModel { | |||||||
|             .clone() |             .clone() | ||||||
|             .unwrap_or_else(|| self.fg_color.clone()) |             .unwrap_or_else(|| self.fg_color.clone()) | ||||||
|     } |     } | ||||||
|  | 
 | ||||||
|  |     pub fn cursor_bg(&self) -> Color { | ||||||
|  |         self.theme | ||||||
|  |             .cursor() | ||||||
|  |             .bg | ||||||
|  |             .clone() | ||||||
|  |             .unwrap_or_else(|| self.bg_color.clone()) | ||||||
|  |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| #[cfg(test)] | #[cfg(test)] | ||||||
|  | |||||||
| @ -1,5 +1,5 @@ | |||||||
| use cairo; | use cairo; | ||||||
| use color::Color; | use color; | ||||||
| use ui::UiMutex; | use ui::UiMutex; | ||||||
| use mode; | use mode; | ||||||
| use std::sync::{Arc, Weak}; | use std::sync::{Arc, Weak}; | ||||||
| @ -75,7 +75,7 @@ pub trait Cursor { | |||||||
|         font_ctx: &render::Context, |         font_ctx: &render::Context, | ||||||
|         line_y: f64, |         line_y: f64, | ||||||
|         double_width: bool, |         double_width: bool, | ||||||
|         bg: &Color, |         color: &color::ColorModel, | ||||||
|     ); |     ); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| @ -94,7 +94,7 @@ impl Cursor for EmptyCursor { | |||||||
|         _font_ctx: &render::Context, |         _font_ctx: &render::Context, | ||||||
|         _line_y: f64, |         _line_y: f64, | ||||||
|         _double_width: bool, |         _double_width: bool, | ||||||
|         _bg: &Color, |         _color: &color::ColorModel, | ||||||
|     ) { |     ) { | ||||||
|     } |     } | ||||||
| } | } | ||||||
| @ -165,7 +165,7 @@ impl<CB: CursorRedrawCb> Cursor for BlinkCursor<CB> { | |||||||
|         font_ctx: &render::Context, |         font_ctx: &render::Context, | ||||||
|         line_y: f64, |         line_y: f64, | ||||||
|         double_width: bool, |         double_width: bool, | ||||||
|         bg: &Color, |         color: &color::ColorModel, | ||||||
|     ) { |     ) { | ||||||
|         let state = self.state.borrow(); |         let state = self.state.borrow(); | ||||||
| 
 | 
 | ||||||
| @ -174,7 +174,9 @@ impl<CB: CursorRedrawCb> Cursor for BlinkCursor<CB> { | |||||||
|         } |         } | ||||||
| 
 | 
 | ||||||
|         let current_point = ctx.get_current_point(); |         let current_point = ctx.get_current_point(); | ||||||
|         ctx.set_source_rgba(1.0 - bg.0, 1.0 - bg.1, 1.0 - bg.2, 0.6 * state.alpha.0); | 
 | ||||||
|  |         let bg = color.cursor_bg(); | ||||||
|  |         ctx.set_source_rgba(bg.0, bg.1, bg.2, state.alpha.0); | ||||||
| 
 | 
 | ||||||
|         let (y, width, height) = cursor_rect( |         let (y, width, height) = cursor_rect( | ||||||
|             self.mode_info.as_ref(), |             self.mode_info.as_ref(), | ||||||
|  | |||||||
| @ -16,7 +16,14 @@ use pangocairo; | |||||||
| use cursor::Cursor; | use cursor::Cursor; | ||||||
| use ui_model; | use ui_model; | ||||||
| 
 | 
 | ||||||
| pub fn clear(ctx: &cairo::Context, color_model: &color::ColorModel) { | pub fn clear(ctx: &cairo::Context) { | ||||||
|  |     ctx.set_operator(cairo::Operator::Clear); | ||||||
|  |     ctx.paint(); | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | pub fn fill_background(ctx: &cairo::Context, color_model: &color::ColorModel) { | ||||||
|  |     // must be dest over here
 | ||||||
|  |     //ctx.set_operator(cairo::Operator::DestOver);
 | ||||||
|     ctx.set_source_rgb( |     ctx.set_source_rgb( | ||||||
|         color_model.bg_color.0, |         color_model.bg_color.0, | ||||||
|         color_model.bg_color.1, |         color_model.bg_color.1, | ||||||
| @ -36,6 +43,40 @@ pub fn render<C: Cursor>( | |||||||
|     let &CellMetrics { char_width, .. } = cell_metrics; |     let &CellMetrics { char_width, .. } = cell_metrics; | ||||||
|     let (cursor_row, cursor_col) = ui_model.get_cursor(); |     let (cursor_row, cursor_col) = ui_model.get_cursor(); | ||||||
| 
 | 
 | ||||||
|  |     // draw text
 | ||||||
|  |     ctx.set_operator(cairo::Operator::Source); | ||||||
|  | 
 | ||||||
|  |     for cell_view in ui_model.get_clip_iterator(ctx, cell_metrics) { | ||||||
|  |         let mut line_x = 0.0; | ||||||
|  | 
 | ||||||
|  |         for (col, cell) in cell_view.line.line.iter().enumerate() { | ||||||
|  |             draw_cell(&cell_view, color_model, cell, col, line_x); | ||||||
|  |             draw_underline(&cell_view, color_model, cell, line_x); | ||||||
|  | 
 | ||||||
|  |             line_x += char_width; | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  | 
 | ||||||
|  |     // draw cursor
 | ||||||
|  |     ctx.set_operator(cairo::Operator::Xor); | ||||||
|  |     let (_x1, _y1, x2, y2) = ctx.clip_extents(); | ||||||
|  |     let line_x = cursor_col as f64 * cell_metrics.char_width; | ||||||
|  |     let line_y = cursor_row as f64 * cell_metrics.line_height; | ||||||
|  | 
 | ||||||
|  |     if line_x < x2 && line_y < y2 { | ||||||
|  |         if let Some(cursor_line) = ui_model.model().get(cursor_row) { | ||||||
|  |             let double_width = cursor_line | ||||||
|  |                 .line | ||||||
|  |                 .get(cursor_col + 1) | ||||||
|  |                 .map_or(false, |c| c.attrs.double_width); | ||||||
|  |             ctx.move_to(line_x, line_y); | ||||||
|  |             cursor.draw(ctx, font_ctx, line_y, double_width, &color_model); | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     // draw background
 | ||||||
|  |     ctx.set_operator(cairo::Operator::DestOver); | ||||||
|     for cell_view in ui_model.get_clip_iterator(ctx, cell_metrics) { |     for cell_view in ui_model.get_clip_iterator(ctx, cell_metrics) { | ||||||
|         let mut line_x = 0.0; |         let mut line_x = 0.0; | ||||||
| 
 | 
 | ||||||
| @ -44,35 +85,6 @@ pub fn render<C: Cursor>( | |||||||
|             line_x += char_width; |             line_x += char_width; | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| 
 |  | ||||||
|     for cell_view in ui_model.get_clip_iterator(ctx, cell_metrics) { |  | ||||||
|         let mut line_x = 0.0; |  | ||||||
|         let RowView { |  | ||||||
|             line, row, line_y, .. |  | ||||||
|         } = cell_view; |  | ||||||
| 
 |  | ||||||
|         for (col, cell) in line.line.iter().enumerate() { |  | ||||||
|             draw_cell(&cell_view, color_model, cell, col, line_x); |  | ||||||
| 
 |  | ||||||
|             draw_underline(&cell_view, color_model, cell, line_x); |  | ||||||
| 
 |  | ||||||
|             if row == cursor_row && col == cursor_col { |  | ||||||
|                 let double_width = line.line |  | ||||||
|                     .get(col + 1) |  | ||||||
|                     .map_or(false, |c| c.attrs.double_width); |  | ||||||
|                 ctx.move_to(line_x, line_y); |  | ||||||
|                 cursor.draw( |  | ||||||
|                     ctx, |  | ||||||
|                     font_ctx, |  | ||||||
|                     line_y, |  | ||||||
|                     double_width, |  | ||||||
|                     color_model.actual_cell_bg(cell), |  | ||||||
|                 ); |  | ||||||
|             } |  | ||||||
| 
 |  | ||||||
|             line_x += char_width; |  | ||||||
|         } |  | ||||||
|     } |  | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn draw_underline( | fn draw_underline( | ||||||
| @ -104,7 +116,13 @@ fn draw_underline( | |||||||
|             let undercurl_height = (underline_thickness * 4.0).min(max_undercurl_height); |             let undercurl_height = (underline_thickness * 4.0).min(max_undercurl_height); | ||||||
|             let undercurl_y = line_y + underline_position - undercurl_height / 2.0; |             let undercurl_y = line_y + underline_position - undercurl_height / 2.0; | ||||||
| 
 | 
 | ||||||
|             pangocairo::functions::show_error_underline(ctx, line_x, undercurl_y, char_width, undercurl_height); |             pangocairo::functions::show_error_underline( | ||||||
|  |                 ctx, | ||||||
|  |                 line_x, | ||||||
|  |                 undercurl_y, | ||||||
|  |                 char_width, | ||||||
|  |                 undercurl_height, | ||||||
|  |             ); | ||||||
|         } else if cell.attrs.underline { |         } else if cell.attrs.underline { | ||||||
|             let fg = color_model.actual_cell_fg(cell); |             let fg = color_model.actual_cell_fg(cell); | ||||||
|             ctx.set_source_rgb(fg.0, fg.1, fg.2); |             ctx.set_source_rgb(fg.0, fg.1, fg.2); | ||||||
|  | |||||||
| @ -7,7 +7,6 @@ use super::context::CellMetrics; | |||||||
| use ui_model; | use ui_model; | ||||||
| 
 | 
 | ||||||
| pub struct RowView<'a> { | pub struct RowView<'a> { | ||||||
|     pub row: usize, |  | ||||||
|     pub line: &'a ui_model::Line, |     pub line: &'a ui_model::Line, | ||||||
|     pub cell_metrics: &'a CellMetrics, |     pub cell_metrics: &'a CellMetrics, | ||||||
|     pub line_y: f64, |     pub line_y: f64, | ||||||
| @ -24,7 +23,6 @@ impl<'a> RowView<'a> { | |||||||
|         RowView { |         RowView { | ||||||
|             line, |             line, | ||||||
|             line_y: row as f64 * cell_metrics.line_height, |             line_y: row as f64 * cell_metrics.line_height, | ||||||
|             row, |  | ||||||
|             cell_metrics, |             cell_metrics, | ||||||
|             ctx, |             ctx, | ||||||
|         } |         } | ||||||
|  | |||||||
| @ -957,7 +957,7 @@ fn gtk_draw_double_buffer(state: &State, ctx: &cairo::Context) { | |||||||
|     buf_ctx.clip(); |     buf_ctx.clip(); | ||||||
| 
 | 
 | ||||||
|     let render_state = state.render_state.borrow(); |     let render_state = state.render_state.borrow(); | ||||||
|     render::clear(buf_ctx, &render_state.color_model); |     render::clear(buf_ctx); | ||||||
|     render::render( |     render::render( | ||||||
|         &buf_ctx, |         &buf_ctx, | ||||||
|         state.cursor.as_ref().unwrap(), |         state.cursor.as_ref().unwrap(), | ||||||
| @ -965,6 +965,7 @@ fn gtk_draw_double_buffer(state: &State, ctx: &cairo::Context) { | |||||||
|         &state.model, |         &state.model, | ||||||
|         &render_state.color_model, |         &render_state.color_model, | ||||||
|     ); |     ); | ||||||
|  |     render::fill_background(buf_ctx, &render_state.color_model); | ||||||
| 
 | 
 | ||||||
|     ctx.set_source_surface(&surface.surface, 0.0, 0.0); |     ctx.set_source_surface(&surface.surface, 0.0, 0.0); | ||||||
|     ctx.paint(); |     ctx.paint(); | ||||||
| @ -973,7 +974,7 @@ fn gtk_draw_double_buffer(state: &State, ctx: &cairo::Context) { | |||||||
| 
 | 
 | ||||||
| fn gtk_draw_direct(state: &State, ctx: &cairo::Context) { | fn gtk_draw_direct(state: &State, ctx: &cairo::Context) { | ||||||
|     let render_state = state.render_state.borrow(); |     let render_state = state.render_state.borrow(); | ||||||
|     render::clear(ctx, &render_state.color_model); |     render::clear(ctx); | ||||||
|     render::render( |     render::render( | ||||||
|         ctx, |         ctx, | ||||||
|         state.cursor.as_ref().unwrap(), |         state.cursor.as_ref().unwrap(), | ||||||
| @ -981,6 +982,7 @@ fn gtk_draw_direct(state: &State, ctx: &cairo::Context) { | |||||||
|         &state.model, |         &state.model, | ||||||
|         &render_state.color_model, |         &render_state.color_model, | ||||||
|     ); |     ); | ||||||
|  |     render::fill_background(ctx, &render_state.color_model); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| fn gtk_draw(state_arc: &Arc<UiMutex<State>>, ctx: &cairo::Context) -> Inhibit { | fn gtk_draw(state_arc: &Arc<UiMutex<State>>, ctx: &cairo::Context) -> Inhibit { | ||||||
| @ -1153,7 +1155,7 @@ fn draw_initializing(state: &State, ctx: &cairo::Context) { | |||||||
|         &render_state.font_ctx, |         &render_state.font_ctx, | ||||||
|         y, |         y, | ||||||
|         false, |         false, | ||||||
|         &color_model.bg_color, |         &color_model, | ||||||
|     ); |     ); | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | |||||||
							
								
								
									
										22
									
								
								src/theme.rs
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								src/theme.rs
									
									
									
									
									
								
							| @ -13,12 +13,14 @@ use value::ValueMapExt; | |||||||
| 
 | 
 | ||||||
| struct State { | struct State { | ||||||
|     pmenu: Pmenu, |     pmenu: Pmenu, | ||||||
|  |     cursor: Cursor, | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
| impl State { | impl State { | ||||||
|     fn new() -> Self { |     fn new() -> Self { | ||||||
|         State { |         State { | ||||||
|             pmenu: Pmenu::new(), |             pmenu: Pmenu::new(), | ||||||
|  |             cursor: Cursor::new(), | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| } | } | ||||||
| @ -38,7 +40,15 @@ impl Theme { | |||||||
|         Ref::map(self.state.borrow(), |s| &s.pmenu) |         Ref::map(self.state.borrow(), |s| &s.pmenu) | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|  |     pub fn cursor(&self) -> Ref<Cursor> { | ||||||
|  |         Ref::map(self.state.borrow(), |s| &s.cursor) | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|     pub fn queue_update(&self, nvim: &mut Neovim) { |     pub fn queue_update(&self, nvim: &mut Neovim) { | ||||||
|  |         self.get_hl(nvim, "Cursor", |state, bg, _fg| { | ||||||
|  |             state.cursor.bg = bg; | ||||||
|  |         }); | ||||||
|  | 
 | ||||||
|         self.get_hl(nvim, "Pmenu", |state, bg, fg| { |         self.get_hl(nvim, "Pmenu", |state, bg, fg| { | ||||||
|             state.pmenu.bg = bg; |             state.pmenu.bg = bg; | ||||||
|             state.pmenu.fg = fg; |             state.pmenu.fg = fg; | ||||||
| @ -70,6 +80,18 @@ impl Theme { | |||||||
|     } |     } | ||||||
| } | } | ||||||
| 
 | 
 | ||||||
|  | pub struct Cursor { | ||||||
|  |     pub bg: Option<Color>, | ||||||
|  | } | ||||||
|  | 
 | ||||||
|  | impl Cursor { | ||||||
|  |     pub fn new() -> Self { | ||||||
|  |         Cursor {  
 | ||||||
|  |             bg: None, | ||||||
|  |         } | ||||||
|  |     } | ||||||
|  | } | ||||||
|  | 
 | ||||||
| pub struct Pmenu { | pub struct Pmenu { | ||||||
|     pub bg: Option<Color>, |     pub bg: Option<Color>, | ||||||
|     pub fg: Option<Color>, |     pub fg: Option<Color>, | ||||||
|  | |||||||
		Loading…
	
		Reference in New Issue
	
	Block a user
	 daa
						daa