chromakitx 1.0.2

A comprehensive color manipulation library for Rust
Documentation
// SPDX-FileCopyrightText: 2023 CELESTIFYX Team
// SPDX-License-Identifier: GPL-3.0-or-later

use std::{
    ops::Add,

    fmt::{
        Display,
        Formatter,
        Result as FmtResult
    }
};

use crate::{
    ColorFormattable,
    Color,
    TextStyle
};

#[derive(Debug, Clone, PartialEq)]
pub struct ColoredString {
    content: String
}

impl ColoredString {
    pub fn new<T: ToString>(text: T) -> Self {
        Self {
            content: text.to_string()
        }
    }

    pub fn fg<C: ColorFormattable>(text: impl ToString, color: C) -> Self {
        let formatted: String = format!("{}{}{}", Color::new(color, false), text.to_string(), Color::new(TextStyle::Reset, false));

        Self {
            content: formatted
        }
    }

    pub fn bg<C: ColorFormattable>(text: impl ToString, color: C) -> Self {
        let formatted: String = format!("{}{}{}", Color::new(color, true), text.to_string(), Color::new(TextStyle::Reset, false));

        Self {
            content: formatted
        }
    }

    pub fn styled<F: ColorFormattable, B: ColorFormattable>(text: impl ToString, fg: F, bg: B) -> Self {
        let formatted: String = format!("{}{}{}{}", Color::new(bg, true), Color::new(fg, false), text.to_string(), Color::new(TextStyle::Reset, false));

        Self {
            content: formatted
        }
    }

    pub fn style<S: ColorFormattable>(text: impl ToString, style: S) -> Self {
        let formatted: String = format!("{}{}{}", Color::new(style, false), text.to_string(), Color::new(TextStyle::Reset, false));

        Self {
            content: formatted
        }
    }

    pub fn plain(text: impl ToString) -> Self {
        Self {
            content: text.to_string()
        }
    }

    pub fn append(&mut self, other: impl Into<ColoredString>) -> () {
        (&mut self.content).push_str(&other.into().content);
    }

    pub fn prepend(&mut self, other: impl Into<ColoredString>) -> () {
        let new_content: String = format!("{}{}", other.into().content, self.content);
        self.content = new_content;
    }

    pub fn as_str(&self) -> &str {
        &self.content
    }

    pub fn len(&self) -> usize {
        self.content.len()
    }

    pub fn is_empty(&self) -> bool {
        self.content.is_empty()
    }

    pub fn clear(&mut self) {
        (&mut self.content).clear();
    }

    pub fn bold(self) -> Self {
        self.apply_style(TextStyle::Bold)
    }

    pub fn dim(self) -> Self {
        self.apply_style(TextStyle::Dim)
    }

    pub fn italic(self) -> Self {
        self.apply_style(TextStyle::Italic)
    }

    pub fn underline(self) -> Self {
        self.apply_style(TextStyle::Underline)
    }

    pub fn blink(self) -> Self {
        self.apply_style(TextStyle::Blink)
    }

    pub fn blink_rapid(self) -> Self {
        self.apply_style(TextStyle::BlinkRapid)
    }

    pub fn reverse(self) -> Self {
        self.apply_style(TextStyle::Reverse)
    }

    pub fn hidden(self) -> Self {
        self.apply_style(TextStyle::Hidden)
    }

    pub fn strikethrough(self) -> Self {
        self.apply_style(TextStyle::Strikethrough)
    }

    pub fn reset(self) -> Self {
        self.apply_style(TextStyle::Reset)
    }

    fn apply_style(self, style: TextStyle) -> Self {
        let styled_content: String = format!("{}{}{}", Color::new(style, false), self.content, Color::new(TextStyle::Reset, false));

        Self {
            content: styled_content
        }
    }

    pub fn color<C: ColorFormattable>(self, color: C) -> Self {
        let colored_content: String = format!("{}{}{}", Color::new(color, false), self.content, Color::new(TextStyle::Reset, false));

        Self {
            content: colored_content
        }
    }

    pub fn on_color<C: ColorFormattable>(self, color: C) -> Self {
        let bg_content: String = format!("{}{}{}", Color::new(color, true), self.content, Color::new(TextStyle::Reset, false));

        Self {
            content: bg_content
        }
    }
}

impl Display for ColoredString {
    fn fmt(&self, f: &mut Formatter<'_>) -> FmtResult {
        write!(f, "{}", self.content)
    }
}

impl From<String> for ColoredString {
    fn from(s: String) -> Self {
        Self::plain(s)
    }
}

impl From<&str> for ColoredString {
    fn from(s: &str) -> Self {
        Self::plain(s)
    }
}

impl From<ColoredString> for String {
    fn from(cs: ColoredString) -> Self {
        cs.content
    }
}

impl Add for ColoredString {
    type Output = Self;

    fn add(self, other: Self) -> Self {
        Self {
            content: format!("{}{}", self.content, other.content)
        }
    }
}

impl Add<&str> for ColoredString {
    type Output = Self;

    fn add(self, other: &str) -> Self {
        Self {
            content: format!("{}{}", self.content, other)
        }
    }
}

impl Add<String> for ColoredString {
    type Output = Self;

    fn add(self, other: String) -> Self {
        Self {
            content: format!("{}{}", self.content, other)
        }
    }
}

impl Add<ColoredString> for &ColoredString {
    type Output = ColoredString;

    fn add(self, other: ColoredString) -> ColoredString {
        ColoredString {
            content: format!("{}{}", self.content, other.content)
        }
    }
}

impl Add<&ColoredString> for ColoredString {
    type Output = Self;

    fn add(self, other: &Self) -> Self {
        Self {
            content: format!("{}{}", self.content, other.content)
        }
    }
}

impl Add<&ColoredString> for &ColoredString {
    type Output = ColoredString;

    fn add(self, other: &ColoredString) -> ColoredString {
        ColoredString {
            content: format!("{}{}", self.content, other.content)
        }
    }
}

impl AsRef<str> for ColoredString {
    fn as_ref(&self) -> &str {
        &self.content
    }
}