Fix display and sync bugs

This commit is contained in:
micialware committed 2026-10-03 21:27:13 +03:00
1 parent 5b2b48c88f
commit 0b23da9eda
4 files changed
+45 -16

No files matched your search

+14
View File
@@ -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");
+12 -6
View File
@@ -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::<u32>().unwrap_or_default()).await?;
if db_wal().exists() {
remove_file(db_wal()).await.map_err(|_| OpenFileError)?;
remove_file(db_wal()).await.map_err(|_| OpenFileError)?;
}
if db_shm().exists() {
remove_file(db_shm()).await.map_err(|_| OpenFileError)?;
}
Ok(())
}
+6 -2
View File
@@ -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<SyncMessage> 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;
+13 -8
View File
@@ -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()
}