diff --git a/.editorconfig b/.editorconfig index c8ff2d9..988b5f7 100644 --- a/.editorconfig +++ b/.editorconfig @@ -4,12 +4,14 @@ root = true [*] charset = utf-8 indent_style = space - -[*.js] -quote_type = single indent_size = 2 insert_final_newline = true trim_trailing_whitespace = true +end_of_line = lf +max_line_length = 120 + +[*.js] +quote_type = single [*.yml] indent_size = 2 diff --git a/.vscode/extensions.json b/.vscode/extensions.json index ac0db24..230fd66 100644 --- a/.vscode/extensions.json +++ b/.vscode/extensions.json @@ -1,10 +1,11 @@ { - "recommendations": [ - "rust-lang.rust-analyzer", - "bradlc.vscode-tailwindcss", - "tamasfe.even-better-toml", - "esbenp.prettier-vscode", - "aaron-bond.better-comments", - "arrterian.nix-env-selector" - ] -} \ No newline at end of file + "recommendations": [ + "rust-lang.rust-analyzer", + "bradlc.vscode-tailwindcss", + "tamasfe.even-better-toml", + "esbenp.prettier-vscode", + "aaron-bond.better-comments", + "arrterian.nix-env-selector", + "editorconfig.editorconfig" + ] +} diff --git a/.vscode/settings.json b/.vscode/settings.json index 69f44f0..0ed9a1b 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -16,13 +16,16 @@ "comments": "on", "strings": true }, + "editor.formatOnSave": true, + "editor.defaultFormatter": "esbenp.prettier-vscode", + "editor.codeActionsOnSave": { + "source.organizeImports": "explicit" + }, "[rust]": { - "editor.defaultFormatter": "rust-lang.rust-analyzer", - "editor.formatOnSave": true + "editor.defaultFormatter": "rust-lang.rust-analyzer" }, "[javascript]": { "editor.defaultFormatter": "esbenp.prettier-vscode", - "editor.formatOnSave": true, "tailwindCSS.experimental.classRegex": ["'@apply([^']*)':"] }, diff --git a/build.rs b/build.rs index e87ecd6..3225be5 100644 --- a/build.rs +++ b/build.rs @@ -3,41 +3,41 @@ use std::io::Write; use std::process::Command; fn main() { - let _ = Command::new("npm") - .args(["run", "build"]) - .output() - .expect("Falha ao executar npm run build"); + let _ = Command::new("npm") + .args(["run", "build"]) + .output() + .expect("Falha ao executar npm run build"); - create_markdown_posts_with_files_to_include(); + create_markdown_posts_with_files_to_include(); } fn create_markdown_posts_with_files_to_include() { - let posts_folder = "./posts"; + let posts_folder = "./posts"; - let mut out_file = - fs::File::create("src/markdown_posts.rs").expect("Falha ao criar o arquivo de saída"); + let mut out_file = + fs::File::create("src/markdown_posts.rs").expect("Falha ao criar o arquivo de saída"); - writeln!(out_file, "// Generated By build.rs").unwrap(); - writeln!(out_file, "pub const FILES: &[(&str, &str)] = &[").unwrap(); + writeln!(out_file, "// Generated By build.rs").unwrap(); + writeln!(out_file, "pub const FILES: &[(&str, &str)] = &[").unwrap(); - let files = fs::read_dir(posts_folder).expect("Falha ao listar os arquivos no diretório"); + let files = fs::read_dir(posts_folder).expect("Falha ao listar os arquivos no diretório"); - for file in files { - let file = file.expect("Falha ao ler o arquivo"); - let path = file.path(); + for file in files { + let file = file.expect("Falha ao ler o arquivo"); + let path = file.path(); - if path.is_file() && path.extension().map_or(false, |ext| ext == "md") { - let file_name = path.file_stem().unwrap().to_str().unwrap(); + if path.is_file() && path.extension().map_or(false, |ext| ext == "md") { + let file_name = path.file_stem().unwrap().to_str().unwrap(); - writeln!( - out_file, - " (\"{}\", include_str!(\"../{}\")),", - file_name, - path.display() - ) - .unwrap(); - } + writeln!( + out_file, + " (\"{}\", include_str!(\"../{}\")),", + file_name, + path.display() + ) + .unwrap(); } + } - writeln!(out_file, "];").unwrap(); + writeln!(out_file, "];").unwrap(); } diff --git a/rustfmt.toml b/rustfmt.toml new file mode 100644 index 0000000..b196eaa --- /dev/null +++ b/rustfmt.toml @@ -0,0 +1 @@ +tab_spaces = 2 diff --git a/src/components/back_to_top.rs b/src/components/back_to_top.rs index 5098132..07bd664 100644 --- a/src/components/back_to_top.rs +++ b/src/components/back_to_top.rs @@ -4,28 +4,28 @@ use web_sys::{ScrollBehavior, ScrollToOptions}; #[component] pub fn BackToTopBtn() -> impl IntoView { - let (_, y) = use_window_scroll(); + let (_, y) = use_window_scroll(); - let opacity_btn = move || { - if y() > 300.0 { - 1 - } else { - 0 - } - }; + let opacity_btn = move || { + if y() > 300.0 { + 1 + } else { + 0 + } + }; - let on_click_go_to_top = |_| { - let options = ScrollToOptions::default(); - options.set_behavior(ScrollBehavior::Smooth); - options.set_top(0.0); - window().scroll_to_with_scroll_to_options(&options); - }; + let on_click_go_to_top = |_| { + let options = ScrollToOptions::default(); + options.set_behavior(ScrollBehavior::Smooth); + options.set_top(0.0); + window().scroll_to_with_scroll_to_options(&options); + }; - view! { -
- -
- } + view! { +
+ +
+ } } diff --git a/src/components/card.rs b/src/components/card.rs index 27a0148..367599b 100644 --- a/src/components/card.rs +++ b/src/components/card.rs @@ -2,9 +2,9 @@ use leptos::*; #[component] pub fn Card(#[prop(optional, into)] class: String, children: Children) -> impl IntoView { - view! { -
- {children()} -
- } + view! { +
+ {children()} +
+ } } diff --git a/src/components/content.rs b/src/components/content.rs index 9501755..4394e2c 100644 --- a/src/components/content.rs +++ b/src/components/content.rs @@ -6,38 +6,38 @@ use wasm_bindgen::prelude::*; #[wasm_bindgen(module = "/esbuild/js/highlight.min.js")] extern "C" { - fn highlight_all(); + fn highlight_all(); } #[component] pub fn BaseContent( - #[prop(into)] title: String, - #[prop(optional_no_strip)] bg_img: Option, - #[prop(optional_no_strip)] bg_color: Option, - #[prop(optional, into)] created_date: Option>, - #[prop(into)] back_href: String, - #[prop(optional, into)] inner_html: Option, - #[prop(optional)] children: Option, + #[prop(into)] title: String, + #[prop(optional_no_strip)] bg_img: Option, + #[prop(optional_no_strip)] bg_color: Option, + #[prop(optional, into)] created_date: Option>, + #[prop(into)] back_href: String, + #[prop(optional, into)] inner_html: Option, + #[prop(optional)] children: Option, ) -> impl IntoView { - create_effect(move |_| highlight_all()); + create_effect(move |_| highlight_all()); - view! { -
-
-

{title}

- -

Criado em {created_date.map(|d| d.format("%d-%m-%Y").to_string())}

-
- - - -
-
- {children.map(|c| c())} -
-
- } + view! { +
+
+

{title}

+ +

Criado em {created_date.map(|d| d.format("%d-%m-%Y").to_string())}

+
+ + + +
+
+ {children.map(|c| c())} +
+
+ } } diff --git a/src/components/dark_mode.rs b/src/components/dark_mode.rs index cec9baf..84d23a7 100644 --- a/src/components/dark_mode.rs +++ b/src/components/dark_mode.rs @@ -4,30 +4,30 @@ use leptos_use::{use_color_mode, ColorMode, UseColorModeReturn}; #[component] pub fn DarkModeToggleBtn() -> impl IntoView { - let UseColorModeReturn { mode, set_mode, .. } = use_color_mode(); + let UseColorModeReturn { mode, set_mode, .. } = use_color_mode(); - let toggle = move |_| { - if mode() == ColorMode::Dark { - set_mode(ColorMode::Light); - } else { - set_mode(ColorMode::Dark); - } - }; - - let icon = move || { - if mode() == ColorMode::Dark { - "fa-solid fa-moon tw-w-[14px]" - } else { - "fa-solid fa-sun" - } - }; + let toggle = move |_| { + if mode() == ColorMode::Dark { + set_mode(ColorMode::Light); + } else { + set_mode(ColorMode::Dark); + } + }; - view! { - -
- -
+ let icon = move || { + if mode() == ColorMode::Dark { + "fa-solid fa-moon tw-w-[14px]" + } else { + "fa-solid fa-sun" } + }; + + view! { + +
+ +
+ } } diff --git a/src/components/divider.rs b/src/components/divider.rs index d38e1e2..28e43dd 100644 --- a/src/components/divider.rs +++ b/src/components/divider.rs @@ -2,7 +2,7 @@ use leptos::*; #[component] pub fn Divider() -> impl IntoView { - view! { -
- } + view! { +
+ } } diff --git a/src/components/nav_menu.rs b/src/components/nav_menu.rs index 1e49821..cf81ed3 100644 --- a/src/components/nav_menu.rs +++ b/src/components/nav_menu.rs @@ -4,83 +4,83 @@ use leptos_use::on_click_outside; #[component] pub fn NavMenu() -> impl IntoView { - let (display_menu, set_display_menu) = create_signal(false); + let (display_menu, set_display_menu) = create_signal(false); - let show_menu = move |_| set_display_menu(true); - let close_menu = move |_| set_display_menu(false); + let show_menu = move |_| set_display_menu(true); + let close_menu = move |_| set_display_menu(false); - let menu_ref = create_node_ref::(); + let menu_ref = create_node_ref::(); - let _ = on_click_outside(menu_ref, close_menu); + let _ = on_click_outside(menu_ref, close_menu); - let items = vec![ - NavItem { - href: "/", - fa_icon: "home", - label: "Home", - }, - NavItem { - href: "about", - fa_icon: "user-circle", - label: "Sobre", - }, - NavItem { - href: "posts", - fa_icon: "book", - label: "Posts", - }, - NavItem { - href: "projects", - fa_icon: "cogs", - label: "Projetos", - }, - ]; + let items = vec![ + NavItem { + href: "/", + fa_icon: "home", + label: "Home", + }, + NavItem { + href: "about", + fa_icon: "user-circle", + label: "Sobre", + }, + NavItem { + href: "posts", + fa_icon: "book", + label: "Posts", + }, + NavItem { + href: "projects", + fa_icon: "cogs", + label: "Projetos", + }, + ]; - let linkItems = items - .into_iter() - .map(|i| view! { }) - .collect_view(); + let linkItems = items + .into_iter() + .map(|i| view! { }) + .collect_view(); - view! { - - } + view! { + + } } #[component] fn NavLinkItem(item: NavItem) -> impl IntoView { - view! { -
  • - -
    - -
    - {item.label} -
    -
  • - } + view! { +
  • + +
    + +
    + {item.label} +
    +
  • + } } #[component] fn NavButton() -> impl IntoView { - view! { - - } + view! { + + } } #[derive(Clone)] struct NavItem { - href: &'static str, - fa_icon: &'static str, - label: &'static str, + href: &'static str, + fa_icon: &'static str, + label: &'static str, } diff --git a/src/contexts/posts.rs b/src/contexts/posts.rs index 8816b2d..4da13b8 100644 --- a/src/contexts/posts.rs +++ b/src/contexts/posts.rs @@ -7,47 +7,47 @@ pub struct PostContext(Vec); #[component] pub fn PostsProvider(children: Children) -> impl IntoView { - let posts = get_posts_data(); + let posts = get_posts_data(); - provide_context(PostContext(posts)); + provide_context(PostContext(posts)); - children() + children() } pub fn use_posts() -> Vec { - use_context::().unwrap().0 + use_context::().unwrap().0 } fn get_posts_data() -> Vec { - use crate::markdown_posts::FILES; - use gray_matter::{engine::YAML, Matter}; - use markdown::{to_html_with_options, Options}; + use crate::markdown_posts::FILES; + use gray_matter::{engine::YAML, Matter}; + use markdown::{to_html_with_options, Options}; - let mut options = Options::default(); + let mut options = Options::default(); - options.compile.allow_dangerous_html = true; - options.parse.constructs.frontmatter = true; + options.compile.allow_dangerous_html = true; + options.parse.constructs.frontmatter = true; - let mut posts: Vec = FILES - .iter() - .map(|file| { - let matter = Matter::::new(); - let path = file.0.to_owned(); - let markdown = matter.parse(file.1); + let mut posts: Vec = FILES + .iter() + .map(|file| { + let matter = Matter::::new(); + let path = file.0.to_owned(); + let markdown = matter.parse(file.1); - let metadata: PostMetadata = markdown.data.unwrap().deserialize().unwrap(); - let content = to_html_with_options(file.1, &options).unwrap(); + let metadata: PostMetadata = markdown.data.unwrap().deserialize().unwrap(); + let content = to_html_with_options(file.1, &options).unwrap(); - PostData { - path, - metadata, - content, - } - }) - .collect(); + PostData { + path, + metadata, + content, + } + }) + .collect(); - posts.sort_by_key(|p| p.metadata.date); - posts.reverse(); + posts.sort_by_key(|p| p.metadata.date); + posts.reverse(); - posts + posts } diff --git a/src/js/highlight.js b/src/js/highlight.js index 61c4950..2e15df9 100644 --- a/src/js/highlight.js +++ b/src/js/highlight.js @@ -1,7 +1,5 @@ import hljs from 'highlight.js/lib/common'; - export function highlight_all() { - hljs.highlightAll() - console.log("Fui chamado") + hljs.highlightAll(); } diff --git a/src/lib.rs b/src/lib.rs index 5d2f905..f5cad96 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -21,46 +21,46 @@ use crate::components::dark_mode::DarkModeToggleBtn; #[component] pub fn App() -> impl IntoView { - // Provides context that manages stylesheets, titles, meta tags, etc. - provide_meta_context(); + // Provides context that manages stylesheets, titles, meta tags, etc. + provide_meta_context(); - let title_formatter = |text: String| { - let base_title: String = "SeraphyBR`s Blog".into(); + let title_formatter = |text: String| { + let base_title: String = "SeraphyBR`s Blog".into(); - if text.is_empty() { - base_title - } else { - format!("{text} - {base_title}") - } - }; + if text.is_empty() { + base_title + } else { + format!("{text} - {base_title}") + } + }; - view! { - + view! { + - // sets the document title - + // sets the document title + <Title formatter=title_formatter /> - // injects metadata in the <head> of the page - <Meta charset="UTF-8"/> - <Meta name="viewport" content="width=device-width, initial-scale=1.0"/> + // injects metadata in the <head> of the page + <Meta charset="UTF-8"/> + <Meta name="viewport" content="width=device-width, initial-scale=1.0"/> - <ErrorBoundaryPage> - <PostsProvider> - <Router> - <NavMenu /> - <DarkModeToggleBtn /> - <Routes> - <Route path="/" view=HomePage/> - <Route path="posts" view=PostListPage/> - <Route path="posts/:path" view=PostPage/> - <Route path="projects" view=ProjectsListPage/> - <Route path="projects/:path" view=ProjectPage/> - <Route path="about" view=AboutPage/> - <Route path="404" view=NotFoundPage/> - <Route path="/*" view=NotFoundPage/> - </Routes> - </Router> - </PostsProvider> - </ErrorBoundaryPage> - } + <ErrorBoundaryPage> + <PostsProvider> + <Router> + <NavMenu /> + <DarkModeToggleBtn /> + <Routes> + <Route path="/" view=HomePage/> + <Route path="posts" view=PostListPage/> + <Route path="posts/:path" view=PostPage/> + <Route path="projects" view=ProjectsListPage/> + <Route path="projects/:path" view=ProjectPage/> + <Route path="about" view=AboutPage/> + <Route path="404" view=NotFoundPage/> + <Route path="/*" view=NotFoundPage/> + </Routes> + </Router> + </PostsProvider> + </ErrorBoundaryPage> + } } diff --git a/src/main.rs b/src/main.rs index b7b1087..b1d4982 100644 --- a/src/main.rs +++ b/src/main.rs @@ -2,13 +2,13 @@ use leptos::*; use seraphybr_page::App; fn main() { - // set up logging - _ = console_log::init_with_level(log::Level::Debug); - console_error_panic_hook::set_once(); + // set up logging + _ = console_log::init_with_level(log::Level::Debug); + console_error_panic_hook::set_once(); - mount_to_body(|| { - view! { - <App /> - } - }) + mount_to_body(|| { + view! { + <App /> + } + }) } diff --git a/src/markdown_posts.rs b/src/markdown_posts.rs index 4f28e91..8ce9d60 100644 --- a/src/markdown_posts.rs +++ b/src/markdown_posts.rs @@ -1,7 +1,19 @@ // Generated By build.rs pub const FILES: &[(&str, &str)] = &[ - ("2019-02-12-Motivacionais", include_str!(".././posts/2019-02-12-Motivacionais.md")), - ("2019-02-19-SonhosDoFuturoTec", include_str!(".././posts/2019-02-19-SonhosDoFuturoTec.md")), - ("2019-02-12-Primeiro-teste", include_str!(".././posts/2019-02-12-Primeiro-teste.md")), - ("2019-03-24-Dotfiles", include_str!(".././posts/2019-03-24-Dotfiles.md")), + ( + "2019-02-12-Motivacionais", + include_str!(".././posts/2019-02-12-Motivacionais.md"), + ), + ( + "2019-02-19-SonhosDoFuturoTec", + include_str!(".././posts/2019-02-19-SonhosDoFuturoTec.md"), + ), + ( + "2019-02-12-Primeiro-teste", + include_str!(".././posts/2019-02-12-Primeiro-teste.md"), + ), + ( + "2019-03-24-Dotfiles", + include_str!(".././posts/2019-03-24-Dotfiles.md"), + ), ]; diff --git a/src/models/posts.rs b/src/models/posts.rs index c98d5ba..e5335b4 100644 --- a/src/models/posts.rs +++ b/src/models/posts.rs @@ -3,22 +3,22 @@ use serde::Deserialize; #[derive(Deserialize, Debug, Clone)] pub struct PostMetadata { - pub title: String, - pub date: DateTime<Utc>, + pub title: String, + pub date: DateTime<Utc>, - pub front_image: Option<String>, - pub front_color: Option<String>, + pub front_image: Option<String>, + pub front_color: Option<String>, - #[serde(default)] - pub brief: String, + #[serde(default)] + pub brief: String, - #[serde(default)] - pub project: bool, + #[serde(default)] + pub project: bool, } #[derive(Debug, Clone)] pub struct PostData { - pub path: String, - pub metadata: PostMetadata, - pub content: String, + pub path: String, + pub metadata: PostMetadata, + pub content: String, } diff --git a/src/pages/about.rs b/src/pages/about.rs index 84a5818..b1d3a31 100644 --- a/src/pages/about.rs +++ b/src/pages/about.rs @@ -5,62 +5,62 @@ use crate::{components::content::BaseContent, pages::base::BasePage}; #[component] pub fn AboutPage() -> impl IntoView { - view! { - <BasePage title="Sobre mim" enable_back_to_top=true> - <BaseContent - title="Sobre mim" - bg_color=Some("#4ce16599".to_string()) - bg_img=Some("url('/img/aboutme.jpg')".to_string()) - back_href="/" - > - <AboutContent /> - </BaseContent> - </BasePage> - } + view! { + <BasePage title="Sobre mim" enable_back_to_top=true> + <BaseContent + title="Sobre mim" + bg_color=Some("#4ce16599".to_string()) + bg_img=Some("url('/img/aboutme.jpg')".to_string()) + back_href="/" + > + <AboutContent /> + </BaseContent> + </BasePage> + } } #[component] fn AboutContent() -> impl IntoView { - let age = Utc::now().year() - 1999; + let age = Utc::now().year() - 1999; - view! { - <ul> - <li>Meu nome é Luiz Junio e tenho {age} anos</li> - <li>Uso SeraphyBR como meu Nickname na internet, originalmente para usar em MMORPGs.</li> - <li> - Minha foto de perfil no github, e algumas outras contas, é uma imagem muito antiga que encontrei na internet, - se trata do Digimon Dorumon (Um personagem fictício) com suas cores trocadas. - </li> - </ul> + view! { + <ul> + <li>Meu nome é Luiz Junio e tenho {age} anos</li> + <li>Uso SeraphyBR como meu Nickname na internet, originalmente para usar em MMORPGs.</li> + <li> + Minha foto de perfil no github, e algumas outras contas, é uma imagem muito antiga que encontrei na internet, + se trata do Digimon Dorumon (Um personagem fictício) com suas cores trocadas. + </li> + </ul> - <h2>Sobre este blog</h2> + <h2>Sobre este blog</h2> - <ul> - <li>Esse blog havia sido originalmente criado para uma atividade de uma disciplina enquanto fazia minha graduação em Ciência da Computação</li> - <li> - Seu propósito inicial era para postar coisas que acharia uteis compartilhar, de coisas que aprendi e/ou vi na internet. - Mas o objetivo principal atualmente é para servir como um portifolio dos meus projetos que compartilho em plataformas como Github e - contar sobre a experiencia e aprendizado obtido com isso. Esse blog por si só tambem se inclui nisso, pois eu mesmo o desenvolvi sem usar plataformas - prontas como Medium e outros, justamente para colocar minhas habilidades em prática. - </li> - <li> - A primeira versão desse blog foi criado em meados de 2019 usando <a href="https://jekyllrb.com/">Jekyll</a>, que era bem conhecido na época como - um bom gerador de site estático que dava suporte a temas e tinha um suporte para ser hospedado de forma simplificada nas plataformas do Github Pages - e Gitlab Pages, e fazia o trabalho de converter os arquivos markdown nas páginas. Nessa época eu não tinha muito conhecimento de Frontend, mas ao mesmo tempo - não queria usar algo como Wordpress ou Blogger "(que outros colegas do curso optaram)" porque queria experimentar algo diferente. - Então foi o que eu fiz, encontrei um tema de template pro Jeklly que se chamava Moon, dei uma leve remodelada em cores, icones e bordas - para ficar no meu gosto, e criei meus primeiros posts em markdown, a pedido da disciplina do curso. - </li> - <li> - Em 2024, após todas as experiencias que adquiri durante o Curso, estágio e trabalho, eu finalmente dei inicio ao projeto de - reescrever todo o Blog em tecnologias mais modernas, onde eu teria muito mais controle, entenderia de fato como funciona, me sentiria mais orgulhoso e ainda - poderia colocar em prática meus conhecimentos em desenvolvimento Web e demais tecnologias, mantendo-se o mais fiel possível - ao design do meu primeiro Blog com Jeklly, que eu já me sentia confortável e ajudaria no processo. - </li> - <li> - Mais detalhes técnicos sobre o desenvolvimento desse Blog, processo de decisão de escolha das tecnologias usadas, design, e paralelos com o original em Jeklly, - estarão presentes na parte de Projetos. - </li> - </ul> - } + <ul> + <li>Esse blog havia sido originalmente criado para uma atividade de uma disciplina enquanto fazia minha graduação em Ciência da Computação</li> + <li> + Seu propósito inicial era para postar coisas que acharia uteis compartilhar, de coisas que aprendi e/ou vi na internet. + Mas o objetivo principal atualmente é para servir como um portifolio dos meus projetos que compartilho em plataformas como Github e + contar sobre a experiencia e aprendizado obtido com isso. Esse blog por si só tambem se inclui nisso, pois eu mesmo o desenvolvi sem usar plataformas + prontas como Medium e outros, justamente para colocar minhas habilidades em prática. + </li> + <li> + A primeira versão desse blog foi criado em meados de 2019 usando <a href="https://jekyllrb.com/">Jekyll</a>, que era bem conhecido na época como + um bom gerador de site estático que dava suporte a temas e tinha um suporte para ser hospedado de forma simplificada nas plataformas do Github Pages + e Gitlab Pages, e fazia o trabalho de converter os arquivos markdown nas páginas. Nessa época eu não tinha muito conhecimento de Frontend, mas ao mesmo tempo + não queria usar algo como Wordpress ou Blogger "(que outros colegas do curso optaram)" porque queria experimentar algo diferente. + Então foi o que eu fiz, encontrei um tema de template pro Jeklly que se chamava Moon, dei uma leve remodelada em cores, icones e bordas + para ficar no meu gosto, e criei meus primeiros posts em markdown, a pedido da disciplina do curso. + </li> + <li> + Em 2024, após todas as experiencias que adquiri durante o Curso, estágio e trabalho, eu finalmente dei inicio ao projeto de + reescrever todo o Blog em tecnologias mais modernas, onde eu teria muito mais controle, entenderia de fato como funciona, me sentiria mais orgulhoso e ainda + poderia colocar em prática meus conhecimentos em desenvolvimento Web e demais tecnologias, mantendo-se o mais fiel possível + ao design do meu primeiro Blog com Jeklly, que eu já me sentia confortável e ajudaria no processo. + </li> + <li> + Mais detalhes técnicos sobre o desenvolvimento desse Blog, processo de decisão de escolha das tecnologias usadas, design, e paralelos com o original em Jeklly, + estarão presentes na parte de Projetos. + </li> + </ul> + } } diff --git a/src/pages/base.rs b/src/pages/base.rs index e186983..1934992 100644 --- a/src/pages/base.rs +++ b/src/pages/base.rs @@ -6,20 +6,20 @@ use crate::components::card::Card; #[component] pub fn BasePage( - #[prop(optional, into)] title: String, - #[prop(optional, into)] class: String, - #[prop(optional, into)] enable_back_to_top: bool, - children: Children, + #[prop(optional, into)] title: String, + #[prop(optional, into)] class: String, + #[prop(optional, into)] enable_back_to_top: bool, + children: Children, ) -> impl IntoView { - view! { - <Title text=title /> - <div class="tw-flex tw-justify-center tw-items-center tw-mt-auto tw-mb-auto tw-pt-7 tw-pb-7"> - <Card class> - {children()} - </Card> - </div> - <Show when=move || enable_back_to_top> - <BackToTopBtn/> - </Show> - } + view! { + <Title text=title /> + <div class="tw-flex tw-justify-center tw-items-center tw-mt-auto tw-mb-auto tw-pt-7 tw-pb-7"> + <Card class> + {children()} + </Card> + </div> + <Show when=move || enable_back_to_top> + <BackToTopBtn/> + </Show> + } } diff --git a/src/pages/error.rs b/src/pages/error.rs index 11815dd..d8c0277 100644 --- a/src/pages/error.rs +++ b/src/pages/error.rs @@ -4,40 +4,40 @@ use crate::pages::base::BasePage; #[component] pub fn ErrorBoundaryPage(children: Children) -> impl IntoView { - view! { - <ErrorBoundary fallback=error> - {children()} - </ErrorBoundary> - } + view! { + <ErrorBoundary fallback=error> + {children()} + </ErrorBoundary> + } } fn error(errors: RwSignal<Errors>) -> impl IntoView { - view! { - <BasePage title="Error"> - <div class="tw-flex tw-flex-col tw-gap-4"> - <div class="tw-flex tw-flex-col tw-gap-1 tw-justify-center tw-items-center tw-text-red-900 tw-text-3xl tw-font-bold"> - <i class="fa-solid fa-exclamation-circle"></i> - <h1> - "Ops! Algo deu errado!" - </h1> - </div> + view! { + <BasePage title="Error"> + <div class="tw-flex tw-flex-col tw-gap-4"> + <div class="tw-flex tw-flex-col tw-gap-1 tw-justify-center tw-items-center tw-text-red-900 tw-text-3xl tw-font-bold"> + <i class="fa-solid fa-exclamation-circle"></i> + <h1> + "Ops! Algo deu errado!" + </h1> + </div> - <p> - {"Um erro inesperado aconteceu. Por favor, tente novamente recarregando a página, e reporte o erro."} - </p> + <p> + {"Um erro inesperado aconteceu. Por favor, tente novamente recarregando a página, e reporte o erro."} + </p> - <p class="tw-text-lg tw-font-medium">"Erros:"</p> + <p class="tw-text-lg tw-font-medium">"Erros:"</p> - <ul> - {move || { - errors - .get() - .into_iter() - .map(|(_, e)| view! { <li>{e.to_string()}</li> }) - .collect_view() - }} - </ul> - </div> - </BasePage> - } + <ul> + {move || { + errors + .get() + .into_iter() + .map(|(_, e)| view! { <li>{e.to_string()}</li> }) + .collect_view() + }} + </ul> + </div> + </BasePage> + } } diff --git a/src/pages/home.rs b/src/pages/home.rs index d1020ec..8a3f134 100644 --- a/src/pages/home.rs +++ b/src/pages/home.rs @@ -5,42 +5,42 @@ use crate::{components::divider::Divider, pages::base::BasePage}; #[component] pub fn HomePage() -> impl IntoView { - view! { - <BasePage title="Home" class="!tw-max-w-lg"> - <div class="tw-vflex tw-justify-center tw-items-center tw-gap-2"> - <img src="/img/logo.png" class="tw-mx-auto tw-rounded-[50%] tw-w-36 tw-h-36 tw-animate-rotateIn"/> - <h3 class="tw-text-xl tw-font-light">"SeraphyBR's Blog"</h3> - <Divider /> - <h3 class="tw-text-base tw-font-light">"Desenvolvedor - Página em construção"</h3> - <Divider /> - <div class="tw-hflex tw-gap-5"> - <A href="mailto:luisjuniorbr@gmail.com" class="tw-btn-primary !tw-text-3xl"> - <i class="fa fa-envelope-square"/> - </A> + view! { + <BasePage title="Home" class="!tw-max-w-lg"> + <div class="tw-vflex tw-justify-center tw-items-center tw-gap-2"> + <img src="/img/logo.png" class="tw-mx-auto tw-rounded-[50%] tw-w-36 tw-h-36 tw-animate-rotateIn"/> + <h3 class="tw-text-xl tw-font-light">"SeraphyBR's Blog"</h3> + <Divider /> + <h3 class="tw-text-base tw-font-light">"Desenvolvedor - Página em construção"</h3> + <Divider /> + <div class="tw-hflex tw-gap-5"> + <A href="mailto:luisjuniorbr@gmail.com" class="tw-btn-primary !tw-text-3xl"> + <i class="fa fa-envelope-square"/> + </A> - <A href="https://github.com/seraphybr" class="tw-btn-primary !tw-text-3xl"> - <i class="fa-brands fa-github"/> - </A> + <A href="https://github.com/seraphybr" class="tw-btn-primary !tw-text-3xl"> + <i class="fa-brands fa-github"/> + </A> - <A href="https://t.me/seraphybr" class="tw-btn-primary !tw-text-3xl"> - <i class="fa-brands fa-telegram"/> - </A> - </div> - <Divider /> - <div class="tw-hflex tw-gap-5"> - <A href="about" class="tw-btn-primary !tw-text-base !tw-font-normal !tw-min-w-24"> - Sobre - </A> + <A href="https://t.me/seraphybr" class="tw-btn-primary !tw-text-3xl"> + <i class="fa-brands fa-telegram"/> + </A> + </div> + <Divider /> + <div class="tw-hflex tw-gap-5"> + <A href="about" class="tw-btn-primary !tw-text-base !tw-font-normal !tw-min-w-24"> + Sobre + </A> - <A href="posts" class="tw-btn-primary !tw-text-base !tw-font-normal !tw-min-w-24"> - Posts - </A> + <A href="posts" class="tw-btn-primary !tw-text-base !tw-font-normal !tw-min-w-24"> + Posts + </A> - <A href="projects" class="tw-btn-primary !tw-text-base !tw-font-normal !tw-min-w-24"> - Projetos - </A> - </div> - </div> - </BasePage> - } + <A href="projects" class="tw-btn-primary !tw-text-base !tw-font-normal !tw-min-w-24"> + Projetos + </A> + </div> + </div> + </BasePage> + } } diff --git a/src/pages/not_found.rs b/src/pages/not_found.rs index 8622311..5764364 100644 --- a/src/pages/not_found.rs +++ b/src/pages/not_found.rs @@ -4,15 +4,15 @@ use crate::pages::base::BasePage; #[component] pub fn NotFoundPage() -> impl IntoView { - view! { - <BasePage title="404"> - <div class="tw-flex tw-justify-center tw-items-center tw-m-9"> - <div class="tw-text-center"> - <i class="fas fa-compass tw-text-5xl tw-mb-4"></i> - <h1 class="tw-text-3xl tw-font-bold tw-mb-2">404</h1> - <p class="tw-text-xl">A página não existe, ou não é mais acessivel!<br/>Use o botão de navegação para voltar.</p> - </div> - </div> - </BasePage> - } + view! { + <BasePage title="404"> + <div class="tw-flex tw-justify-center tw-items-center tw-m-9"> + <div class="tw-text-center"> + <i class="fas fa-compass tw-text-5xl tw-mb-4"></i> + <h1 class="tw-text-3xl tw-font-bold tw-mb-2">404</h1> + <p class="tw-text-xl">A página não existe, ou não é mais acessivel!<br/>Use o botão de navegação para voltar.</p> + </div> + </div> + </BasePage> + } } diff --git a/src/pages/posts.rs b/src/pages/posts.rs index dd601b6..96a8118 100644 --- a/src/pages/posts.rs +++ b/src/pages/posts.rs @@ -10,79 +10,80 @@ use crate::{contexts::posts::use_posts, models::posts::PostMetadata, pages::base #[component] pub fn PostListPage() -> impl IntoView { - let posts = use_posts(); + let posts = use_posts(); - view! { - <BasePage title="Todos os Posts"> - <div class="tw-vflex tw-justify-center tw-items-center tw-gap-5 tw-text-neutral-800 dark:tw-text-white tw-p-8"> - <div class="tw-vflex tw-items-center tw-gap-6 tw-pb-12"> - <h1 class="tw-text-3xl tw-font-bold tw-text-center">Todas as postagens</h1> - <A href="/" class="tw-btn-primary"><i class="fa fa-home"></i></A> - </div> - <ul class="tw-vflex tw-gap-8"> - { - posts.into_iter() - .filter(|p| !p.metadata.project) - .map(|p| view! { <PostItem path=p.path metadata=p.metadata /> }) - .collect_view() - } - </ul> - </div> - </BasePage> - } + view! { + <BasePage title="Todos os Posts"> + <div class="tw-vflex tw-justify-center tw-items-center tw-gap-5 tw-text-neutral-800 dark:tw-text-white tw-p-8"> + <div class="tw-vflex tw-items-center tw-gap-6 tw-pb-12"> + <h1 class="tw-text-3xl tw-font-bold tw-text-center">Todas as postagens</h1> + <A href="/" class="tw-btn-primary"><i class="fa fa-home"></i></A> + </div> + <ul class="tw-vflex tw-gap-8"> + { + posts.into_iter() + .filter(|p| !p.metadata.project) + .map(|p| view! { <PostItem path=p.path metadata=p.metadata /> }) + .collect_view() + } + </ul> + </div> + </BasePage> + } } #[component] fn PostItem(path: String, metadata: PostMetadata) -> impl IntoView { - view! { - <li class="tw-vflex tw-gap-4"> - <A href=path.clone() class="tw-font-bold tw-text-xl tw-text-clickable-colors">{metadata.title}</A> - <p class="tw-font-light tw-text-base">{metadata.brief}</p> - <A href=path class="tw-btn-primary">Ler Mais</A> - </li> - } + view! { + <li class="tw-vflex tw-gap-4"> + <A href=path.clone() class="tw-font-bold tw-text-xl tw-text-clickable-colors">{metadata.title}</A> + <p class="tw-font-light tw-text-base">{metadata.brief}</p> + <A href=path class="tw-btn-primary">Ler Mais</A> + </li> + } } #[derive(Params, PartialEq, Clone)] struct PostPageUrlParams { - path: String, + path: String, } #[component] pub fn PostPage() -> impl IntoView { - let params = use_params::<PostPageUrlParams>(); + let params = use_params::<PostPageUrlParams>(); - move || { - let path = params.get().map(|p| p.path).unwrap_or_default(); + move || { + let path = params.get().map(|p| p.path).unwrap_or_default(); - let posts = use_posts(); + let posts = use_posts(); - let post = posts - .into_iter() - .filter(|p| !p.metadata.project) - .find(|p| p.path == path); + let post = posts + .into_iter() + .filter(|p| !p.metadata.project) + .find(|p| p.path == path); - post.map(|p| view! { <PostContentPage post=p/> }) - .or_else(|| Some(view! { <Redirect path="/404"/> })) - .into_view() - } + post + .map(|p| view! { <PostContentPage post=p/> }) + .or_else(|| Some(view! { <Redirect path="/404"/> })) + .into_view() + } } #[component] fn PostContentPage(post: PostData) -> impl IntoView { - let bg_img = post.metadata.front_image.map(|bg| format!("url({bg})")); + let bg_img = post.metadata.front_image.map(|bg| format!("url({bg})")); - view! { - <BasePage title=post.metadata.title.clone() enable_back_to_top=true> - <BaseContent - title=post.metadata.title - bg_color=post.metadata.front_color - bg_img=bg_img - created_date=post.metadata.date - inner_html=post.content - back_href="/posts" - > - </BaseContent> - </BasePage> - } + view! { + <BasePage title=post.metadata.title.clone() enable_back_to_top=true> + <BaseContent + title=post.metadata.title + bg_color=post.metadata.front_color + bg_img=bg_img + created_date=post.metadata.date + inner_html=post.content + back_href="/posts" + > + </BaseContent> + </BasePage> + } } diff --git a/src/pages/projects.rs b/src/pages/projects.rs index 6116547..898e202 100644 --- a/src/pages/projects.rs +++ b/src/pages/projects.rs @@ -2,99 +2,99 @@ use leptos::*; use leptos_router::{use_params, Params, Redirect, A}; use crate::{ - components::content::BaseContent, - contexts::posts::use_posts, - models::posts::{PostData, PostMetadata}, - pages::base::BasePage, + components::content::BaseContent, + contexts::posts::use_posts, + models::posts::{PostData, PostMetadata}, + pages::base::BasePage, }; #[component] pub fn ProjectsListPage() -> impl IntoView { - let posts = use_posts(); + let posts = use_posts(); - view! { - <BasePage title="Projetos"> - <div class="tw-vflex tw-justify-center tw-items-center tw-gap-5 tw-text-neutral-800 dark:tw-text-white tw-p-8"> - <div class="tw-vflex tw-items-center tw-gap-6 tw-pb-12"> - <h1 class="tw-text-3xl tw-font-bold tw-text-center">Projetos</h1> - <A href="/" class="tw-btn-primary"><i class="fa fa-home"></i></A> - </div> - <div class="tw-grid tw-grid-cols-1 md:tw-grid-cols-2 lg:tw-grid-cols-3 tw-gap-4"> - { - posts.into_iter() - .filter(|p| p.metadata.project) - .map(|p| view! { <ProjectItem path=p.path metadata=p.metadata /> }) - .collect_view() - } - </div> - </div> - </BasePage> - } + view! { + <BasePage title="Projetos"> + <div class="tw-vflex tw-justify-center tw-items-center tw-gap-5 tw-text-neutral-800 dark:tw-text-white tw-p-8"> + <div class="tw-vflex tw-items-center tw-gap-6 tw-pb-12"> + <h1 class="tw-text-3xl tw-font-bold tw-text-center">Projetos</h1> + <A href="/" class="tw-btn-primary"><i class="fa fa-home"></i></A> + </div> + <div class="tw-grid tw-grid-cols-1 md:tw-grid-cols-2 lg:tw-grid-cols-3 tw-gap-4"> + { + posts.into_iter() + .filter(|p| p.metadata.project) + .map(|p| view! { <ProjectItem path=p.path metadata=p.metadata /> }) + .collect_view() + } + </div> + </div> + </BasePage> + } } #[component] fn ProjectItem(path: String, metadata: PostMetadata) -> impl IntoView { - view! { - <div class="tw-max-w-sm tw-rounded-xl tw-overflow-hidden tw-shadow-lg dark:tw-shadow-none dark:tw-border-2 dark:tw-bg-graphite tw-border-clickable-colors"> - <img - class="tw-w-full tw-h-36" - src=metadata.front_image - alt="" - style:background-color=metadata.front_color - /> - <A href=path class="tw-text-clickable-colors"> - <div class="tw-px-6 tw-py-4"> - <div class="tw-font-bold tw-text-xl tw-mb-2">{metadata.title}</div> - <p class="tw-text-base"> - {metadata.brief} - </p> - </div> - </A> - </div> - } + view! { + <div class="tw-max-w-sm tw-rounded-xl tw-overflow-hidden tw-shadow-lg dark:tw-shadow-none dark:tw-border-2 dark:tw-bg-graphite tw-border-clickable-colors"> + <img + class="tw-w-full tw-h-36" + src=metadata.front_image + alt="" + style:background-color=metadata.front_color + /> + <A href=path class="tw-text-clickable-colors"> + <div class="tw-px-6 tw-py-4"> + <div class="tw-font-bold tw-text-xl tw-mb-2">{metadata.title}</div> + <p class="tw-text-base"> + {metadata.brief} + </p> + </div> + </A> + </div> + } } #[derive(Params, PartialEq, Clone)] struct ProjectPageUrlParams { - path: String, + path: String, } #[component] pub fn ProjectPage() -> impl IntoView { - let params = use_params::<ProjectPageUrlParams>(); + let params = use_params::<ProjectPageUrlParams>(); - move || { - let path = params.get().map(|p| p.path).unwrap_or_default(); + move || { + let path = params.get().map(|p| p.path).unwrap_or_default(); - let posts = use_posts(); + let posts = use_posts(); - let project = posts - .into_iter() - .filter(|p| p.metadata.project) - .find(|p| p.path == path); + let project = posts + .into_iter() + .filter(|p| p.metadata.project) + .find(|p| p.path == path); - project - .map(|p| view! { <ProjectContentPage post=p/> }) - .or_else(|| Some(view! { <Redirect path="/404"/> })) - .into_view() - } + project + .map(|p| view! { <ProjectContentPage post=p/> }) + .or_else(|| Some(view! { <Redirect path="/404"/> })) + .into_view() + } } #[component] fn ProjectContentPage(post: PostData) -> impl IntoView { - let bg_img = post.metadata.front_image.map(|bg| format!("url({bg})")); + let bg_img = post.metadata.front_image.map(|bg| format!("url({bg})")); - view! { - <BasePage title=post.metadata.title.clone() enable_back_to_top=true> - <BaseContent - title=post.metadata.title - bg_color=post.metadata.front_color - bg_img=bg_img - created_date=post.metadata.date - inner_html=post.content - back_href="/projects" - > - </BaseContent> - </BasePage> - } + view! { + <BasePage title=post.metadata.title.clone() enable_back_to_top=true> + <BaseContent + title=post.metadata.title + bg_color=post.metadata.front_color + bg_img=bg_img + created_date=post.metadata.date + inner_html=post.content + back_href="/projects" + > + </BaseContent> + </BasePage> + } }