hlctl/src/hlwm/tag.rs

99 lines
2.4 KiB
Rust

use std::{
fmt::{Display, Write},
str::FromStr,
};
use serde::{Deserialize, Serialize};
use strum::IntoEnumIterator;
use super::parser::ParseError;
pub struct TagStatus {
name: String,
state: TagState,
}
#[allow(unused)]
impl TagStatus {
pub fn name(&self) -> &str {
&self.name
}
pub fn state(&self) -> TagState {
self.state
}
}
impl FromStr for TagStatus {
type Err = ParseError;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let mut parts = s.chars();
let state = parts
.next()
.ok_or(ParseError::InvalidCommand(s.to_string()))?
.try_into()?;
let name = parts.collect();
Ok(Self { name, state })
}
}
#[derive(Debug, Clone, Copy, Serialize, Deserialize, strum::EnumIter)]
pub enum TagState {
Empty,
NotEmpty,
/// The tag contains an urgent window
Urgent,
/// The tag is viewed on the specified MONITOR and it is focused
SameMonitorFocused,
/// The tag is viewed on the specified MONITOR, but this monitor is not focused
SameMonitor,
/// The tag is viewed on a different MONITOR and it is focused
DifferentMonitorFocused,
/// The tag is viewed on a different MONITOR, but this monitor is not focused
DifferentMonitor,
}
impl TryFrom<char> for TagState {
type Error = ParseError;
fn try_from(value: char) -> Result<Self, Self::Error> {
Self::iter()
.into_iter()
.find(|i| char::from(i) == value)
.ok_or(ParseError::InvalidCommand(value.to_string()))
}
}
impl FromStr for TagState {
type Err = ParseError;
fn from_str(s: &str) -> Result<Self, Self::Err> {
Self::iter()
.into_iter()
.find(|i| i.to_string() == s)
.ok_or(ParseError::InvalidCommand(s.to_string()))
}
}
impl From<&TagState> for char {
fn from(value: &TagState) -> Self {
match value {
TagState::SameMonitorFocused => '#',
TagState::SameMonitor => '+',
TagState::DifferentMonitorFocused => '%',
TagState::DifferentMonitor => '-',
TagState::Empty => '.',
TagState::NotEmpty => ':',
TagState::Urgent => '!',
}
}
}
impl Display for TagState {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
f.write_char(self.into())
}
}