1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63
//! Data types that are meant to be shared and read across Duat.
//!
//! The data types revolve around the [`RwLock<T>`] struct from std,
//! and are adapters that may block the mutation of the inner data,
//! for the purpose of making it available for reading to any
//! extension on Duat.
//!
//! The first data type is [`RwData<T>`], which is a read and write
//! wrapper over information. It should mostly not be shared, being
//! used instead to write information while making sure that no other
//! part of the code is still reading it. The second data type is
//! [`RoData<T>`], or read only data. It is derived from the first
//! one, and cannot mutate the inner data.
//!
//! The most common usecase for these data types is in the
//! [`FileWidget], where many readers
//! can peer into the [`Text`] or other useful
//! information, such as the printed lines, cursors, etc.
//!
//! [`FileWidget]: crate::FileWidget<U>
//! [`Text`]: crate::text::Text
pub use self::{
ro::RoData,
rw::{ReadWriteGuard, RwData},
statics::{CurrentFile, CurrentWidget, FileReader},
};
mod ro;
mod rw;
mod statics;
/// Private trait for the [`RwData`] and [`RoData`] structs.
///
/// [`RwData`]: super::RwData
/// [`RoData`]: super::RoData
pub trait Data<T>: private::InnerData<T>
where
T: ?Sized,
{
fn to_ro(&self) -> RoData<T>;
fn has_changed(&self) -> bool;
}
mod private {
use std::sync::{atomic::AtomicUsize, Arc};
use parking_lot::RwLockReadGuard;
pub trait InnerData<T: ?Sized> {
/// The data, usually an [`Arc`]
fn data(&self) -> RwLockReadGuard<'_, T>;
/// Attempt to get the data, that is usually an [`Arc`]
fn try_data(&self) -> Option<RwLockReadGuard<'_, T>>;
/// The most up to date state of the data.
fn cur_state(&self) -> &Arc<AtomicUsize>;
/// The last read state of the data.
fn read_state(&self) -> &AtomicUsize;
}
}