Maked windows compilable and worked on the screen manager for windows.
This commit is contained in:
parent
e48b952604
commit
bb2067ed7b
1026
.idea/workspace.xml
1026
.idea/workspace.xml
File diff suppressed because it is too large
Load Diff
@ -5,6 +5,7 @@
|
||||
|
||||
use super::*;
|
||||
use Context;
|
||||
use super::super::shared::functions;
|
||||
|
||||
use std::fmt::Display;
|
||||
use std::io::Write;
|
||||
@ -20,7 +21,7 @@ impl <'context> TerminalCursor<'context>
|
||||
/// Create new cursor instance whereon cursor related actions can be performed.
|
||||
pub fn new(context: &'context Context) -> TerminalCursor<'context> {
|
||||
#[cfg(target_os = "windows")]
|
||||
let cursor = functions::get_module::<Box<ITerminalCursor>>(WinApiCursor::new(), AnsiCursor::new());
|
||||
let cursor = functions::get_module::<Box<ITerminalCursor>>(WinApiCursor::new(), AnsiCursor::new(), context);
|
||||
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
let cursor = Some(AnsiCursor::new() as Box<ITerminalCursor>);
|
||||
|
@ -26,23 +26,23 @@ impl ITerminalCursor for WinApiCursor {
|
||||
}
|
||||
|
||||
fn move_up(&self, count: u16, context: &Context) {
|
||||
let (xpos,ypos) = self.pos();
|
||||
self.goto(xpos, ypos - count);
|
||||
let (xpos,ypos) = self.pos(context);
|
||||
self.goto(xpos, ypos - count, context);
|
||||
}
|
||||
|
||||
fn move_right(&self, count: u16, context: &Context) {
|
||||
let (xpos,ypos) = self.pos();
|
||||
self.goto(xpos + count, ypos);
|
||||
let (xpos,ypos) = self.pos(context);
|
||||
self.goto(xpos + count, ypos, context);
|
||||
}
|
||||
|
||||
fn move_down(&self, count: u16, context: &Context) {
|
||||
let (xpos,ypos) = self.pos();
|
||||
self.goto(xpos, ypos + count);
|
||||
let (xpos,ypos) = self.pos(context);
|
||||
self.goto(xpos, ypos + count,context);
|
||||
}
|
||||
|
||||
fn move_left(&self, count: u16, context: &Context) {
|
||||
let (xpos,ypos) = self.pos();
|
||||
self.goto(xpos - count, ypos);
|
||||
let (xpos,ypos) = self.pos(context);
|
||||
self.goto(xpos - count, ypos,context);
|
||||
}
|
||||
|
||||
fn save_position(&mut self, context: &Context)
|
||||
|
@ -1,6 +1,6 @@
|
||||
//! This module handles the enabling `ANSI escape codes` for windows terminals.
|
||||
|
||||
use StateManager;
|
||||
use {Context, StateManager};
|
||||
use state::commands::ICommand;
|
||||
|
||||
static mut HAS_BEEN_TRYED_TO_ENABLE: bool = false;
|
||||
@ -8,11 +8,11 @@ static mut IS_ANSI_ON_WINDOWS_ENABLED: Option<bool> = None;
|
||||
static mut DOES_WINDOWS_SUPPORT_ANSI: Option<bool> = None;
|
||||
|
||||
/// Try enable `ANSI escape codes` and return the result.
|
||||
pub fn try_enable_ansi_support() -> bool
|
||||
pub fn try_enable_ansi_support(context: &Context) -> bool
|
||||
{
|
||||
use state::commands::win_commands::EnableAnsiCommand;
|
||||
let mut command = EnableAnsiCommand::new();
|
||||
let success = command.execute();
|
||||
let success = command.execute(&context);
|
||||
|
||||
set_is_windows_ansi_supportable(success);
|
||||
set_ansi_enabled(success);
|
||||
|
@ -6,15 +6,17 @@ use std::io::{self, Write};
|
||||
|
||||
use super::IScreenManager;
|
||||
|
||||
pub struct AnsiScreenManager<Output:Write>
|
||||
pub struct AnsiScreenManager
|
||||
{
|
||||
pub is_alternate_screen: bool,
|
||||
output: Output,
|
||||
output: Box<Write>,
|
||||
}
|
||||
|
||||
impl<Output :Write> IScreenManager<Output> for AnsiScreenManager<Output>
|
||||
impl IScreenManager for AnsiScreenManager
|
||||
{
|
||||
fn stdout(&mut self) -> &mut Output
|
||||
type Output = Box<Write>;
|
||||
|
||||
fn stdout(&mut self) -> &mut Self::Output
|
||||
{
|
||||
return &mut self.output
|
||||
}
|
||||
@ -37,7 +39,7 @@ impl<Output :Write> IScreenManager<Output> for AnsiScreenManager<Output>
|
||||
}
|
||||
}
|
||||
|
||||
impl AnsiScreenManager<Box<Write>> {
|
||||
impl AnsiScreenManager {
|
||||
pub fn new() -> Self {
|
||||
AnsiScreenManager {
|
||||
output: (Box::from(io::stdout()) as Box<Write>),
|
||||
@ -46,7 +48,7 @@ impl AnsiScreenManager<Box<Write>> {
|
||||
}
|
||||
}
|
||||
|
||||
impl<Output:Write> Write for AnsiScreenManager<Output>
|
||||
impl Write for AnsiScreenManager
|
||||
{
|
||||
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
|
||||
self.output.write(buf)
|
||||
|
@ -9,7 +9,7 @@ use std::io::Write;
|
||||
/// Struct that stores an specific platform implementation for screen related actions.
|
||||
pub struct ScreenManager
|
||||
{
|
||||
screen_manager: Box<IScreenManager<Box<Write>>>
|
||||
screen_manager: Box<IScreenManager<Output=Box<Write>>>
|
||||
}
|
||||
|
||||
impl ScreenManager
|
||||
|
@ -13,10 +13,12 @@ use self::ansi_manager::AnsiScreenManager;
|
||||
|
||||
pub use self::manager::{ ScreenManager };
|
||||
|
||||
pub trait IScreenManager<Output>
|
||||
pub trait IScreenManager
|
||||
{
|
||||
type Output;
|
||||
|
||||
/// get the stdout of the screen. This can be used to write to the
|
||||
fn stdout(&mut self) -> &mut Output;
|
||||
fn stdout(&mut self) -> &mut Self::Output;
|
||||
fn toggle_is_alternate_screen(&mut self, is_alternate_screen: bool);
|
||||
/// Write ansi code as String to the current stdout.
|
||||
fn write_ansi(&mut self, string: String);
|
||||
|
@ -1,4 +1,56 @@
|
||||
use super::IScreenManager;
|
||||
use kernel::windows_kernel::kernel;
|
||||
use winapi::um::winnt::HANDLE;
|
||||
|
||||
pub struct WinApiScreenManager
|
||||
{
|
||||
|
||||
pub is_alternate_screen: bool,
|
||||
output: Box<HANDLE>,
|
||||
}
|
||||
|
||||
impl IScreenManager for WinApiScreenManager where
|
||||
{
|
||||
type Output = HANDLE;
|
||||
|
||||
fn stdout(&mut self) -> &mut Self::Output
|
||||
{
|
||||
return &mut self.output
|
||||
}
|
||||
|
||||
fn toggle_is_alternate_screen(&mut self, is_alternate_screen: bool)
|
||||
{
|
||||
self.is_alternate_screen = is_alternate_screen;
|
||||
}
|
||||
|
||||
fn write_ansi(&mut self, string: String)
|
||||
{
|
||||
// write!(self.output, "{}", string);
|
||||
// self.flush();
|
||||
}
|
||||
|
||||
fn write_ansi_str(&mut self, string: &str)
|
||||
{
|
||||
// write!(self.output, "{}", string);
|
||||
// self.flush();
|
||||
}
|
||||
}
|
||||
|
||||
impl WinApiScreenManager {
|
||||
pub fn new() -> Self {
|
||||
WinApiScreenManager {
|
||||
output: (Box::from(kernel::get_output_handle())),
|
||||
is_alternate_screen: false
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//impl<Output:Write> Write for AnsiScreenManager<Output>
|
||||
//{
|
||||
// fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
|
||||
// self.output.write(buf)
|
||||
// }
|
||||
//
|
||||
// fn flush(&mut self) -> io::Result<()> {
|
||||
// self.stdout().flush()
|
||||
// }
|
||||
//}
|
@ -31,7 +31,7 @@ pub fn get_cursor_position(screen: &Context) -> (u16, u16)
|
||||
|
||||
#[cfg(windows)]
|
||||
/// Get an module specific implementation based on the current platform.
|
||||
pub fn get_module<T>(winapi_impl: T, unix_impl: T) -> Option<T>
|
||||
pub fn get_module<T>(winapi_impl: T, unix_impl: T, context: &Context) -> Option<T>
|
||||
{
|
||||
let mut term: Option<T> = None;
|
||||
let mut does_support = true;
|
||||
@ -41,7 +41,7 @@ pub fn get_module<T>(winapi_impl: T, unix_impl: T) -> Option<T>
|
||||
use kernel::windows_kernel::ansi_support::try_enable_ansi_support;
|
||||
|
||||
// Try to enable ansi on windows if not than use WINAPI.
|
||||
does_support = try_enable_ansi_support();
|
||||
does_support = try_enable_ansi_support(&context);
|
||||
|
||||
if !does_support
|
||||
{
|
||||
|
@ -2,7 +2,7 @@
|
||||
|
||||
use Context;
|
||||
use state::commands::*;
|
||||
|
||||
use super::functions;
|
||||
use std::io::{self, Write};
|
||||
|
||||
pub struct AlternateScreen<'context> {
|
||||
@ -14,20 +14,20 @@ impl<'context> AlternateScreen<'context> {
|
||||
/// By calling this method the current screen will be changed to the alternate screen.
|
||||
/// And you get back an handle for that screen.
|
||||
pub fn from(context: &'context Context) -> Self {
|
||||
get_to_alternate_screen_command().execute(&context);
|
||||
get_to_alternate_screen_command(context).execute(&context);
|
||||
AlternateScreen { context: context }
|
||||
}
|
||||
|
||||
/// Change the current screen to the mainscreen.
|
||||
pub fn to_main(&self)
|
||||
{
|
||||
get_to_alternate_screen_command().undo(&self.context);
|
||||
get_to_alternate_screen_command(&self.context).undo(&self.context);
|
||||
}
|
||||
|
||||
/// Change the current screen to alternate screen.
|
||||
pub fn to_alternate(&self)
|
||||
{
|
||||
get_to_alternate_screen_command().execute(&self.context);
|
||||
get_to_alternate_screen_command(&self.context).execute(&self.context);
|
||||
}
|
||||
}
|
||||
|
||||
@ -51,15 +51,15 @@ impl<'context> Drop for AlternateScreen<'context>
|
||||
{
|
||||
fn drop(&mut self)
|
||||
{
|
||||
get_to_alternate_screen_command().undo(&self.context);
|
||||
get_to_alternate_screen_command(&self.context).undo(&self.context);
|
||||
}
|
||||
}
|
||||
|
||||
// Get the alternate screen command to enable and disable alternate screen based on the current platform
|
||||
fn get_to_alternate_screen_command() -> Box<ICommand>
|
||||
fn get_to_alternate_screen_command(context: &Context) -> Box<ICommand>
|
||||
{
|
||||
#[cfg(target_os = "windows")]
|
||||
let command = functions::get_module::<Box<ICommand>>(win_commands::ToAlternateScreenBufferCommand::new(), shared_commands::ToAlternateScreenBufferCommand::new()).unwrap();
|
||||
let command = functions::get_module::<Box<ICommand>>(win_commands::ToAlternateScreenBufferCommand::new(), shared_commands::ToAlternateScreenBufferCommand::new(), context).unwrap();
|
||||
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
let command = shared_commands::ToAlternateScreenBufferCommand::new();
|
||||
|
@ -1,7 +1,7 @@
|
||||
//! This module contains the commands that can be used for windows systems.
|
||||
|
||||
use super::{ICommand, IStateCommand};
|
||||
use super::super::StateManager;
|
||||
use { StateManager, Context };
|
||||
|
||||
use kernel::windows_kernel::{kernel, ansi_support};
|
||||
use winapi::shared::minwindef::DWORD;
|
||||
@ -23,18 +23,16 @@ pub struct EnableAnsiCommand
|
||||
impl ICommand for EnableAnsiCommand
|
||||
{
|
||||
fn new() -> Box<EnableAnsiCommand> {
|
||||
let key = super::generate_key();
|
||||
let command = EnableAnsiCommand { mask: ENABLE_VIRTUAL_TERMINAL_PROCESSING };
|
||||
Box::from(command)
|
||||
}
|
||||
|
||||
fn execute(&mut self) -> bool
|
||||
fn execute(&mut self, context: &Context) -> bool
|
||||
{
|
||||
// we need to check whether we tried to enable ansi before. If we have we can just return if that had succeeded.
|
||||
if ansi_support::has_been_tried_to_enable_ansi() && ansi_support::ansi_enabled()
|
||||
{
|
||||
return ansi_support::windows_supportable();
|
||||
|
||||
} else {
|
||||
let output_handle = kernel::get_output_handle();
|
||||
|
||||
@ -56,7 +54,7 @@ impl ICommand for EnableAnsiCommand
|
||||
}
|
||||
}
|
||||
|
||||
fn undo(&mut self) -> bool
|
||||
fn undo(&mut self, context: &Context) -> bool
|
||||
{
|
||||
if ansi_support::ansi_enabled()
|
||||
{
|
||||
@ -86,23 +84,28 @@ impl ICommand for EnableAnsiCommand
|
||||
pub struct EnableRawModeCommand
|
||||
{
|
||||
mask: DWORD,
|
||||
key: i16
|
||||
key: u16
|
||||
}
|
||||
|
||||
impl EnableRawModeCommand
|
||||
{
|
||||
pub fn new(state_manager: &Mutex<StateManager>) -> u16 {
|
||||
use self::wincon::{ENABLE_LINE_INPUT,ENABLE_PROCESSED_INPUT, ENABLE_PROCESSED_OUTPUT, ENABLE_WRAP_AT_EOL_OUTPUT, ENABLE_ECHO_INPUT};
|
||||
|
||||
|
||||
let mut state = state_manager.lock().unwrap();
|
||||
{
|
||||
let key = state.get_changes_count();
|
||||
let command = EnableRawModeCommand { mask: ENABLE_LINE_INPUT | ENABLE_PROCESSED_INPUT | ENABLE_ECHO_INPUT, key: key };
|
||||
state.register_change(Box::from(command), key);
|
||||
key
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl IStateCommand for EnableRawModeCommand
|
||||
{
|
||||
fn new(state: &mut StateManager) -> (Box<EnableRawModeCommand>, i16) {
|
||||
use self::wincon::{ENABLE_LINE_INPUT,ENABLE_PROCESSED_INPUT, ENABLE_PROCESSED_OUTPUT, ENABLE_WRAP_AT_EOL_OUTPUT, ENABLE_ECHO_INPUT};
|
||||
|
||||
let key = super::generate_key();
|
||||
let command = EnableRawModeCommand { mask: ENABLE_LINE_INPUT | ENABLE_PROCESSED_INPUT | ENABLE_ECHO_INPUT, key: key };
|
||||
let rc = Rc::new(command);
|
||||
|
||||
state.register_change(rc.clone(), key);
|
||||
(rc.clone(),key)
|
||||
}
|
||||
|
||||
fn execute(&mut self, terminal: &Terminal) -> bool
|
||||
fn execute(&mut self, context: &Context) -> bool
|
||||
{
|
||||
use self::wincon::{ENABLE_LINE_INPUT,ENABLE_PROCESSED_INPUT, ENABLE_ECHO_INPUT};
|
||||
|
||||
@ -124,7 +127,7 @@ impl IStateCommand for EnableRawModeCommand
|
||||
true
|
||||
}
|
||||
|
||||
fn undo(&mut self, terminal: &Terminal) -> bool
|
||||
fn undo(&mut self, context: &Context) -> bool
|
||||
{
|
||||
let output_handle = kernel::get_output_handle();
|
||||
|
||||
@ -157,7 +160,7 @@ impl ICommand for ToAlternateScreenBufferCommand
|
||||
Box::from(ToAlternateScreenBufferCommand {})
|
||||
}
|
||||
|
||||
fn execute(&mut self, state: &StateManager) -> bool
|
||||
fn execute(&mut self, context: &Context) -> bool
|
||||
{
|
||||
let mut chi_buffer: [CHAR_INFO;160] = unsafe {mem::zeroed() };
|
||||
|
||||
@ -211,7 +214,7 @@ impl ICommand for ToAlternateScreenBufferCommand
|
||||
true
|
||||
}
|
||||
|
||||
fn undo(&mut self, state: &StateManager) -> bool
|
||||
fn undo(&mut self, context: &Context) -> bool
|
||||
{
|
||||
let handle = kernel::get_output_handle();
|
||||
kernel::set_active_screen_buffer(handle);
|
||||
|
@ -78,7 +78,7 @@ impl Context
|
||||
where
|
||||
D: fmt::Display,
|
||||
{
|
||||
style::ObjectStyle::new().apply_to(val, self.screen_manager.clone())
|
||||
style::ObjectStyle::new().apply_to(val, &self)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -50,6 +50,11 @@ impl StateManager
|
||||
|
||||
return Rc::new(Mutex::new(Box::new(EmptyCommand)))
|
||||
}
|
||||
|
||||
pub fn get_changes_count(&self) -> u16
|
||||
{
|
||||
return self.changed_states.len() as u16
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
@ -1,12 +1,13 @@
|
||||
//! With this module you can perform actions that are color related.
|
||||
//! Like styling the font, foreground color and background.
|
||||
|
||||
use {ScreenManager, Context};
|
||||
use super::*;
|
||||
use style::Color;
|
||||
|
||||
use std::io;
|
||||
use std::rc::Rc;
|
||||
use std::sync::Mutex;
|
||||
use super::super::super::shared::functions;
|
||||
|
||||
/// Struct that stores an specific platform implementation for color related actions.
|
||||
pub struct TerminalColor {
|
||||
@ -16,14 +17,14 @@ pub struct TerminalColor {
|
||||
|
||||
impl TerminalColor {
|
||||
/// Create new instance whereon color related actions can be performed.
|
||||
pub fn new(screen_manager: Rc<Mutex<ScreenManager>> ) -> TerminalColor {
|
||||
pub fn new(context: &Context ) -> TerminalColor {
|
||||
#[cfg(target_os = "windows")]
|
||||
let color = functions::get_module::<Box<ITerminalColor>>(WinApiColor::new(), AnsiColor::new());
|
||||
let color = functions::get_module::<Box<ITerminalColor>>(WinApiColor::new(), AnsiColor::new(), context);
|
||||
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
let color = Some(AnsiColor::new() as Box<ITerminalColor>);
|
||||
|
||||
TerminalColor { color: color, screen_manager: screen_manager.clone() }
|
||||
TerminalColor { color: color, screen_manager: context.screen_manager.clone() }
|
||||
}
|
||||
|
||||
/// Set the foreground color to the given color.
|
||||
@ -126,6 +127,6 @@ impl TerminalColor {
|
||||
///
|
||||
/// Check `/examples/version/color` in the libary for more specific examples.
|
||||
///
|
||||
pub fn color(screen_manager: Rc<Mutex<ScreenManager>>) -> Box<TerminalColor> {
|
||||
Box::from(TerminalColor::new(screen_manager.clone()))
|
||||
pub fn color(context: &Context) -> Box<TerminalColor> {
|
||||
Box::from(TerminalColor::new(context))
|
||||
}
|
||||
|
@ -1,8 +1,11 @@
|
||||
use Construct;
|
||||
use super::ITerminalColor;
|
||||
use super::super::{ColorType, Color};
|
||||
use winapi::um::wincon;
|
||||
use kernel::windows_kernel::kernel;
|
||||
use ScreenManager;
|
||||
|
||||
use std::sync::Mutex;
|
||||
use std::rc::Rc;
|
||||
|
||||
/// This struct is an windows implementation for color related actions.
|
||||
#[derive(Debug)]
|
||||
@ -10,8 +13,8 @@ pub struct WinApiColor {
|
||||
original_console_color: u16,
|
||||
}
|
||||
|
||||
impl Construct for WinApiColor {
|
||||
fn new() -> Box<WinApiColor> {
|
||||
impl WinApiColor {
|
||||
pub fn new() -> Box<WinApiColor> {
|
||||
Box::from(WinApiColor {
|
||||
original_console_color: kernel::get_original_console_color(),
|
||||
})
|
||||
@ -20,7 +23,7 @@ impl Construct for WinApiColor {
|
||||
|
||||
impl ITerminalColor for WinApiColor {
|
||||
|
||||
fn set_fg(&self, fg_color: Color) {
|
||||
fn set_fg(&self, fg_color: Color, screen_manager: Rc<Mutex<ScreenManager>>) {
|
||||
let color_value = &self.color_value(fg_color, ColorType::Foreground);
|
||||
|
||||
let csbi = kernel::get_console_screen_buffer_info();
|
||||
@ -41,7 +44,7 @@ impl ITerminalColor for WinApiColor {
|
||||
kernel::set_console_text_attribute(color);
|
||||
}
|
||||
|
||||
fn set_bg(&self, bg_color: Color) {
|
||||
fn set_bg(&self, bg_color: Color, screen_manager: Rc<Mutex<ScreenManager>>) {
|
||||
let color_value = &self.color_value(bg_color, ColorType::Background);
|
||||
|
||||
let csbi = kernel::get_console_screen_buffer_info();
|
||||
@ -61,7 +64,7 @@ impl ITerminalColor for WinApiColor {
|
||||
kernel::set_console_text_attribute(color);
|
||||
}
|
||||
|
||||
fn reset(&self) {
|
||||
fn reset(&self, screen_manager: Rc<Mutex<ScreenManager>>) {
|
||||
kernel::set_console_text_attribute(self.original_console_color);
|
||||
}
|
||||
|
||||
|
@ -2,7 +2,7 @@
|
||||
|
||||
use std::fmt::Display;
|
||||
use style::{Color, StyledObject};
|
||||
use ScreenManager;
|
||||
use { ScreenManager, Context };
|
||||
use std::sync::Mutex;
|
||||
use std::rc::Rc;
|
||||
|
||||
@ -32,13 +32,13 @@ impl Default for ObjectStyle {
|
||||
|
||||
impl ObjectStyle {
|
||||
/// Apply an `StyledObject` to the passed displayable object.
|
||||
pub fn apply_to<D>(&self, val: D, screen: Rc<Mutex<ScreenManager>>) -> StyledObject<D>
|
||||
pub fn apply_to<'a, D>(&self, val: D, context: &'a Context) -> StyledObject<'a, D>
|
||||
where
|
||||
D: Display,
|
||||
{
|
||||
StyledObject {
|
||||
object_style: self.clone(),
|
||||
screen_manager: screen,
|
||||
context: context,
|
||||
content: val,
|
||||
}
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ use std::fmt;
|
||||
use std::io::Write;
|
||||
use std::sync::Mutex;
|
||||
use std::rc::Rc;
|
||||
use ScreenManager;
|
||||
use { ScreenManager, Context};
|
||||
|
||||
#[cfg(unix)]
|
||||
use super::super::Attribute;
|
||||
@ -12,13 +12,13 @@ use super::super::Attribute;
|
||||
use style::{Color, ObjectStyle};
|
||||
|
||||
/// Struct that contains both the style and the content wits can be styled.
|
||||
pub struct StyledObject<D> {
|
||||
pub struct StyledObject<'a, D> {
|
||||
pub object_style: ObjectStyle,
|
||||
pub content: D,
|
||||
pub screen_manager: Rc<Mutex<ScreenManager>>
|
||||
pub context: &'a Context
|
||||
}
|
||||
|
||||
impl<D> StyledObject<D> {
|
||||
impl<'a, D> StyledObject<'a,D> {
|
||||
/// Set the foreground of the styled object to the passed `Color`
|
||||
///
|
||||
/// #Example
|
||||
@ -39,7 +39,7 @@ impl<D> StyledObject<D> {
|
||||
/// println!("{}", paint("I am colored green").with(Color::Green));
|
||||
///
|
||||
/// ```
|
||||
pub fn with(mut self, foreground_color: Color) -> StyledObject<D> {
|
||||
pub fn with(mut self, foreground_color: Color) -> StyledObject<'a,D> {
|
||||
self.object_style = self.object_style.fg(foreground_color);
|
||||
self
|
||||
}
|
||||
@ -64,7 +64,7 @@ impl<D> StyledObject<D> {
|
||||
/// println!("{}", paint("I am colored green").on(Color::Green))
|
||||
///
|
||||
/// ```
|
||||
pub fn on(mut self, background_color: Color) -> StyledObject<D> {
|
||||
pub fn on(mut self, background_color: Color) -> StyledObject<'a,D> {
|
||||
self.object_style = self.object_style.bg(background_color);
|
||||
self
|
||||
}
|
||||
@ -82,7 +82,7 @@ impl<D> StyledObject<D> {
|
||||
///
|
||||
/// ```
|
||||
#[cfg(unix)]
|
||||
pub fn attr(mut self, attr: Attribute) -> StyledObject<D>
|
||||
pub fn attr(mut self, attr: Attribute) -> StyledObject<'a,D>
|
||||
{
|
||||
&self.object_style.add_attr(attr);
|
||||
self
|
||||
@ -113,10 +113,10 @@ impl<D> StyledObject<D> {
|
||||
macro_rules! impl_fmt
|
||||
{
|
||||
($name:ident) => {
|
||||
impl<D: fmt::$name> fmt::$name for StyledObject<D> {
|
||||
impl<'a, D: fmt::$name> fmt::$name for StyledObject<'a, D> {
|
||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result
|
||||
{
|
||||
let mut colored_terminal = super::super::color(self.screen_manager.clone());
|
||||
let mut colored_terminal = super::super::color(&self.context);
|
||||
let mut reset = true;
|
||||
|
||||
if let Some(bg) = self.object_style.bg_color
|
||||
@ -138,7 +138,7 @@ macro_rules! impl_fmt
|
||||
|
||||
fmt::$name::fmt(&self.content, f)?;
|
||||
|
||||
let mutex = &self.screen_manager;
|
||||
let mutex = &self.context.screen_manager;
|
||||
{
|
||||
let mut screen = mutex.lock().unwrap();
|
||||
screen.stdout().flush().expect("Flush stdout failed");
|
||||
|
@ -4,8 +4,9 @@
|
||||
use super::*;
|
||||
use Context;
|
||||
|
||||
use super::super::style;
|
||||
use std::fmt;
|
||||
use super::super::style;
|
||||
use super::super::shared::functions;
|
||||
|
||||
/// Struct that stores an specific platform implementation for terminal related actions.
|
||||
pub struct Terminal<'context> {
|
||||
@ -17,7 +18,7 @@ impl<'context> Terminal<'context> {
|
||||
/// Create new terminal instance whereon terminal related actions can be performed.
|
||||
pub fn new(context: &'context Context) -> Terminal<'context> {
|
||||
#[cfg(target_os = "windows")]
|
||||
let terminal = functions::get_module::<Box<ITerminal>>(WinApiTerminal::new(), AnsiTerminal::new());
|
||||
let terminal = functions::get_module::<Box<ITerminal>>(WinApiTerminal::new(), AnsiTerminal::new(), context);
|
||||
|
||||
#[cfg(not(target_os = "windows"))]
|
||||
let terminal = Some(AnsiTerminal::new() as Box<ITerminal>);
|
||||
@ -182,7 +183,7 @@ impl<'context> Terminal<'context> {
|
||||
where
|
||||
D: fmt::Display,
|
||||
{
|
||||
style::ObjectStyle::new().apply_to(val, self.context.screen_manager.clone())
|
||||
style::ObjectStyle::new().apply_to(val, &self.context)
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1,7 +1,7 @@
|
||||
//! This is an `WINAPI` specific implementation for terminal related action.
|
||||
//! This module is used for non supporting `ANSI` windows terminals.
|
||||
|
||||
use {Construct};
|
||||
use Context;
|
||||
use cursor::cursor;
|
||||
use super::{ClearType, ITerminal};
|
||||
use winapi::um::wincon::{SMALL_RECT, COORD, CONSOLE_SCREEN_BUFFER_INFO,};
|
||||
@ -10,37 +10,37 @@ use kernel::windows_kernel::{kernel, terminal};
|
||||
/// This struct is an windows implementation for terminal related actions.
|
||||
pub struct WinApiTerminal;
|
||||
|
||||
impl Construct for WinApiTerminal {
|
||||
fn new() -> Box<WinApiTerminal> {
|
||||
impl WinApiTerminal {
|
||||
pub fn new() -> Box<WinApiTerminal> {
|
||||
Box::from(WinApiTerminal {})
|
||||
}
|
||||
}
|
||||
|
||||
impl ITerminal for WinApiTerminal {
|
||||
|
||||
fn clear(&self, clear_type: ClearType) {
|
||||
fn clear(&self, clear_type: ClearType, context: &Context) {
|
||||
let csbi = kernel::get_console_screen_buffer_info();
|
||||
let pos = cursor().pos();
|
||||
let pos = cursor(&context).pos();
|
||||
|
||||
match clear_type
|
||||
{
|
||||
ClearType::All => clear_entire_screen(csbi),
|
||||
ClearType::FromCursorDown => clear_after_cursor(pos,csbi),
|
||||
ClearType::FromCursorUp => clear_before_cursor(pos, csbi),
|
||||
ClearType::CurrentLine => clear_current_line(pos, csbi),
|
||||
ClearType::UntilNewLine => clear_until_line(pos, csbi),
|
||||
ClearType::All => clear_entire_screen(csbi, &context),
|
||||
ClearType::FromCursorDown => clear_after_cursor(pos,csbi,&context),
|
||||
ClearType::FromCursorUp => clear_before_cursor(pos, csbi, &context),
|
||||
ClearType::CurrentLine => clear_current_line(pos, csbi, &context),
|
||||
ClearType::UntilNewLine => clear_until_line(pos, csbi,&context),
|
||||
};
|
||||
}
|
||||
|
||||
fn terminal_size(&self) -> (u16, u16) {
|
||||
fn terminal_size(&self, context: &Context) -> (u16, u16) {
|
||||
terminal::terminal_size()
|
||||
}
|
||||
|
||||
fn scroll_up(&self, count: i16) {
|
||||
fn scroll_up(&self, count: i16, context: &Context) {
|
||||
// yet to be inplemented
|
||||
}
|
||||
|
||||
fn scroll_down(&self, count: i16) {
|
||||
fn scroll_down(&self, count: i16, context: &Context) {
|
||||
let csbi = kernel::get_console_screen_buffer_info();
|
||||
let mut srct_window;
|
||||
|
||||
@ -60,7 +60,7 @@ impl ITerminal for WinApiTerminal {
|
||||
}
|
||||
|
||||
/// Set the current terminal size
|
||||
fn set_size(&self, width: i16, height: i16) {
|
||||
fn set_size(&self, width: i16, height: i16, context: &Context) {
|
||||
if width <= 0
|
||||
{
|
||||
panic!("Cannot set the terminal width lower than 1");
|
||||
@ -136,7 +136,7 @@ impl ITerminal for WinApiTerminal {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn clear_after_cursor(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO) {
|
||||
pub fn clear_after_cursor(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO, context: &Context) {
|
||||
let (mut x,mut y) = pos;
|
||||
|
||||
// if cursor position is at the outer right position
|
||||
@ -154,7 +154,7 @@ pub fn clear_after_cursor(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO) {
|
||||
clear(start_location,cells_to_write);
|
||||
}
|
||||
|
||||
pub fn clear_before_cursor(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO) {
|
||||
pub fn clear_before_cursor(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO, context: &Context) {
|
||||
let (xpos,ypos) = pos;
|
||||
|
||||
// one cell after cursor position
|
||||
@ -170,7 +170,7 @@ pub fn clear_before_cursor(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO) {
|
||||
clear(start_location, cells_to_write);
|
||||
}
|
||||
|
||||
pub fn clear_entire_screen(csbi: CONSOLE_SCREEN_BUFFER_INFO) {
|
||||
pub fn clear_entire_screen(csbi: CONSOLE_SCREEN_BUFFER_INFO, context: &Context) {
|
||||
// position x at start
|
||||
let x = 0;
|
||||
// position y at start
|
||||
@ -185,10 +185,10 @@ pub fn clear_entire_screen(csbi: CONSOLE_SCREEN_BUFFER_INFO) {
|
||||
clear( start_location, cells_to_write);
|
||||
|
||||
// put the cursor back at (0, 0)
|
||||
cursor().goto(0, 0);
|
||||
cursor(&context).goto(0, 0);
|
||||
}
|
||||
|
||||
pub fn clear_current_line(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO)
|
||||
pub fn clear_current_line(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO, context: &Context)
|
||||
{
|
||||
// position x at start
|
||||
let x = 0;
|
||||
@ -204,10 +204,10 @@ pub fn clear_current_line(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO)
|
||||
clear(start_location, cells_to_write);
|
||||
|
||||
// put the cursor back at 1 cell on current row
|
||||
cursor().goto(0, y);
|
||||
cursor(&context).goto(0, y);
|
||||
}
|
||||
|
||||
pub fn clear_until_line(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO)
|
||||
pub fn clear_until_line(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO, context: &Context)
|
||||
{
|
||||
let (x,y) = pos;
|
||||
|
||||
@ -219,7 +219,7 @@ pub fn clear_until_line(pos: (u16,u16), csbi: CONSOLE_SCREEN_BUFFER_INFO)
|
||||
clear(start_location, cells_to_write);
|
||||
|
||||
// put the cursor back at original cursor position
|
||||
cursor().goto(x,y);
|
||||
cursor(&context).goto(x,y);
|
||||
}
|
||||
|
||||
fn clear(
|
||||
|
Loading…
Reference in New Issue
Block a user