use core::any::TypeId;
use crate::{
build::{Build, Builder},
implementer,
protocol::{Implementer, ImplementerExt},
protocols::{bool, ControlFlow},
walk::WalkOnce,
};
#[derive(thiserror::Error, Debug)]
#[error("The value is complete.")]
pub struct IncompleteValue;
#[derive(Default)]
pub struct BoolBuilder(Option<bool>);
impl<'ctx> Build<'ctx> for bool {
type Builder = BoolBuilder;
}
impl<'ctx> Builder<'ctx> for BoolBuilder {
type Error = IncompleteValue;
type Value = bool;
fn as_visitor(&mut self) -> &mut dyn crate::protocol::Implementer<'ctx> {
self
}
fn build(self) -> Result<Self::Value, Self::Error> {
match self.0 {
Some(value) => Ok(value),
None => Err(IncompleteValue),
}
}
fn accepts(id: core::any::TypeId) -> bool {
id == TypeId::of::<bool::Bool>()
}
}
implementer! {
impl['ctx] BoolBuilder = [bool::Bool];
}
impl<'ctx> bool::Object<'ctx> for BoolBuilder {
fn visit(&mut self, value: bool) -> crate::protocols::ControlFlow {
self.0 = Some(value);
ControlFlow::Done
}
}
impl<'ctx> WalkOnce<'ctx> for bool {
type Error = ();
type Value = ();
#[inline]
fn walk_once(self, visitor: &mut dyn Implementer<'ctx>) -> Result<Self::Value, Self::Error> {
if let Some(interface) = visitor.interface_for::<bool::Bool>() {
interface.as_object().visit(self);
}
Ok(())
}
}