diff --git a/src/data_provider/sqlite.rs b/src/data_provider/sqlite.rs index 333661e..59e4d9d 100644 --- a/src/data_provider/sqlite.rs +++ b/src/data_provider/sqlite.rs @@ -24,6 +24,8 @@ fn create_tables(conn: &Connection) { make_card_stats(conn).expect("Failed to init table"); make_history(conn).expect("Failed to init table"); make_custom_fields(conn).expect("Failed to init table"); + make_exams(conn).expect("Failed to init table"); + make_exam_entry(conn).expect("Failed to init table"); } fn make_settings(conn: &Connection) -> Result<(), rusqlite::Error> { @@ -68,6 +70,18 @@ fn make_custom_fields(conn: &Connection) -> Result<(), rusqlite::Error> { Ok(()) } +fn make_exams(conn: &Connection) -> Result<(), rusqlite::Error> { + let query = include_str!("../../sql/exam.sql"); + conn.execute(query, ())?; + Ok(()) +} + +fn make_exam_entry(conn: &Connection) -> Result<(), rusqlite::Error> { + let query = include_str!("../../sql/exam_entry.sql"); + conn.execute(query, ())?; + Ok(()) +} + pub fn default_connection() -> Connection { let db_file = db_path(); let connection = Connection::open(db_file).expect("Failed to open database"); diff --git a/src/data_provider/web_api.rs b/src/data_provider/web_api.rs index a4fb725..31f31e1 100644 --- a/src/data_provider/web_api.rs +++ b/src/data_provider/web_api.rs @@ -1,9 +1,11 @@ use crate::fs::*; -use crate::notification::NotificationData::{CompressError, OpenFileError, PermissionDenied, WebApiUnavailable}; +use crate::notification::NotificationData::{ + CompressError, OpenFileError, PermissionDenied, WebApiUnavailable, +}; use crate::notification::{MaybeError, NotificationData}; use log::info; use std::io; -use tokio::fs::{remove_file, File, OpenOptions}; +use tokio::fs::{File, OpenOptions, remove_file}; use tokio::io::{AsyncReadExt, AsyncWriteExt}; use zstd::{DEFAULT_COMPRESSION_LEVEL, Decoder, Encoder}; @@ -49,10 +51,10 @@ pub async fn load_data(id: String, temp: bool) -> MaybeError { .get(&id_url) .send() .await - .map_err(|_| WebApiUnavailable)? + .map_err(|e| WebApiUnavailable)? .bytes() .await - .map_err(|_| WebApiUnavailable)? + .map_err(|e| WebApiUnavailable)? .to_vec(); let data = decompress(data)?; @@ -62,7 +64,7 @@ pub async fn load_data(id: String, temp: bool) -> MaybeError { tokio::fs::write(db_file, data) .await - .map_err(|_| PermissionDenied)?; + .map_err(|e| PermissionDenied)?; let version_url = format!("{API_URL}{id}/version"); let version = client @@ -74,8 +76,12 @@ pub async fn load_data(id: String, temp: bool) -> MaybeError { .await .map_err(|_| WebApiUnavailable)?; set_local_version(version.parse::().unwrap_or_default()).await?; - remove_file(db_wal()).await.map_err(|_| OpenFileError)?; - remove_file(db_wal()).await.map_err(|_| OpenFileError)?; + if db_wal().exists() { + remove_file(db_wal()).await.map_err(|_| OpenFileError)?; + } + if db_shm().exists() { + remove_file(db_shm()).await.map_err(|_| OpenFileError)?; + } Ok(()) } diff --git a/src/pages/sync.rs b/src/pages/sync.rs index 6205d35..0a61b5b 100644 --- a/src/pages/sync.rs +++ b/src/pages/sync.rs @@ -5,7 +5,7 @@ use crate::data_provider::web_api::*; use crate::jl_button; use crate::navigation::Page::PreviousPage; use crate::navigation::{NavigatedPage, Page, RootMessage}; -use crate::notification::{NotificationData, NotificationRequest}; +use crate::notification::{MaybeError, NotificationData, NotificationRequest}; use crate::pages::sync::SyncMessage::*; use crate::styling::*; use crate::{push_error, push_error_task}; @@ -115,12 +115,16 @@ impl NavigatedPage for SyncState { self.real_load = false; let id = self.state.sync_data.read().key.clone().unwrap(); + self.state.connection.lock().finish(); let tasks = Task::batch([ Task::perform( async { tokio::time::sleep(Duration::from_millis(200)).await }, |_| RootMessage::Sync(NextAnimation), ), - Task::perform(load_data(id, false), |_| RootMessage::Sync(NetworkFinished)), + Task::perform(load_data(id, false), |load_result| match load_result { + Ok(_) => RootMessage::Sync(NetworkFinished), + Err(error) => push_error!(error) + }), ]); return tasks; diff --git a/src/widgets/card_display.rs b/src/widgets/card_display.rs index cfbdd6c..81f31d3 100644 --- a/src/widgets/card_display.rs +++ b/src/widgets/card_display.rs @@ -1,7 +1,9 @@ use crate::data::entities::{CustomField, DeckSettings, WordData}; use crate::data::Id; use iced::widget::{button, center, column, rule, space, text}; +use iced_core::Alignment::Center; use iced_core::Length::Fill; +use crate::styling::HALF_SPACING; pub fn word_display<'a, T: 'a + Clone>( deck: &DeckSettings, @@ -64,9 +66,9 @@ fn property_draw<'a, T: 'a + Clone>( for part in parts { println!("displaying {}", part); match part { - "key" => column = column.push(text!("{}", word.key).size(48)), - "value" => column = column.push(text!("{}", word.value).size(28)), - "tags" => column = column.push(text!("{}", word.tags).size(28)), + "key" => column = column.push(text!("{}", word.key).align_x(Center).size(48)), + "value" => column = column.push(text!("{}", word.value).align_x(Center).size(28)), + "tags" => column = column.push(text!("{}", word.tags).align_x(Center).size(28)), "speech" => { column = column.push(button("Воспроизвести").on_press(speech_action.clone())) } @@ -74,29 +76,32 @@ fn property_draw<'a, T: 'a + Clone>( if part == "reading" && let Some(reading) = word.additional.get(&Id(1)) { - column = column.push(text!("{}", reading).size(24)) + column = column.push(text!("{}", reading).align_x(Center).size(24)); + continue } if part == "description" && let Some(description) = word.additional.get(&Id(2)) { - column = column.push(text!("{}", description).size(20)) + column = column.push(text!("{}", description).align_x(Center).size(20)); + continue } if part == "context" && let Some(context) = word.additional.get(&Id(3)) { - column = column.push(text!("{}", context).size(24)) + column = column.push(text!("{}", context).align_x(Center).size(24)); + continue } let field_id = fields_set.iter().find(|f| f.identifier == part); if let Some(id) = field_id && let Some(custom) = word.additional.get(&id.id) { - column = column.push(text!("{}", custom).size(24)) + column = column.push(text!("{}", custom).align_x(Center).size(24)) } } } } - column.into() + column.align_x(Center).spacing(HALF_SPACING).into() }