fml 0.1.0

Friendly Markup Language
use std::io::{self, ErrorKind::Unsupported};

#[derive(Debug, PartialEq, Eq, PartialOrd, Ord)]
pub struct Content(pub Vec<Section>);

// #[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Clone, Hash)]
// pub struct Values(pub Vec<FmlValue>);

type Values = Vec<FmlValue>;

#[derive(Debug, PartialEq, Eq, PartialOrd, Ord)]
pub struct Section(pub Values);

// TODO: separate fmlval parser from section n content parser
// make an intermediate enum that holds either a ToProcess(Token) or Ready(FmlValue)
// make the parser a facade and apply post processing to the intermediate result before returning ast

#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Clone, Hash)]
pub enum FmlValue {
	/// Equivalent of HTML's <h1>, spans entire line. "# "
	Heading1(Values),
	/// Equivalent of HTML's <h2>, spans entire line. "## "
	Heading2(Values),
	/// Equivalent of HTML's <h3>, spans entire line. "### "
	Heading3(Values),

	/// Superscript spanning the entire line. "#^"
	Superline(Values),
	/// Subscript spanning the entire line. "#_" or "#!"
	Subline(Values),

	/// Bold text "*"
	Bold(Values),
	/// Italicized text "_"
	Italic(Values),
	/// Strikethrough text "~"
	Strikethrough(Values),

	/// Quote, is its own section. "> "
	Quote(Values),
	/// List item. "- "
	ListItem(Values),

	/// Used as an intermediary form in parsing.\
	/// Gets swapped to a specific function call later on.
	Function(FmlFunction),

	/// Superscript. "^{body}"
	Superscript(Values),
	/// Subscript. "_{body}"
	Subscript(Values),
	/// Underlined text. "__"
	Underline(Values),

	/// Colored foreground, uses HTML color name or 6-digit hexadecimal RRGGBB with a "0x" or "#" prefix.\
	/// "#fg<blue>{body}" or "#color<0x00FF00>{body}"
	ColorFg(FmlColor),

	/// Colored background, uses HTML color name or 6-digit hexadecimal RRGGBB with a "0x" or "#" prefix.\
	/// "#bg<blue>{body}" or "#bg<0x00FF00>{body}"
	ColorBg(FmlColor),

	/// Content-warning. "#cw<reason>{body}" or "|spoiler|"
	ContentWarning { reason: String, body: Values },

	/// Code-block, optional `lang` var for syntax-highlighting. "```"
	CodeBlock { lang: Option<String>, body: String },

	/// Newline, for convenience between environments.
	Newline,

	/// Inline code. "`"
	InlineCode(String),
	/// Typst block. Its body gets passed to the typst compiler.
	Typst(String),

	/// Bottom-most element of every other FmlValue,
	/// a catch-all for whatever does not belong in the other tokens.
	Text(String),
}

#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Clone, Hash)]
pub struct FmlFunction {
	pub name: String,
	pub params: Option<String>,
	pub body: Values,
}

#[derive(Debug, PartialEq, Eq, PartialOrd, Ord, Clone, Hash)]
pub struct FmlColor {
	pub color: String,
	pub body: Values,
}