#[derive(Debug, Clone, Copy, PartialEq)]
pub enum InlineBoxKind {
InFlow { width: f64, height: f64 },
OutOfFlow,
CustomOutOfFlow,
}
#[derive(Debug, Clone, Copy, PartialEq)]
pub struct InlineBox {
pub id: u64,
pub kind: InlineBoxKind,
}
impl InlineBox {
pub fn in_flow(id: u64, width: f64, height: f64) -> Self {
Self { id, kind: InlineBoxKind::InFlow { width: width.max(0.0), height: height.max(0.0) } }
}
pub fn out_of_flow(id: u64) -> Self {
Self { id, kind: InlineBoxKind::OutOfFlow }
}
pub fn custom_out_of_flow(id: u64) -> Self {
Self { id, kind: InlineBoxKind::CustomOutOfFlow }
}
pub fn width(&self) -> f64 {
match self.kind {
InlineBoxKind::InFlow { width, .. } => width,
InlineBoxKind::OutOfFlow | InlineBoxKind::CustomOutOfFlow => 0.0,
}
}
pub fn height(&self) -> f64 {
match self.kind {
InlineBoxKind::InFlow { height, .. } => height,
InlineBoxKind::OutOfFlow | InlineBoxKind::CustomOutOfFlow => 0.0,
}
}
pub fn ascent(&self) -> f64 {
self.height()
}
pub fn descent(&self) -> f64 {
0.0
}
}
#[derive(Debug, Clone, Copy, PartialEq)]
pub struct InlineBoxSlot {
pub run_index: usize,
pub byte_offset: usize,
pub inline_box: InlineBox,
}
impl InlineBoxSlot {
pub fn new(run_index: usize, byte_offset: usize, inline_box: InlineBox) -> Self {
Self { run_index, byte_offset, inline_box }
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn in_flow_reports_its_own_width_height_and_bottom_on_baseline_metrics() {
let b = InlineBox::in_flow(1, 24.0, 40.0);
assert_eq!(b.width(), 24.0);
assert_eq!(b.height(), 40.0);
assert_eq!(b.ascent(), 40.0);
assert_eq!(b.descent(), 0.0);
}
#[test]
fn in_flow_clamps_negative_dimensions_to_zero() {
let b = InlineBox::in_flow(2, -5.0, -1.0);
assert_eq!(b.width(), 0.0);
assert_eq!(b.height(), 0.0);
}
#[test]
fn out_of_flow_variants_contribute_nothing_to_wrap_or_baseline() {
let a = InlineBox::out_of_flow(3);
let b = InlineBox::custom_out_of_flow(4);
for box_ in [a, b] {
assert_eq!(box_.width(), 0.0);
assert_eq!(box_.height(), 0.0);
assert_eq!(box_.ascent(), 0.0);
assert_eq!(box_.descent(), 0.0);
}
}
}