diff --git a/packages/autofmt/src/lib.rs b/packages/autofmt/src/lib.rs index a7a0bbbdf..9eeb82e7c 100644 --- a/packages/autofmt/src/lib.rs +++ b/packages/autofmt/src/lib.rs @@ -1,5 +1,6 @@ //! pretty printer for rsx! use dioxus_rsx::*; +use quote::ToTokens; use std::fmt::{self, Write}; mod prettyplease; @@ -15,7 +16,7 @@ pub fn fmt_block(block: &str) -> Option { Some(buf) } -pub fn write_ident(buf: &mut dyn Write, node: &BodyNode, indent: usize) -> fmt::Result { +pub fn write_ident(buf: &mut String, node: &BodyNode, indent: usize) -> fmt::Result { match node { BodyNode::Element(el) => { let Element { @@ -81,7 +82,66 @@ pub fn write_ident(buf: &mut dyn Write, node: &BodyNode, indent: usize) -> fmt:: write_tabs(buf, indent)?; writeln!(buf, "}}")?; } - BodyNode::Component(_) => { + BodyNode::Component(component) => { + let Component { + name, + body, + children, + manual_props, + } = component; + + let name = name.to_token_stream().to_string(); + + write_tabs(buf, indent)?; + writeln!(buf, "{name} {{")?; + + for field in body { + write_tabs(buf, indent + 1)?; + let name = &field.name; + match &field.content { + ContentField::ManExpr(exp) => { + let out = prettyplease::unparse_expr(exp); + writeln!(buf, "{}: {},", name, out)?; + } + ContentField::Formatted(s) => { + writeln!(buf, "{}: {},", name, s.value())?; + } + ContentField::OnHandlerRaw(exp) => { + let out = prettyplease::unparse_expr(exp); + let mut lines = out.split('\n').peekable(); + let first = lines.next().unwrap(); + write!(buf, "{}: {}", name, first)?; + for line in lines { + writeln!(buf)?; + write_tabs(buf, indent + 1)?; + write!(buf, "{}", line)?; + } + writeln!(buf, ",")?; + } + } + } + + if let Some(exp) = manual_props { + write_tabs(buf, indent + 1)?; + let out = prettyplease::unparse_expr(exp); + let mut lines = out.split('\n').peekable(); + let first = lines.next().unwrap(); + write!(buf, "..{}", first)?; + for line in lines { + writeln!(buf)?; + write_tabs(buf, indent + 1)?; + write!(buf, "{}", line)?; + } + writeln!(buf)?; + } + + for child in children { + write_ident(buf, child, indent + 1)?; + } + + write_tabs(buf, indent)?; + writeln!(buf, "}}")?; + // // write!(buf, "{}", " ".repeat(ident)) } diff --git a/packages/autofmt/tests/sink.rs b/packages/autofmt/tests/sink.rs index c35f996b7..62feeef59 100644 --- a/packages/autofmt/tests/sink.rs +++ b/packages/autofmt/tests/sink.rs @@ -53,9 +53,43 @@ fn parse_comment() { } "#; - // let parsed: CallBody = syn::parse_str(block).ok()?; - let parsed: TokenStream2 = syn::parse_str(block).unwrap(); dbg!(parsed); } + +#[test] +fn formats_component() { + let block = r#" + Component { + adsasd: "asd", // this is a comment + onclick: move |_| { + let blah = 120; + let blah = 120; + }, + } +"#; + + let formatted = fmt_block(block).unwrap(); + + print!("{formatted}"); +} + +#[test] +fn formats_component_man_props() { + let block = r#" + Component { + ..MyProps { + val: 123 + }, + adsasd: "asd", // this is a comment + onclick: move |_| { + let blah = 120; + }, + } +"#; + + let formatted = fmt_block(block).unwrap(); + + print!("{formatted}"); +} diff --git a/packages/rsx/src/component.rs b/packages/rsx/src/component.rs index dfdda74b8..158660baa 100644 --- a/packages/rsx/src/component.rs +++ b/packages/rsx/src/component.rs @@ -150,11 +150,11 @@ impl ToTokens for Component { // the struct's fields info pub struct ComponentField { - name: Ident, - content: ContentField, + pub name: Ident, + pub content: ContentField, } -enum ContentField { +pub enum ContentField { ManExpr(Expr), Formatted(LitStr), OnHandlerRaw(Expr),