use crate::{
ActiveTopologyBond, Annotation, EntityKind, EntityRef, Guide, InteractionEdge, LigandPoseBatch,
Measurement, Mesh, Primitive, Scene,
};
#[cfg(test)]
#[path = "provenance_tests.rs"]
mod tests;
#[derive(Clone, Copy, Debug)]
pub struct EntityProvenance<'a> {
pub entity: EntityRef,
pub entry: &'a molframe::EntryMetadata,
pub detail: ProvenanceDetail<'a>,
}
#[derive(Clone, Copy, Debug)]
#[non_exhaustive]
pub enum ProvenanceDetail<'a> {
Atom(molframe::AtomRef<'a>),
Bond(molframe::BondRecord),
DynamicBond(&'a ActiveTopologyBond),
Interaction(&'a InteractionEdge),
Guide(&'a Guide),
Annotation(&'a Annotation),
Measurement(&'a Measurement),
Primitive(&'a Primitive),
LigandPoseBatch(&'a LigandPoseBatch),
Mesh(&'a Mesh),
}
impl Scene {
#[must_use]
pub fn provenance(&self, entity: EntityRef) -> Option<EntityProvenance<'_>> {
let placed = self.structure(entity.structure)?;
let structure = placed.source.molframe()?;
let detail = match entity.kind {
EntityKind::Atom => ProvenanceDetail::Atom(structure.atom_at(entity.index as usize)?),
EntityKind::Bond => ProvenanceDetail::Bond(
structure
.engine()
.data()
.bonds
.get(molframe::BondIndex::new(entity.index))?,
),
EntityKind::DynamicBond => {
ProvenanceDetail::DynamicBond(placed.bond_topology()?.bond(entity.index)?)
}
EntityKind::Edge => {
ProvenanceDetail::Interaction(self.interaction_for_entity(entity)?.1)
}
EntityKind::Guide => ProvenanceDetail::Guide(self.guide_for_entity(entity)?.1),
EntityKind::Label => {
if let Some((_, annotation)) = self.annotation_for_entity(entity) {
ProvenanceDetail::Annotation(annotation)
} else {
ProvenanceDetail::Measurement(self.measurement_for_entity(entity)?.1)
}
}
EntityKind::Primitive => {
ProvenanceDetail::Primitive(self.primitive_for_entity(entity)?)
}
EntityKind::Mesh => ProvenanceDetail::Mesh(self.mesh_for_entity(entity)?),
EntityKind::LigandPoseBatch => {
ProvenanceDetail::LigandPoseBatch(self.ligand_pose_batch_for_entity(entity)?)
}
EntityKind::Point
| EntityKind::Instance
| EntityKind::TemplatePart
| EntityKind::Relation => return None,
};
Some(EntityProvenance {
entity,
entry: structure.metadata(),
detail,
})
}
}