feat: localization support
This commit is contained in:
parent
e3e92a158a
commit
f48d78d03b
9 changed files with 106 additions and 26 deletions
|
|
@ -1 +1,6 @@
|
|||
not-found = We couldn't find that page.
|
||||
title = Hypergeometric Distribution Calculator
|
||||
population = Population Size
|
||||
successes = Successes in Population
|
||||
sample = Sample Size
|
||||
sample_successes = Successes in Sample
|
||||
|
|
|
|||
|
|
@ -1 +1,6 @@
|
|||
not-found = No pudimos encontrar esta página.
|
||||
title = Calculadora Distribución Hipergeométrica
|
||||
population = Tamaño población
|
||||
successes = Éxitos en la población
|
||||
sample = Tamaño de la muestra
|
||||
sample_successes = Éxitos en la muestra
|
||||
|
|
|
|||
|
|
@ -32,6 +32,11 @@ h6 {
|
|||
padding: 2rem;
|
||||
}
|
||||
|
||||
h1.title {
|
||||
width: 80vw;
|
||||
max-inline-size: 80vw;
|
||||
}
|
||||
|
||||
p {
|
||||
margin: var(--size-6);
|
||||
}
|
||||
|
|
@ -59,7 +64,7 @@ form input {
|
|||
|
||||
form > div.results {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr 6em 6em 1fr;
|
||||
grid-template-columns: 1fr 8em 5em 1fr;
|
||||
min-width: 20em;
|
||||
max-width: 30em;
|
||||
width: 30vw;
|
||||
|
|
|
|||
|
|
@ -1,9 +1,10 @@
|
|||
//! Hypergeometric Distribution Calculator
|
||||
use leptos::html::ElementChild;
|
||||
use leptos::prelude::{
|
||||
signal, ClassAttribute, Get, GlobalAttributes, OnTargetAttribute, PropAttribute, Set,
|
||||
ClassAttribute, Get, GlobalAttributes, OnTargetAttribute, PropAttribute, Set, signal,
|
||||
};
|
||||
use leptos::{component, view, IntoView};
|
||||
use leptos::{IntoView, component, view};
|
||||
use leptos_fluent::move_tr;
|
||||
|
||||
use crate::calc::hyper_geometric;
|
||||
|
||||
|
|
@ -26,7 +27,7 @@ pub fn Calculator() -> impl IntoView {
|
|||
view! {
|
||||
<form>
|
||||
<p>
|
||||
<label for="population">Population Size</label>
|
||||
<label for="population">{move_tr!("population")}</label>
|
||||
<input
|
||||
id="population"
|
||||
type="number"
|
||||
|
|
@ -38,7 +39,7 @@ pub fn Calculator() -> impl IntoView {
|
|||
/>
|
||||
</p>
|
||||
<p>
|
||||
<label for="successes">Successes in Population</label>
|
||||
<label for="successes">{move_tr!("successes")}</label>
|
||||
<input
|
||||
id="successes"
|
||||
type="number"
|
||||
|
|
@ -51,7 +52,7 @@ pub fn Calculator() -> impl IntoView {
|
|||
/>
|
||||
</p>
|
||||
<p>
|
||||
<label for="sample">Sample Size</label>
|
||||
<label for="sample">{move_tr!("sample")}</label>
|
||||
<input
|
||||
id="sample"
|
||||
type="number"
|
||||
|
|
@ -64,7 +65,7 @@ pub fn Calculator() -> impl IntoView {
|
|||
/>
|
||||
</p>
|
||||
<p>
|
||||
<label for="sample_successes">Successes in Sample</label>
|
||||
<label for="sample_successes">{move_tr!("sample_successes")}</label>
|
||||
<input
|
||||
id="sample_successes"
|
||||
type="number"
|
||||
|
|
|
|||
55
src/components/localization.rs
Normal file
55
src/components/localization.rs
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
//! Localization selector
|
||||
|
||||
use fluent_templates::static_loader;
|
||||
use leptos::html::ElementChild;
|
||||
use leptos::prelude::{Children, GlobalAttributes, OnAttribute, PropAttribute, Set};
|
||||
use leptos::{IntoView, component, view};
|
||||
use leptos_fluent::{Language, expect_i18n, leptos_fluent};
|
||||
|
||||
static_loader! {
|
||||
pub static TRANSLATIONS = {
|
||||
locales: "./locales",
|
||||
fallback_language: "en",
|
||||
};
|
||||
}
|
||||
|
||||
/// This component provide localization context to every children component.
|
||||
#[component]
|
||||
pub fn I18n(children: Children) -> impl IntoView {
|
||||
leptos_fluent! {
|
||||
children: children(),
|
||||
translations: [TRANSLATIONS],
|
||||
locales: "./locales",
|
||||
check_translations: "./src/**/*.rs",
|
||||
}
|
||||
}
|
||||
#[component]
|
||||
pub fn LanguageSelector() -> impl IntoView {
|
||||
// Use `expect_i18n()` to get the current i18n context:
|
||||
let i18n = expect_i18n();
|
||||
|
||||
view! {
|
||||
<label for="language">"A/文:"</label>
|
||||
<select id="language">
|
||||
{move || {
|
||||
i18n.languages.iter().map(|lang| render_language(lang)).collect::<Vec<_>>()
|
||||
}}
|
||||
</select>
|
||||
}
|
||||
}
|
||||
|
||||
fn render_language(lang: &'static Language) -> impl IntoView {
|
||||
// Passed as atrribute, `Language` is converted to their code,
|
||||
// so `<input id=lang` becomes `<input id=lang.id.to_string()`
|
||||
let i18n = expect_i18n();
|
||||
view! {
|
||||
<option
|
||||
id=lang
|
||||
value=lang
|
||||
prop:selected=lang.is_active()
|
||||
on:click=move |_| i18n.language.set(lang)
|
||||
>
|
||||
{lang.name}
|
||||
</option>
|
||||
}
|
||||
}
|
||||
|
|
@ -1 +1,2 @@
|
|||
pub mod calculator;
|
||||
pub mod localization;
|
||||
|
|
|
|||
13
src/lib.rs
13
src/lib.rs
|
|
@ -1,6 +1,5 @@
|
|||
use fluent_templates::static_loader;
|
||||
use leptos::prelude::{AddAnyAttr, IntoAttribute};
|
||||
use leptos::{component, view, IntoView};
|
||||
use leptos::{IntoView, component, view};
|
||||
use leptos_meta::*;
|
||||
use leptos_router::{components::*, path};
|
||||
|
||||
|
|
@ -12,14 +11,6 @@ mod pages;
|
|||
// Top-Level pages
|
||||
use crate::pages::home::Home;
|
||||
|
||||
// Localization
|
||||
static_loader! {
|
||||
pub static TRANSLATIONS = {
|
||||
locales: "./locales",
|
||||
fallback_language: "en",
|
||||
};
|
||||
}
|
||||
|
||||
/// An app router which renders the homepage and handles 404's
|
||||
#[component]
|
||||
pub fn App() -> impl IntoView {
|
||||
|
|
@ -30,7 +21,7 @@ pub fn App() -> impl IntoView {
|
|||
<Html attr:lang="en" attr:dir="ltr" attr:data-theme="light" />
|
||||
|
||||
// sets the document title
|
||||
<Title text="Welcome to Leptos CSR" />
|
||||
<Title text="Hypergeometric Calculator" />
|
||||
|
||||
// injects metadata in the <head> of the page
|
||||
<Meta charset="UTF-8" />
|
||||
|
|
|
|||
|
|
@ -2,9 +2,11 @@ use leptos::attr::global::ClassAttribute;
|
|||
use leptos::error::ErrorBoundary;
|
||||
use leptos::html::ElementChild;
|
||||
use leptos::prelude::{CollectView, Get};
|
||||
use leptos::{component, view, IntoView};
|
||||
use leptos::{IntoView, component, view};
|
||||
use leptos_fluent::move_tr;
|
||||
|
||||
use crate::components::calculator::Calculator;
|
||||
use crate::components::localization::{I18n, LanguageSelector};
|
||||
|
||||
/// Default Home Page
|
||||
#[component]
|
||||
|
|
@ -28,13 +30,21 @@ pub fn Home() -> impl IntoView {
|
|||
</ul>
|
||||
}
|
||||
}>
|
||||
<I18n>
|
||||
<header>
|
||||
<LanguageSelector />
|
||||
</header>
|
||||
<div class="container">
|
||||
<h1>"Hypergeometric Distribution Calculator"</h1>
|
||||
|
||||
<div class="calculator">
|
||||
<Title />
|
||||
<Calculator />
|
||||
</div>
|
||||
</div>
|
||||
</I18n>
|
||||
</ErrorBoundary>
|
||||
}
|
||||
}
|
||||
|
||||
/// Title
|
||||
#[component]
|
||||
pub fn Title() -> impl IntoView {
|
||||
view! {<h1 class="title">{move_tr!("title")}</h1>}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,8 +1,15 @@
|
|||
use leptos::html::ElementChild;
|
||||
use leptos::{component, view, IntoView};
|
||||
use leptos::{IntoView, component, view};
|
||||
use leptos_fluent::move_tr;
|
||||
|
||||
use crate::components::localization::I18n;
|
||||
|
||||
/// 404 Not Found Page
|
||||
#[component]
|
||||
pub fn NotFound() -> impl IntoView {
|
||||
view! { <h1>"We couldn't find that page."</h1> }
|
||||
view! {
|
||||
<I18n>
|
||||
<h1>{move_tr!("not-found")}</h1>
|
||||
</I18n>
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue