use gpui::{Axis, Bounds, EntityId, Pixels};
#[derive(Clone, Copy, PartialEq, Eq, Hash, Debug, PartialOrd, Ord)]
pub struct NodeId(u64);
impl NodeId {
pub(crate) fn from_u64(raw: u64) -> Self {
Self(raw)
}
pub fn as_u64(self) -> u64 {
self.0
}
}
#[derive(Clone, Copy, PartialEq, Eq, Hash, Debug, PartialOrd, Ord)]
pub struct PanelId(u64);
impl PanelId {
pub fn from_u64(raw: u64) -> Self {
Self(raw)
}
pub fn as_u64(self) -> u64 {
self.0
}
}
impl From<EntityId> for PanelId {
fn from(id: EntityId) -> Self {
Self(id.as_u64())
}
}
#[derive(Clone, Copy, PartialEq, Debug)]
pub struct TilePanel {
panel: PanelId,
bounds: Bounds<Pixels>,
z_index: usize,
}
impl TilePanel {
pub fn new(panel: PanelId, bounds: Bounds<Pixels>) -> Self {
Self {
panel,
bounds,
z_index: 0,
}
}
pub fn with_z_index(mut self, z_index: usize) -> Self {
self.z_index = z_index;
self
}
pub fn with_bounds(mut self, bounds: Bounds<Pixels>) -> Self {
self.bounds = bounds;
self
}
pub fn panel(&self) -> PanelId {
self.panel
}
pub fn bounds(&self) -> Bounds<Pixels> {
self.bounds
}
pub fn z_index(&self) -> usize {
self.z_index
}
}
#[derive(Clone, PartialEq, Debug)]
pub(crate) enum NodeKind {
Split {
axis: Axis,
children: Vec<PaneNode>,
sizes: Vec<Option<Pixels>>,
},
Tabs {
panels: Vec<PanelId>,
active_ix: usize,
},
Tiles {
panels: Vec<TilePanel>,
},
}
pub enum PaneRef<'a> {
Split {
axis: Axis,
children: &'a [PaneNode],
sizes: &'a [Option<Pixels>],
},
Tabs {
panels: &'a [PanelId],
active_ix: usize,
},
Tiles {
panels: &'a [TilePanel],
},
}
#[derive(Clone, PartialEq, Debug)]
pub struct PaneNode {
id: NodeId,
kind: NodeKind,
}
impl PaneNode {
pub(crate) fn new(id: NodeId, kind: NodeKind) -> Self {
Self { id, kind }
}
pub fn id(&self) -> NodeId {
self.id
}
pub fn kind(&self) -> PaneRef<'_> {
match &self.kind {
NodeKind::Split {
axis,
children,
sizes,
} => PaneRef::Split {
axis: *axis,
children,
sizes,
},
NodeKind::Tabs { panels, active_ix } => PaneRef::Tabs {
panels,
active_ix: *active_ix,
},
NodeKind::Tiles { panels } => PaneRef::Tiles { panels },
}
}
pub(crate) fn kind_mut(&mut self) -> &mut NodeKind {
&mut self.kind
}
pub(crate) fn kind_ref(&self) -> &NodeKind {
&self.kind
}
pub fn walk(&self, f: &mut impl FnMut(&PaneNode)) {
f(self);
if let NodeKind::Split { children, .. } = &self.kind {
for child in children {
child.walk(f);
}
}
}
}