summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/view.rs110
1 files changed, 103 insertions, 7 deletions
diff --git a/src/view.rs b/src/view.rs
index 38cfa58..6953496 100644
--- a/src/view.rs
+++ b/src/view.rs
@@ -1,21 +1,49 @@
+extern crate console_error_panic_hook;
use crate::pdfgen;
use wasm_bindgen::prelude::*;
use js_sys;
use yew::prelude::*;
+use vcard::{VCard, VCardError};
+use std::panic;
-struct Form {
+fn init() {
+ panic::set_hook(Box::new(console_error_panic_hook::hook));
+}
+
+pub struct Form {
+ link: ComponentLink<Self>,
+ error: Option<String>,
+ formatted_name: String,
+ generated_vcard: Option<String>,
+}
+
+pub enum Msg {
+ UpdateFormattedName(String),
+ GenerateVCard,
+ Nope,
}
impl Component for Form {
- type Message = ();
+ type Message = Msg;
type Properties = ();
- fn create(_props: Self::Properties, _link: ComponentLink<Self>) -> Self {
- Self { }
+ fn create(_props: Self::Properties, link: ComponentLink<Self>) -> Self {
+ Self { link, error: None, formatted_name: String::new(), generated_vcard: None }
}
- fn update(&mut self, _msg: Self::Message) -> ShouldRender {
- false
+ fn update(&mut self, msg: Self::Message) -> ShouldRender {
+ match msg {
+ Msg::UpdateFormattedName(value) => self.formatted_name = String::from(value),
+ Msg::GenerateVCard => {
+ match self.generate_vcard() {
+ Ok(vcard) => self.generated_vcard = Some(vcard.to_string()),
+ Err(VCardError::FormatError(err)) => self.error = Some(err.to_string()),
+ Err(VCardError::EmptyFormatName) => self.error = Some(String::from("A VCard should have at least one formatted name.")),
+ };
+ }
+ Msg::Nope => (),
+ };
+ true
}
fn change(&mut self, _props: Self::Properties) -> ShouldRender {
@@ -23,19 +51,87 @@ impl Component for Form {
}
fn view(&self) -> Html {
+
+ let raw = pdfgen::genpdf();
+ let data = base64::encode(&raw);
+ let uri_component: String = js_sys::encode_uri_component(&data).into();
+ let href = format!{"data:application/pdf;base64,{}", uri_component };
+
+ let formatted_name_input = self.link.callback(|e: ChangeData|
+ match e {
+ ChangeData::Value(v) => Msg::UpdateFormattedName(v),
+ _ => Msg::Nope,
+ }
+ );
+
+ html!{
+ <div id="form" >
+ { self.render_error() }
+ <label for="formatted_name">{ "Formatted Name" }</label>
+ <input type="text" id="formatted_name" onchange=formatted_name_input/>
+ <input id="prefix"/>
+ <input id="first_name"/>
+ <input id="middle_name"/>
+ <input id="last_name"/>
+ <input id="suffix"/>
+ <button id="generate-vcard" class="button primary small" onclick=self.link.callback(|_| Msg::GenerateVCard)>{ "Generate VCard" }</button>
+
+ { self.render_pdf() } { self.render_vcard() }
+ </div>
+ }
+ }
+}
+
+impl Form {
+ fn generate_vcard(&self) -> Result<VCard, VCardError> {
+ match VCard::from_formatted_name_str(&self.formatted_name) {
+ Ok(vcard) => Ok(vcard),
+ Err(err) => Err(err),
+ }
+ }
+ fn render_error(&self) -> Html {
+ if self.error.is_some() {
+ html!{
+ <div class="alert danger">
+ <p>{ self.error.as_ref().unwrap() }</p>
+ </div>
+ }
+ } else {
+ html!{}
+ }
+ }
+ fn render_pdf(&self) -> Html {
let raw = pdfgen::genpdf();
let data = base64::encode(&raw);
let uri_component: String = js_sys::encode_uri_component(&data).into();
let href = format!{"data:application/pdf;base64,{}", uri_component };
+
html!{
- <a href=href download="demo.pdf" >
+ <a href=href download="demo.pdf" class="button success small" >
{ "Download PDF" }
</a>
}
}
+ fn render_vcard(&self) -> Html {
+ if self.generated_vcard.is_some() {
+ let data = base64::encode(self.generated_vcard.as_ref().unwrap());
+ let uri_component: String = js_sys::encode_uri_component(&data).into();
+ let href = format!("data:text/vcard;base64,{}", uri_component);
+
+ html!{
+ <a href=href download=format!("{}.vcs",self.formatted_name) class="button success small">
+ { "Download vCard" }
+ </a>
+ }
+ } else {
+ html!{}
+ }
+ }
}
+
#[wasm_bindgen(start)]
pub fn run_app() {
+ init();
App::<Form>::new().mount_to_body();
} \ No newline at end of file