Removed downcast for HANDLE WinAPi. Also we do not need to keep track of current HANDLE since this will now be gotton from CreateFileW
This commit is contained in:
parent
c848beb721
commit
cc55c190d8
@ -19,19 +19,6 @@ use std::io::Write;
|
||||
use std::{thread,time};
|
||||
fn main()
|
||||
{
|
||||
use crossterm::screen::RawScreen;
|
||||
use crossterm::Screen;
|
||||
|
||||
let mut screen = Screen::new(true);
|
||||
|
||||
cursor::goto();
|
||||
|
||||
// write!(screen, "text \n\r");
|
||||
let a = screen.enable_alternate_modes(true).unwrap();
|
||||
// cursor::goto();
|
||||
terminal::raw_mode::print_wait_screen_on_alternate_window();
|
||||
thread::sleep(time::Duration::from_millis(2000));
|
||||
drop(a);
|
||||
cursor::goto();
|
||||
//
|
||||
// write!(a, "text \n\r");
|
||||
}
|
||||
|
@ -25,14 +25,10 @@ fn main()
|
||||
/// run the program
|
||||
pub fn run()
|
||||
{
|
||||
print_welcome_screen();
|
||||
|
||||
// This is represents the current screen.
|
||||
let screen = Screen::new(true);
|
||||
|
||||
// set size of terminal so the map we are going to draw is fitting the screen.
|
||||
terminal(&screen).set_size(60,110);
|
||||
|
||||
print_welcome_screen(&screen);
|
||||
|
||||
start_algorithm(&screen);
|
||||
drop(screen);
|
||||
}
|
||||
@ -56,8 +52,9 @@ fn start_algorithm(screen: &Screen)
|
||||
}
|
||||
}
|
||||
|
||||
fn print_welcome_screen(screen: &Screen)
|
||||
fn print_welcome_screen()
|
||||
{
|
||||
let screen = Screen::default();
|
||||
let crossterm = Crossterm::new(&screen);
|
||||
|
||||
// create the handle for the cursor and terminal.
|
||||
@ -65,17 +62,20 @@ fn print_welcome_screen(screen: &Screen)
|
||||
let cursor = crossterm.cursor();
|
||||
let input = crossterm.input();
|
||||
|
||||
// set size of terminal so the map we are going to draw is fitting the screen.
|
||||
terminal.set_size(60,110);
|
||||
|
||||
// clear the screen and print the welcome message.
|
||||
terminal.clear(ClearType::All);
|
||||
cursor.goto(0, 0);
|
||||
terminal.write(WELCOME_MESSAGE.join("\n\r"));
|
||||
terminal.write(WELCOME_MESSAGE.join("\r\n"));
|
||||
|
||||
cursor.hide();
|
||||
cursor.goto(0, 10);
|
||||
terminal.write("The first depth search algorithm will start in: Seconds");
|
||||
|
||||
cursor.goto(0, 11);
|
||||
terminal.write("\nPress `q` to abort the program");
|
||||
terminal.write("Press `q` to abort the program");
|
||||
|
||||
let mut stdin = input.read_async().bytes();
|
||||
|
||||
|
@ -73,14 +73,10 @@ fn main() {
|
||||
|
||||
snake.draw_snake(&screen);
|
||||
|
||||
|
||||
|
||||
if snake.has_eaten_food(map.foot_pos)
|
||||
{
|
||||
map.spawn_food(&free_positions, &screen);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
}
|
||||
game_over_screen();
|
||||
|
@ -7,20 +7,21 @@ use crossterm::style::{style, Color};
|
||||
use std::io::{stdout, Write};
|
||||
use std::{thread, time};
|
||||
|
||||
fn print_wait_screen(screen: &Screen) {
|
||||
fn print_wait_screen(screen: &mut Screen) {
|
||||
let crossterm = Crossterm::new(screen);
|
||||
let terminal = crossterm.terminal();
|
||||
let cursor = crossterm.cursor();
|
||||
|
||||
terminal.clear(ClearType::All);
|
||||
cursor.goto(0, 0);
|
||||
cursor.hide();
|
||||
|
||||
terminal.write(
|
||||
"Welcome to the wait screen.\n\
|
||||
Please wait a few seconds until we arrive back at the main screen.\n\
|
||||
Progress: ",
|
||||
);
|
||||
cursor.hide();
|
||||
cursor.goto(0, 0);
|
||||
screen.write(b"Welcome to the wait screen.");
|
||||
cursor.goto(0, 1);
|
||||
screen.write(b"Please wait a few seconds until we arrive back at the main screen.");
|
||||
cursor.goto(0, 2);
|
||||
screen.write(b"Progress:");
|
||||
cursor.goto(0, 3);
|
||||
|
||||
// print some progress example.
|
||||
for i in 1..5 {
|
||||
@ -37,9 +38,9 @@ fn print_wait_screen(screen: &Screen) {
|
||||
pub fn print_wait_screen_on_alternate_window() {
|
||||
let screen = Screen::default();
|
||||
|
||||
if let Ok(alternate) = screen.enable_alternate_modes(true)
|
||||
if let Ok(ref mut alternate) = screen.enable_alternate_modes(true)
|
||||
{
|
||||
print_wait_screen(&alternate.screen);
|
||||
print_wait_screen(&mut alternate.screen);
|
||||
}
|
||||
|
||||
println!("Whe are back at the main screen");
|
||||
|
@ -88,7 +88,7 @@ impl RawModeCommand {
|
||||
/// Enables raw mode.
|
||||
pub fn enable(&mut self) -> Result<()> {
|
||||
let mut dw_mode: DWORD = 0;
|
||||
let stdout = handle::get_current_handle_1().unwrap();
|
||||
let stdout = handle::get_current_handle().unwrap();
|
||||
|
||||
if !kernel::get_console_mode(&stdout, &mut dw_mode) {
|
||||
return Err(Error::new(
|
||||
@ -111,7 +111,7 @@ impl RawModeCommand {
|
||||
|
||||
/// Disables raw mode.
|
||||
pub fn disable(&self) -> Result<()> {
|
||||
let stdout = handle::get_current_handle_1().unwrap();
|
||||
let stdout = handle::get_current_handle().unwrap();
|
||||
|
||||
let mut dw_mode: DWORD = 0;
|
||||
if !kernel::get_console_mode(&stdout, &mut dw_mode) {
|
||||
@ -156,16 +156,6 @@ impl IAlternateScreenCommand for ToAlternateScreenCommand {
|
||||
// Make the new screen buffer the active screen buffer.
|
||||
csbi::set_active_screen_buffer(new_handle)?;
|
||||
|
||||
let b: &mut WinApiOutput = match stdout
|
||||
.as_any_mut()
|
||||
.downcast_mut::<WinApiOutput>()
|
||||
{
|
||||
Some(b) => b,
|
||||
None => return Err(Error::new(ErrorKind::Other, "Invalid cast exception")),
|
||||
};
|
||||
|
||||
b.set(new_handle);
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
|
@ -22,7 +22,10 @@ pub fn get_terminal_size() -> (u16, u16) {
|
||||
|
||||
/// Get the cursor position based on the current platform.
|
||||
pub fn get_cursor_position(stdout: &Arc<TerminalOutput>) -> (u16, u16) {
|
||||
#[cfg(unix)]
|
||||
return pos(stdout);
|
||||
#[cfg(windows)]
|
||||
return pos();
|
||||
}
|
||||
|
||||
/// exit the current terminal.
|
||||
|
@ -10,7 +10,7 @@
|
||||
//! The characters are not processed by the terminal driver, but are sent straight through.
|
||||
//! Special character have no meaning, like backspace will not be interpret as backspace but instead will be directly send to the terminal.
|
||||
//! - Escape characters
|
||||
//! Note that in raw modes `\n` will move to the new line but the cursor will be at the same position as before on the new line therefor use `\n\r` to start at the new line at the first cell.
|
||||
//! Note that in raw modes `\n` `\r` will move to the new line but the cursor will be at the same position as before on the new line therefor use `\n\r` to start at the new line at the first cell.
|
||||
//!
|
||||
//! With these modes you can easier design the terminal screen.
|
||||
|
||||
|
@ -55,7 +55,7 @@ impl Screen
|
||||
{
|
||||
if raw_mode
|
||||
{
|
||||
let screen = Screen { stdout: Arc::new(TerminalOutput::new()), buffer: Vec::new() };
|
||||
let screen = Screen { stdout: Arc::new(TerminalOutput::new(true)), buffer: Vec::new() };
|
||||
RawScreen::into_raw_mode();
|
||||
return screen;
|
||||
}
|
||||
@ -71,11 +71,25 @@ impl Screen
|
||||
/// For an example of this behavior, consider when vim is launched from bash.
|
||||
/// Vim uses the entirety of the screen to edit the file, then returning to bash leaves the original buffer unchanged.
|
||||
pub fn enable_alternate_modes(&self, raw_mode: bool) -> Result<AlternateScreen> {
|
||||
let stdout = TerminalOutput::new();
|
||||
let stdout = TerminalOutput::new(raw_mode);
|
||||
|
||||
let alternate_screen = AlternateScreen::to_alternate_screen(stdout, raw_mode)?;
|
||||
return Ok(alternate_screen);
|
||||
}
|
||||
|
||||
/// Write buffer to an internal buffer. When you want to write the buffer to screen use `flush()`.
|
||||
///
|
||||
/// This function is useful if you want to build up some output and when you are ready you could flush the output to the screen.
|
||||
pub fn write_buf(&mut self, buf: &[u8]) -> Result<usize> {
|
||||
self.buffer.write(buf);
|
||||
Ok(buf.len())
|
||||
}
|
||||
|
||||
/// Flush the internal buffer to the screen.
|
||||
pub fn flush_buf(&mut self) -> Result<()> {
|
||||
self.stdout.write_buf(&self.buffer);
|
||||
self.stdout.flush()
|
||||
}
|
||||
}
|
||||
|
||||
impl From<TerminalOutput> for Screen
|
||||
@ -98,7 +112,7 @@ impl Default for Screen
|
||||
{
|
||||
/// Create an new screen which will not be in raw mode or alternate mode.
|
||||
fn default() -> Self {
|
||||
return Screen { stdout: Arc::new(TerminalOutput::new()), buffer: Vec::new() };
|
||||
return Screen { stdout: Arc::new(TerminalOutput::new(false)), buffer: Vec::new() };
|
||||
}
|
||||
}
|
||||
|
||||
@ -115,17 +129,11 @@ impl Drop for Screen
|
||||
|
||||
impl Write for Screen
|
||||
{
|
||||
/// Write buffer to an internal buffer. When you want to write the buffer to screen use `flush()`.
|
||||
///
|
||||
/// This function is useful if you want to build up some output and when you are ready you could flush the output to the screen.
|
||||
fn write(&mut self, buf: &[u8]) -> Result<usize> {
|
||||
self.buffer.write(buf);
|
||||
Ok(buf.len())
|
||||
self.stdout.write_buf(buf)
|
||||
}
|
||||
|
||||
/// Flush the internal buffer to the screen.
|
||||
fn flush(&mut self) -> Result<()> {
|
||||
self.stdout.write_buf(&self.buffer);
|
||||
self.stdout.flush()
|
||||
}
|
||||
}
|
@ -18,12 +18,12 @@ use std::mem::size_of;
|
||||
use std::sync::Arc;
|
||||
|
||||
/// Create a new console screen buffer info struct.
|
||||
pub fn get_csbi(stdout: &Arc<TerminalOutput>) -> Result<CONSOLE_SCREEN_BUFFER_INFO> {
|
||||
pub fn get_csbi() -> Result<CONSOLE_SCREEN_BUFFER_INFO> {
|
||||
let mut csbi = CONSOLE_SCREEN_BUFFER_INFO::empty();
|
||||
let success;
|
||||
|
||||
unsafe {
|
||||
success = GetConsoleScreenBufferInfo(handle::get_current_handle(stdout)?, &mut csbi)
|
||||
success = GetConsoleScreenBufferInfo(handle::get_current_handle()?, &mut csbi)
|
||||
}
|
||||
|
||||
if success == 0 {
|
||||
@ -37,10 +37,8 @@ pub fn get_csbi(stdout: &Arc<TerminalOutput>) -> Result<CONSOLE_SCREEN_BUFFER_IN
|
||||
}
|
||||
|
||||
/// Get buffer info and handle of the current screen.
|
||||
pub fn get_csbi_and_handle(
|
||||
stdout: &Arc<TerminalOutput>,
|
||||
) -> Result<(CONSOLE_SCREEN_BUFFER_INFO, HANDLE)> {
|
||||
let handle = handle::get_current_handle(stdout)?;
|
||||
pub fn get_csbi_and_handle() -> Result<(CONSOLE_SCREEN_BUFFER_INFO, HANDLE)> {
|
||||
let handle = handle::get_current_handle()?;
|
||||
let csbi = get_csbi_by_handle(&handle)?;
|
||||
|
||||
return Ok((csbi, handle));
|
||||
@ -63,8 +61,8 @@ pub fn get_csbi_by_handle(handle: &HANDLE) -> Result<CONSOLE_SCREEN_BUFFER_INFO>
|
||||
}
|
||||
|
||||
/// Set the console screen buffer size
|
||||
pub fn set_console_screen_buffer_size(size: COORD, stdout: &Arc<TerminalOutput>) -> bool {
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
pub fn set_console_screen_buffer_size(size: COORD) -> bool {
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
unsafe {
|
||||
if !kernel::is_true(SetConsoleScreenBufferSize(handle, size)) {
|
||||
|
@ -14,19 +14,18 @@ use std::sync::Arc;
|
||||
static mut SAVED_CURSOR_POS: (u16, u16) = (0, 0);
|
||||
|
||||
/// Reset to saved cursor position
|
||||
pub fn reset_to_saved_position(stdout: &Arc<TerminalOutput>) {
|
||||
pub fn reset_to_saved_position() {
|
||||
unsafe {
|
||||
set_console_cursor_position(
|
||||
SAVED_CURSOR_POS.0 as i16,
|
||||
SAVED_CURSOR_POS.1 as i16,
|
||||
stdout,
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/// Save current cursor position to recall later.
|
||||
pub fn save_cursor_pos(stdout: &Arc<TerminalOutput>) {
|
||||
let position = pos(stdout);
|
||||
pub fn save_cursor_pos() {
|
||||
let position = pos();
|
||||
|
||||
unsafe {
|
||||
SAVED_CURSOR_POS = (position.0, position.1);
|
||||
@ -34,8 +33,8 @@ pub fn save_cursor_pos(stdout: &Arc<TerminalOutput>) {
|
||||
}
|
||||
|
||||
/// get the current cursor position.
|
||||
pub fn pos(stdout: &Arc<TerminalOutput>) -> (u16, u16) {
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
pub fn pos() -> (u16, u16) {
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
if let Ok(csbi) = csbi::get_csbi_by_handle(&handle) {
|
||||
(
|
||||
@ -48,7 +47,7 @@ pub fn pos(stdout: &Arc<TerminalOutput>) -> (u16, u16) {
|
||||
}
|
||||
|
||||
/// 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, stdout: &Arc<TerminalOutput>) {
|
||||
pub fn set_console_cursor_position(x: i16, y: i16) {
|
||||
if x < 0 || x >= <i16>::max_value() {
|
||||
panic!(
|
||||
"Argument Out of Range Exception when setting cursor position to X: {}",
|
||||
@ -63,7 +62,7 @@ pub fn set_console_cursor_position(x: i16, y: i16, stdout: &Arc<TerminalOutput>)
|
||||
);
|
||||
}
|
||||
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
let position = COORD { X: x, Y: y };
|
||||
|
||||
@ -77,8 +76,8 @@ pub fn set_console_cursor_position(x: i16, y: i16, stdout: &Arc<TerminalOutput>)
|
||||
}
|
||||
|
||||
/// change the cursor visibility.
|
||||
pub fn cursor_visibility(visable: bool, stdout: &Arc<TerminalOutput>) -> io::Result<()> {
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
pub fn cursor_visibility(visable: bool) -> io::Result<()> {
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
let cursor_info = CONSOLE_CURSOR_INFO {
|
||||
dwSize: 100,
|
||||
|
@ -15,22 +15,11 @@ use std::ptr::null_mut;
|
||||
|
||||
use winapi::ctypes::c_void;
|
||||
|
||||
/// Get the global stored handle whits provides access to the current screen.
|
||||
pub fn get_current_handle(stdout: &Arc<TerminalOutput>) -> Result<HANDLE> {
|
||||
// let handle: Result<HANDLE>;
|
||||
//
|
||||
// let winapi_stdout: &WinApiOutput = match stdout
|
||||
// .as_any()
|
||||
// .downcast_ref::<WinApiOutput>()
|
||||
// {
|
||||
// Some(win_api) => win_api,
|
||||
// None => return Err(io::Error::new(io::ErrorKind::Other,"Could not convert to winapi screen write, this could happen when the user has an ANSI screen write and is calling the platform specific operations 'get_cursor_pos' or 'get_terminal_size'"))
|
||||
// };
|
||||
|
||||
/// Get the handle of the active screen.
|
||||
pub fn get_current_handle() -> Result<HANDLE> {
|
||||
let dw: DWORD = 0;
|
||||
unsafe {
|
||||
|
||||
let utf16: Vec<u16> = "CONOUT$".encode_utf16().collect();
|
||||
let utf16: Vec<u16> = "CONOUT$\0".encode_utf16().collect();
|
||||
let utf16_ptr: *const u16 = utf16.as_ptr();
|
||||
|
||||
let handle = CreateFileW(utf16_ptr, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_WRITE, null_mut(), OPEN_EXISTING, dw, null_mut());
|
||||
@ -51,30 +40,6 @@ pub fn get_current_handle(stdout: &Arc<TerminalOutput>) -> Result<HANDLE> {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_current_handle_1() -> Result<HANDLE>
|
||||
{
|
||||
let handle: Result<HANDLE>;
|
||||
use std::str;
|
||||
unsafe
|
||||
{
|
||||
let dw: DWORD = 0;
|
||||
|
||||
let utf16: Vec<u16> = "CONOUT$".encode_utf16().collect();
|
||||
let utf16_ptr: *const u16 = utf16.as_ptr();
|
||||
|
||||
let handle = CreateFileW(utf16_ptr, GENERIC_READ | GENERIC_WRITE, FILE_SHARE_WRITE, null_mut(), OPEN_EXISTING,dw, null_mut());
|
||||
|
||||
if !is_valid_handle(&handle) {
|
||||
return Err(io::Error::new(
|
||||
io::ErrorKind::Other,
|
||||
"Could not get output handle 1 !",
|
||||
));
|
||||
}
|
||||
|
||||
Ok(handle)
|
||||
}
|
||||
}
|
||||
|
||||
/// Get the std_output_handle of the console
|
||||
pub fn get_output_handle() -> Result<HANDLE> {
|
||||
unsafe {
|
||||
|
@ -30,8 +30,8 @@ pub fn get_console_mode(handle: &HANDLE, current_mode: &mut u32) -> bool {
|
||||
}
|
||||
|
||||
/// Change the console text attribute.
|
||||
pub fn set_console_text_attribute(value: u16, stdout: &Arc<TerminalOutput>) -> bool {
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
pub fn set_console_text_attribute(value: u16) -> bool {
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
unsafe {
|
||||
return is_true(SetConsoleTextAttribute(handle, value));
|
||||
@ -39,8 +39,8 @@ pub fn set_console_text_attribute(value: u16, stdout: &Arc<TerminalOutput>) -> b
|
||||
}
|
||||
|
||||
/// Change console info.
|
||||
pub fn set_console_info(absolute: bool, rect: &SMALL_RECT, stdout: &Arc<TerminalOutput>) -> bool {
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
pub fn set_console_info(absolute: bool, rect: &SMALL_RECT) -> bool {
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
let absolute = match absolute {
|
||||
true => 1,
|
||||
|
@ -17,7 +17,7 @@ pub fn terminal_size() -> (u16, u16) {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn buffer_size(stdout: &Arc<TerminalOutput>) -> (u16, u16) {
|
||||
pub fn buffer_size() -> (u16, u16) {
|
||||
let handle = handle::get_output_handle().unwrap();
|
||||
|
||||
if let Ok(csbi) = csbi::get_csbi_by_handle(&handle) {
|
||||
|
@ -18,10 +18,9 @@ use std::sync::Arc;
|
||||
pub fn fill_console_output_character(
|
||||
cells_written: &mut u32,
|
||||
start_location: COORD,
|
||||
cells_to_write: u32,
|
||||
stdout: &Arc<TerminalOutput>,
|
||||
cells_to_write: u32
|
||||
) -> bool {
|
||||
let handle = handle::get_current_handle(stdout).unwrap();
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
|
||||
unsafe {
|
||||
// fill the cells in console with blanks
|
||||
@ -40,12 +39,11 @@ pub fn fill_console_output_character(
|
||||
pub fn fill_console_output_attribute(
|
||||
cells_written: &mut u32,
|
||||
start_location: COORD,
|
||||
cells_to_write: u32,
|
||||
stdout: &Arc<TerminalOutput>,
|
||||
cells_to_write: u32
|
||||
) -> bool {
|
||||
// Get the position of the current console window
|
||||
|
||||
let (csbi, handle) = csbi::get_csbi_and_handle(stdout).unwrap();
|
||||
let (csbi, handle) = csbi::get_csbi_and_handle().unwrap();
|
||||
|
||||
let success;
|
||||
|
||||
|
@ -17,11 +17,11 @@ impl WinApiCursor {
|
||||
|
||||
impl ITerminalCursor for WinApiCursor {
|
||||
fn goto(&self, x: u16, y: u16, stdout: &Arc<TerminalOutput>) {
|
||||
cursor::set_console_cursor_position(x as i16, y as i16, stdout);
|
||||
cursor::set_console_cursor_position(x as i16, y as i16);
|
||||
}
|
||||
|
||||
fn pos(&self, stdout: &Arc<TerminalOutput>) -> (u16, u16) {
|
||||
cursor::pos(stdout)
|
||||
cursor::pos()
|
||||
}
|
||||
|
||||
fn move_up(&self, count: u16, stdout: &Arc<TerminalOutput>) {
|
||||
@ -45,19 +45,19 @@ impl ITerminalCursor for WinApiCursor {
|
||||
}
|
||||
|
||||
fn save_position(&self, stdout: &Arc<TerminalOutput>) {
|
||||
cursor::save_cursor_pos(stdout);
|
||||
cursor::save_cursor_pos();
|
||||
}
|
||||
|
||||
fn reset_position(&self, stdout: &Arc<TerminalOutput>) {
|
||||
cursor::reset_to_saved_position(stdout);
|
||||
cursor::reset_to_saved_position();
|
||||
}
|
||||
|
||||
fn hide(&self, stdout: &Arc<TerminalOutput>) {
|
||||
cursor::cursor_visibility(false, stdout);
|
||||
cursor::cursor_visibility(false);
|
||||
}
|
||||
|
||||
fn show(&self, stdout: &Arc<TerminalOutput>) {
|
||||
cursor::cursor_visibility(true, stdout);
|
||||
cursor::cursor_visibility(true);
|
||||
}
|
||||
fn blink(&self, blink: bool, stdout: &Arc<TerminalOutput>) {}
|
||||
}
|
||||
|
@ -35,7 +35,7 @@ pub struct TerminalOutput {
|
||||
|
||||
impl TerminalOutput {
|
||||
/// Create new screen write instance whereon screen related actions can be performed.
|
||||
pub fn new() -> Self {
|
||||
pub fn new(raw_mode: bool) -> Self {
|
||||
#[cfg(target_os = "windows")]
|
||||
let stdout: Box<IStdout + Send + Sync> = functions::get_module::<Box<IStdout + Send + Sync>>(
|
||||
Box::from(WinApiOutput::new()),
|
||||
@ -45,7 +45,7 @@ impl TerminalOutput {
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
let stdout = Box::from(AnsiOutput::new()) as Box<IStdout + Send + Sync>;
|
||||
|
||||
TerminalOutput { stdout , is_in_raw_mode: false}
|
||||
TerminalOutput { stdout , is_in_raw_mode: raw_mode}
|
||||
}
|
||||
|
||||
/// Write String to the current screen.
|
||||
|
@ -9,9 +9,14 @@ use std::any::Any;
|
||||
use std::io;
|
||||
|
||||
/// This struct is a wrapper for WINAPI `HANDLE`
|
||||
pub struct WinApiOutput {
|
||||
pub handle: Mutex<HANDLE>,
|
||||
raw_mode: bool,
|
||||
pub struct WinApiOutput;
|
||||
|
||||
impl WinApiOutput
|
||||
{
|
||||
pub fn new() -> WinApiOutput
|
||||
{
|
||||
WinApiOutput {}
|
||||
}
|
||||
}
|
||||
|
||||
impl IStdout for WinApiOutput {
|
||||
@ -21,7 +26,8 @@ impl IStdout for WinApiOutput {
|
||||
}
|
||||
|
||||
fn write(&self, buf: &[u8]) -> io::Result<usize> {
|
||||
writing::write_char_buffer(&self.handle.lock().unwrap(), buf)
|
||||
let handle = handle::get_current_handle().unwrap();
|
||||
writing::write_char_buffer(&handle, buf)
|
||||
}
|
||||
|
||||
fn flush(&self) -> io::Result<()> {
|
||||
@ -37,23 +43,6 @@ impl IStdout for WinApiOutput {
|
||||
}
|
||||
}
|
||||
|
||||
impl WinApiOutput {
|
||||
pub fn new() -> Self {
|
||||
let handle = handle::get_output_handle().unwrap();
|
||||
WinApiOutput { raw_mode: false, handle: Mutex::new(handle) }
|
||||
}
|
||||
|
||||
pub fn set(&mut self, handle: HANDLE)
|
||||
{
|
||||
self.handle = Mutex::new(handle);
|
||||
}
|
||||
|
||||
pub fn get_handle(&self) -> HANDLE
|
||||
{
|
||||
return self.handle.lock().unwrap().clone();
|
||||
}
|
||||
}
|
||||
|
||||
unsafe impl Send for WinApiOutput {}
|
||||
|
||||
unsafe impl Sync for WinApiOutput {}
|
||||
|
@ -23,7 +23,7 @@ impl ITerminalColor for WinApiColor {
|
||||
fn set_fg(&self, fg_color: Color, stdout: &Arc<TerminalOutput>) {
|
||||
let color_value = &self.color_value(fg_color, ColorType::Foreground);
|
||||
|
||||
let csbi = csbi::get_csbi(stdout).unwrap();
|
||||
let csbi = csbi::get_csbi().unwrap();
|
||||
|
||||
// Notice that the color values are stored in wAttribute.
|
||||
// So we need to use bitwise operators to check if the values exists or to get current console colors.
|
||||
@ -38,13 +38,13 @@ impl ITerminalColor for WinApiColor {
|
||||
color = color | wincon::BACKGROUND_INTENSITY as u16;
|
||||
}
|
||||
|
||||
kernel::set_console_text_attribute(color, stdout);
|
||||
kernel::set_console_text_attribute(color);
|
||||
}
|
||||
|
||||
fn set_bg(&self, bg_color: Color, stdout: &Arc<TerminalOutput>) {
|
||||
let color_value = &self.color_value(bg_color, ColorType::Background);
|
||||
|
||||
let (csbi, handle) = csbi::get_csbi_and_handle(stdout).unwrap();
|
||||
let (csbi, handle) = csbi::get_csbi_and_handle().unwrap();
|
||||
|
||||
// Notice that the color values are stored in wAttribute.
|
||||
// So wee need to use bitwise operators to check if the values exists or to get current console colors.
|
||||
@ -59,11 +59,11 @@ impl ITerminalColor for WinApiColor {
|
||||
color = color | wincon::FOREGROUND_INTENSITY as u16;
|
||||
}
|
||||
|
||||
kernel::set_console_text_attribute(color, stdout);
|
||||
kernel::set_console_text_attribute(color);
|
||||
}
|
||||
|
||||
fn reset(&self, stdout: &Arc<TerminalOutput>) {
|
||||
kernel::set_console_text_attribute(self.original_color, stdout);
|
||||
kernel::set_console_text_attribute(self.original_color);
|
||||
}
|
||||
|
||||
/// This will get the winapi color value from the Color and ColorType struct
|
||||
|
@ -20,7 +20,7 @@ impl WinApiTerminal {
|
||||
|
||||
impl ITerminal for WinApiTerminal {
|
||||
fn clear(&self, clear_type: ClearType, stdout: &Arc<TerminalOutput>) {
|
||||
let csbi = csbi::get_csbi(stdout).unwrap();
|
||||
let csbi = csbi::get_csbi().unwrap();
|
||||
let pos = TerminalCursor::new(stdout).pos();
|
||||
|
||||
match clear_type {
|
||||
@ -39,7 +39,7 @@ impl ITerminal for WinApiTerminal {
|
||||
}
|
||||
|
||||
fn scroll_up(&self, count: i16, stdout: &Arc<TerminalOutput>) {
|
||||
let csbi = csbi::get_csbi(&stdout).unwrap();
|
||||
let csbi = csbi::get_csbi().unwrap();
|
||||
|
||||
// Set srctWindow to the current window size and location.
|
||||
let mut srct_window = csbi.srWindow;
|
||||
@ -49,7 +49,7 @@ impl ITerminal for WinApiTerminal {
|
||||
srct_window.Top -= count; // move top down
|
||||
srct_window.Bottom = count; // move bottom down
|
||||
|
||||
let success = kernel::set_console_info(false, &mut srct_window, &stdout);
|
||||
let success = kernel::set_console_info(false, &mut srct_window);
|
||||
if success {
|
||||
panic!("Something went wrong when scrolling down");
|
||||
}
|
||||
@ -57,7 +57,7 @@ impl ITerminal for WinApiTerminal {
|
||||
}
|
||||
|
||||
fn scroll_down(&self, count: i16, stdout: &Arc<TerminalOutput>) {
|
||||
let csbi = csbi::get_csbi(&stdout).unwrap();
|
||||
let csbi = csbi::get_csbi().unwrap();
|
||||
// Set srctWindow to the current window size and location.
|
||||
let mut srct_window = csbi.srWindow;
|
||||
|
||||
@ -66,7 +66,7 @@ impl ITerminal for WinApiTerminal {
|
||||
srct_window.Top += count; // move top down
|
||||
srct_window.Bottom += count; // move bottom down
|
||||
|
||||
let success = kernel::set_console_info(true, &mut srct_window, &stdout);
|
||||
let success = kernel::set_console_info(true, &mut srct_window);
|
||||
if success {
|
||||
panic!("Something went wrong when scrolling down");
|
||||
}
|
||||
@ -84,7 +84,7 @@ impl ITerminal for WinApiTerminal {
|
||||
}
|
||||
|
||||
// Get the position of the current console window
|
||||
let csbi = csbi::get_csbi(&stdout).unwrap();
|
||||
let csbi = csbi::get_csbi().unwrap();
|
||||
let mut success = false;
|
||||
|
||||
// If the buffer is smaller than this new window size, resize the
|
||||
@ -113,7 +113,7 @@ impl ITerminal for WinApiTerminal {
|
||||
}
|
||||
|
||||
if resize_buffer {
|
||||
success = csbi::set_console_screen_buffer_size(size, &stdout);
|
||||
success = csbi::set_console_screen_buffer_size(size);
|
||||
|
||||
if !success {
|
||||
panic!("Something went wrong when setting screen buffer size.");
|
||||
@ -125,12 +125,12 @@ impl ITerminal for WinApiTerminal {
|
||||
fsr_window.Bottom = fsr_window.Top + height;
|
||||
fsr_window.Right = fsr_window.Left + width;
|
||||
|
||||
let success = kernel::set_console_info(true, &fsr_window, &stdout);
|
||||
let success = kernel::set_console_info(true, &fsr_window);
|
||||
|
||||
if success {
|
||||
// If we resized the buffer, un-resize it.
|
||||
if resize_buffer {
|
||||
csbi::set_console_screen_buffer_size(csbi.dwSize, &stdout);
|
||||
csbi::set_console_screen_buffer_size(csbi.dwSize);
|
||||
}
|
||||
|
||||
let bounds = kernel::get_largest_console_window_size();
|
||||
@ -179,7 +179,7 @@ pub fn clear_after_cursor(
|
||||
// get sum cells before cursor
|
||||
let cells_to_write = csbi.dwSize.X as u32 * csbi.dwSize.Y as u32;
|
||||
|
||||
clear(start_location, cells_to_write, stdout);
|
||||
clear(start_location, cells_to_write);
|
||||
}
|
||||
|
||||
pub fn clear_before_cursor(
|
||||
@ -202,7 +202,7 @@ pub fn clear_before_cursor(
|
||||
// get sum cells before cursor
|
||||
let cells_to_write = (csbi.dwSize.X as u32 * ypos as u32) + (xpos as u32 + 1);
|
||||
|
||||
clear(start_location, cells_to_write, stdout);
|
||||
clear(start_location, cells_to_write);
|
||||
}
|
||||
|
||||
pub fn clear_entire_screen(csbi: CONSOLE_SCREEN_BUFFER_INFO, stdout: &Arc<TerminalOutput>) {
|
||||
@ -220,7 +220,7 @@ pub fn clear_entire_screen(csbi: CONSOLE_SCREEN_BUFFER_INFO, stdout: &Arc<Termin
|
||||
|
||||
let cells_to_write = csbi.dwSize.X as u32 * csbi.dwSize.Y as u32;
|
||||
|
||||
clear(start_location, cells_to_write, &stdout);
|
||||
clear(start_location, cells_to_write);
|
||||
|
||||
// put the cursor back at (0, 0)
|
||||
TerminalCursor::new(stdout).goto(0, 0);
|
||||
@ -245,7 +245,7 @@ pub fn clear_current_line(
|
||||
|
||||
let cells_to_write = csbi.dwSize.X as u32;
|
||||
|
||||
clear(start_location, cells_to_write, stdout);
|
||||
clear(start_location, cells_to_write);
|
||||
|
||||
// put the cursor back at 1 cell on current row
|
||||
TerminalCursor::new(stdout).goto(0, y);
|
||||
@ -266,13 +266,13 @@ pub fn clear_until_line(
|
||||
// get sum cells before cursor
|
||||
let cells_to_write = (csbi.dwSize.X - x as i16) as u32;
|
||||
|
||||
clear(start_location, cells_to_write, &stdout);
|
||||
clear(start_location, cells_to_write);
|
||||
|
||||
// put the cursor back at original cursor position
|
||||
TerminalCursor::new(stdout).goto(x, y);
|
||||
}
|
||||
|
||||
fn clear(start_loaction: COORD, cells_to_write: u32, stdout: &Arc<TerminalOutput>) {
|
||||
fn clear(start_loaction: COORD, cells_to_write: u32) {
|
||||
let mut cells_written = 0;
|
||||
let mut success = false;
|
||||
|
||||
@ -280,7 +280,6 @@ fn clear(start_loaction: COORD, cells_to_write: u32, stdout: &Arc<TerminalOutput
|
||||
&mut cells_written,
|
||||
start_loaction,
|
||||
cells_to_write,
|
||||
stdout,
|
||||
);
|
||||
|
||||
if !success {
|
||||
@ -293,7 +292,6 @@ fn clear(start_loaction: COORD, cells_to_write: u32, stdout: &Arc<TerminalOutput
|
||||
&mut cells_written,
|
||||
start_loaction,
|
||||
cells_to_write,
|
||||
stdout,
|
||||
);
|
||||
|
||||
if !success {
|
||||
|
Loading…
Reference in New Issue
Block a user