Fixed unix code after refactoring windows cursor, input, rawscreen, alternate screen

This commit is contained in:
Timon 2018-07-28 08:37:21 +00:00
parent c7603fe79d
commit 8f160713bb
8 changed files with 69 additions and 86 deletions

View File

@ -6,7 +6,6 @@ use std::sync::mpsc;
use std::thread; use std::thread;
use super::super::kernel::unix_kernel::terminal::{get_tty, read_char}; use super::super::kernel::unix_kernel::terminal::{get_tty, read_char};
use super::super::terminal::terminal;
use super::{AsyncReader, ITerminalInput, Key}; use super::{AsyncReader, ITerminalInput, Key};
use ScreenManager; use ScreenManager;
pub struct UnixInput; pub struct UnixInput;

View File

@ -45,11 +45,11 @@ pub fn terminal_size() -> (u16, u16) {
use std::time::{SystemTime, Duration}; use std::time::{SystemTime, Duration};
use std::io::ErrorKind; use std::io::ErrorKind;
use Crossterm; use Terminal;
use std::io::Read; use std::io::Read;
/// Get the current cursor position. /// Get the current cursor position.
pub fn pos(context: Rc<Context>) -> (u16, u16) { pub fn pos() -> (u16, u16) {
let crossterm = Crossterm::from(context.clone()); let crossterm = Terminal::new();
let input = crossterm.input(); let input = crossterm.input();
let delimiter = b'R'; let delimiter = b'R';
@ -58,7 +58,7 @@ pub fn pos(context: Rc<Context>) -> (u16, u16) {
// Where is the cursor? // Where is the cursor?
// Use `ESC [ 6 n`. // Use `ESC [ 6 n`.
crossterm.write("\x1B[6n"); // crossterm.write("\x1B[6n");
let mut buf: [u8; 1] = [0]; let mut buf: [u8; 1] = [0];
let mut read_chars = Vec::new(); let mut read_chars = Vec::new();

View File

@ -38,7 +38,7 @@ pub fn save_cursor_pos(screen_manager: &ScreenManager) {
/// get the current cursor position. /// get the current cursor position.
pub fn pos(screen_manager: &ScreenManager) -> (u16, u16) { pub fn pos(screen_manager: &ScreenManager) -> (u16, u16) {
let handle = handle::get_output_handle().unwrap(); let handle = handle::get_current_handle(screen_manager).unwrap();
if let Ok(csbi) = csbi::get_csbi_by_handle(&handle) { if let Ok(csbi) = csbi::get_csbi_by_handle(&handle) {
( csbi.dwCursorPosition.X as u16, csbi.dwCursorPosition.Y as u16 ) ( csbi.dwCursorPosition.X as u16, csbi.dwCursorPosition.Y as u16 )
@ -47,19 +47,6 @@ pub fn pos(screen_manager: &ScreenManager) -> (u16, u16) {
} }
} }
pub fn absolute_cursor_pos(screen_manager: &ScreenManager) -> (u16, u16) {
let handle = handle::get_output_handle().unwrap();
if let Ok(csbi) = csbi::get_csbi_by_handle(&handle) {
(
(csbi.dwMaximumWindowSize.X) as u16,
(csbi.dwMaximumWindowSize.Y) as u16,
)
} else {
return (0, 0);
}
}
/// Set the cursor position to the given x and y. Note that this is 0 based. /// Set the cursor position to the given x and y. Note that this is 0 based.
pub fn set_console_cursor_position(x: i16, y: i16, screen_manager: &ScreenManager) { pub fn set_console_cursor_position(x: i16, y: i16, screen_manager: &ScreenManager) {

View File

@ -1,52 +1,52 @@
////! This module provides easy access to the functionalities of crossterm. //////! This module provides easy access to the functionalities of crossterm.
////! since `crossterm version 0.3.0` an `Context` type is introduced (check that documentation for more info why this type is introduced). //////! since `crossterm version 0.3.0` an `Context` type is introduced (check that documentation for more info why this type is introduced).
////! //////!
////! You have to provide this `Context` to the modules: `cursor::cursor(), color::color(), terminal::terminal()`. //////! You have to provide this `Context` to the modules: `cursor::cursor(), color::color(), terminal::terminal()`.
////! //////!
////! use crossterm::Context; //////! use crossterm::Context;
////! use crossterm::cursor; //////! use crossterm::cursor;
////! use crossterm::color; //////! use crossterm::color;
////! use crossterm::terminal; //////! use crossterm::terminal;
////! //////!
////! let context = Context::new(); //////! let context = Context::new();
////! let cursor = cursor::cursor(&context) //////! let cursor = cursor::cursor(&context)
////! let terminal = terminal::terminal(&context); //////! let terminal = terminal::terminal(&context);
////! let color = terminal::color(&context); //////! let color = terminal::color(&context);
////! //////!
////! Because it can seem a little odd to constantly create an Context and provide it to these modules. //////! Because it can seem a little odd to constantly create an Context and provide it to these modules.
////! You can better use `Crossterm` for accessing these modules. //////! You can better use `Crossterm` for accessing these modules.
////! `Crossterm` handles the Context internally so jo do not have to bother about it, for example: //////! `Crossterm` handles the Context internally so jo do not have to bother about it, for example:
////! //////!
////! let crossterm = Crossterm::new(); //////! let crossterm = Crossterm::new();
////! let color = crossterm.color(); //////! let color = crossterm.color();
////! let cursor = crossterm.cursor(); //////! let cursor = crossterm.cursor();
////! let terminal = crossterm.terminal(); //////! let terminal = crossterm.terminal();
// ////
//use super::super::cursor; ////use super::super::cursor;
//use super::super::input::input; ////use super::super::input::input;
//use super::super::style; ////use super::super::style;
//use super::super::terminal::terminal; ////use super::super::terminal::terminal;
// ////
//use Context; ////use Context;
// ////
//use std::convert::From; ////use std::convert::From;
//use std::fmt::Display; ////use std::fmt::Display;
//use std::mem; ////use std::mem;
//use std::rc::Rc; ////use std::rc::Rc;
//use std::sync::Arc; ////use std::sync::Arc;
// ////
///// Because it can seem a little odd to constantly create an `Context` and provide it to modules like: `cursor, color and terminal`. /////// Because it can seem a little odd to constantly create an `Context` and provide it to modules like: `cursor, color and terminal`.
///// You can better use `Crossterm` for accessing these modules. /////// You can better use `Crossterm` for accessing these modules.
///// `Crossterm` handles the Context internally so jo do not have to bother about it, for example: /////// `Crossterm` handles the Context internally so jo do not have to bother about it, for example:
///// ///////
///// Check `/examples/Crossterm 0.3.0/program_examples/first_depth_search` in the library for more specific examples. /////// Check `/examples/Crossterm 0.3.0/program_examples/first_depth_search` in the library for more specific examples.
///// ///////
///// let crossterm = Crossterm::new(); /////// let crossterm = Crossterm::new();
///// let color = crossterm.color(); /////// let color = crossterm.color();
///// let cursor = crossterm.cursor(); /////// let cursor = crossterm.cursor();
///// let terminal = crossterm.terminal(); /////// let terminal = crossterm.terminal();
pub struct Crossterm { pub struct Crossterm {
// context: Rc<Context>, //// context: Rc<Context>,
} }
// //
///// Create `Crossterm` instance from `Context` ///// Create `Crossterm` instance from `Context`

View File

@ -15,18 +15,18 @@ use kernel::windows_kernel::cursor::{pos, absolute_cursor_pos};
use kernel::unix_kernel::terminal::{exit, pos, terminal_size}; use kernel::unix_kernel::terminal::{exit, pos, terminal_size};
/// Get the terminal size based on the current platform. /// Get the terminal size based on the current platform.
pub fn get_terminal_size(screen_manager: &ScreenManager) -> (u16, u16) { pub fn get_terminal_size() -> (u16, u16) {
#[cfg(unix)] #[cfg(unix)]
return terminal_size(); return terminal_size();
#[cfg(windows)] #[cfg(windows)]
return terminal_size(screen_manager); return terminal_size();
} }
/// Get the cursor position based on the current platform. /// Get the cursor position based on the current platform.
pub fn get_cursor_position(screen_manager: &ScreenManager) -> (u16, u16) { pub fn get_cursor_position(screen_manager: &ScreenManager) -> (u16, u16) {
#[cfg(unix)] #[cfg(unix)]
return pos(screen_manager); return pos();
#[cfg(windows)] #[cfg(windows)]
return pos(screen_manager); return pos(screen_manager);

View File

@ -98,6 +98,7 @@ impl AlternateScreen {
/// By calling this method the current screen will be changed to the alternate screen. /// By calling this method the current screen will be changed to the alternate screen.
/// And you get back an handle for that screen. /// And you get back an handle for that screen.
pub fn new() -> Box<IAlternateScreenCommand> { pub fn new() -> Box<IAlternateScreenCommand> {
#[cfg(target_os = "windows")]
let command = functions::get_module::<Box<IAlternateScreenCommand>>( let command = functions::get_module::<Box<IAlternateScreenCommand>>(
win_commands::ToAlternateScreenBufferCommand::new(), win_commands::ToAlternateScreenBufferCommand::new(),
shared_commands::ToAlternateScreenBufferCommand::new(), shared_commands::ToAlternateScreenBufferCommand::new(),

View File

@ -1,13 +1,13 @@
//! This module contains the commands that can be used for unix systems. //! This module contains the commands that can be used for unix systems.
use super::IStateCommand; use super::{IStateCommand, IRawScreenCommand};
use kernel::unix_kernel::terminal; use kernel::unix_kernel::terminal;
use termios::{tcsetattr, Termios, CREAD, ECHO, ICANON, TCSAFLUSH}; use termios::{tcsetattr, Termios, CREAD, ECHO, ICANON, TCSAFLUSH};
use {CommandManager, Context, StateManager}; use {CommandManager, Context, StateManager};
const FD_STDIN: ::std::os::unix::io::RawFd = 1; const FD_STDIN: ::std::os::unix::io::RawFd = 1;
use std::io::Result; use std::io::{Result,Error, ErrorKind};
use std::rc::Rc; use std::rc::Rc;
use std::sync::Mutex; use std::sync::Mutex;
@ -76,28 +76,24 @@ impl EnableRawModeCommand {
} }
} }
impl EnableRawModeCommand { impl IRawScreenCommand for EnableRawModeCommand {
fn execute(&mut self) -> bool { fn enable(&mut self) -> Result<()> {
if let Ok(original_mode) = self.original_mode { if let Ok(original_mode) = self.original_mode {
let mut new_mode = original_mode; let mut new_mode = original_mode;
terminal::make_raw(&mut new_mode); terminal::make_raw(&mut new_mode);
terminal::set_terminal_mode(&new_mode); terminal::set_terminal_mode(&new_mode);
true
} else { } else {
return false; return Err(Error::new(ErrorKind::Other,"Could not set console mode when enabling raw mode"))
} }
Ok(())
} }
fn undo(&mut self) -> bool { fn disable(&mut self) -> Result<()> {
if let Some(ref original_mode) = self.original_mode { if let Ok(ref original_mode) = self.original_mode {
let result = terminal::set_terminal_mode(&original_mode); let result = terminal::set_terminal_mode(&original_mode)?;
match result {
Ok(()) => true,
Err(_) => false,
}
} else { } else {
return false; return Err(Error::new(ErrorKind::Other,"Could not set console mode when enabling raw mode"))
} }
Ok(())
} }
} }

View File

@ -37,7 +37,7 @@ impl ITerminal for AnsiTerminal {
} }
fn terminal_size(&self, screen_manager: &ScreenManager) -> (u16, u16) { fn terminal_size(&self, screen_manager: &ScreenManager) -> (u16, u16) {
functions::get_terminal_size(&self.context.screen_manager) functions::get_terminal_size()
} }
fn scroll_up(&self, count: i16, screen_manager: &ScreenManager) { fn scroll_up(&self, count: i16, screen_manager: &ScreenManager) {