use super::composite::EncodeFieldsAsType;
use crate::{
error::{Error, ErrorKind, Kind},
EncodeAsType,
};
use codec::Encode;
use scale_info::{PortableRegistry, TypeDef};
#[doc(hidden)]
pub struct Variant<Tuples> {
pub name: &'static str,
pub fields: super::composite::Composite<Tuples>,
}
impl<Tuples> EncodeAsType for Variant<Tuples>
where
super::composite::Composite<Tuples>: EncodeFieldsAsType,
{
fn encode_as_type_to(
&self,
type_id: u32,
types: &PortableRegistry,
out: &mut Vec<u8>,
) -> Result<(), Error> {
let type_id = super::find_single_entry_with_same_repr(type_id, types);
let ty = types
.resolve(type_id)
.ok_or_else(|| Error::new(ErrorKind::TypeNotFound(type_id)))?;
match ty.type_def() {
TypeDef::Variant(var) => {
let vars = var.variants();
let Some(v) = vars.iter().find(|v| v.name == self.name) else {
return Err(Error::new(ErrorKind::CannotFindVariant { name: self.name.to_string(), expected: type_id }));
};
v.index().encode_to(out);
self.fields
.encode_fields_to(v.fields(), type_id, types, out)
}
_ => Err(Error::new(ErrorKind::WrongShape {
actual: Kind::Str,
expected: type_id,
})),
}
}
}