cg2 0.1.0

Rust code generator.
Documentation
use alloc::string::String;

use crate::repeat_char;

use crate::{Keyword, Punct};

#[derive(Debug, Default)]
pub struct Generator {
  code: String,
}

impl Generator {
  #[must_use]
  pub fn new() -> Self {
    Self {
      code: String::new(),
    }
  }

  #[must_use]
  pub fn code(&self) -> &String {
    &self.code
  }

  #[must_use]
  pub fn into_code(self) -> String {
    self.code
  }

  pub fn out(&mut self, s: &str) -> &mut Self {
    self.code.push_str(s);
    self
  }

  pub fn outc(&mut self, c: char) -> &mut Self {
    self.code.push(c);
    self
  }
}

impl Generator {
  pub fn space(&mut self) -> &mut Self {
    self.outc(' ')
  }

  pub fn line(&mut self) -> &mut Self {
    self.outc('\n')
  }

  pub fn lines(&mut self, n: usize) -> &mut Self {
    self.out(&repeat_char('\n', n))
  }

  pub fn punct(&mut self, p: Punct) -> &mut Self {
    self.outc(p as u8 as _)
  }

  pub fn keyword(&mut self, kw: Keyword) -> &mut Self {
    self.out(kw.as_str())
  }

  pub fn ident(&mut self, i: &str) -> &mut Self {
    self.out(i)
  }
}

impl Generator {
  impl_punct!(semi, Semi);
  impl_punct!(dot, Dot);
  impl_punct!(comma, Comma);
  impl_punct!(colon, Colon);
  impl_punct!(hash, Hash);
  impl_punct!(star, Star);
  impl_punct!(l_paren, LParen);
  impl_punct!(r_paren, RParen);
  impl_punct!(l_brace, LBrace);
  impl_punct!(r_brace, RBrace);
  impl_punct!(l_curly, LCurly);
  impl_punct!(r_curly, RCurly);
  impl_punct!(quote, Quote);
  impl_punct!(single_quote, SingleQuote);
}

impl Generator {
  impl_keyword!(public, Pub);
  impl_keyword!(not_safe, Unsafe);
  impl_keyword!(func, Fn);
  impl_keyword!(mutable, Mut);
  impl_keyword!(implement, Impl);
  impl_keyword!(variable, Let);
  impl_keyword!(constant, Const);
}

impl Generator {
  impl_alias!(deref, star);
}

macro_rules! impl_punct {
  ($fn:ident, $var:ident) => {
    pub fn $fn(&mut self) -> &mut Self {
      self.punct(Punct::$var)
    }
  };
}

macro_rules! impl_keyword {
  ($fn:ident, $var:ident) => {
    pub fn $fn(&mut self) -> &mut Self {
      self.keyword(Keyword::$var)
    }
  };
}

macro_rules! impl_alias {
  ($fn:ident, $alias:ident) => {
    pub fn $fn(&mut self) -> &mut Self {
      self.$alias()
    }
  };
}

use {impl_alias, impl_keyword, impl_punct};