Path: blob/main/crates/bevy_reflect/src/serde/ser/enums.rs
9440 views
use crate::{1enums::{Enum, VariantInfo, VariantType},2serde::{ser::error_utils::make_custom_error, TypedReflectSerializer},3TypeInfo, TypeRegistry,4};5use serde::{6ser::{SerializeStructVariant, SerializeTupleVariant},7Serialize,8};910use super::ReflectSerializerProcessor;1112/// A serializer for [`Enum`] values.13pub(super) struct EnumSerializer<'a, P> {14pub enum_value: &'a dyn Enum,15pub registry: &'a TypeRegistry,16pub processor: Option<&'a P>,17}1819impl<P: ReflectSerializerProcessor> Serialize for EnumSerializer<'_, P> {20fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>21where22S: serde::Serializer,23{24let type_info = self.enum_value.get_represented_type_info().ok_or_else(|| {25make_custom_error(format_args!(26"cannot get type info for `{}`",27self.enum_value.reflect_type_path()28))29})?;3031let enum_info = match type_info {32TypeInfo::Enum(enum_info) => enum_info,33info => {34return Err(make_custom_error(format_args!(35"expected enum type but received {info:?}"36)));37}38};3940let enum_name = enum_info.type_path_table().ident().unwrap();41let variant_index = self.enum_value.variant_index() as u32;42let variant_info = enum_info43.variant_at(variant_index as usize)44.ok_or_else(|| {45make_custom_error(format_args!(46"variant at index `{variant_index}` does not exist",47))48})?;49let variant_name = variant_info.name();50let variant_type = self.enum_value.variant_type();51let field_len = self.enum_value.field_len();5253match variant_type {54VariantType::Unit => {55if type_info.type_path_table().module_path() == Some("core::option")56&& type_info.type_path_table().ident() == Some("Option")57{58serializer.serialize_none()59} else {60serializer.serialize_unit_variant(enum_name, variant_index, variant_name)61}62}63VariantType::Struct => {64let struct_info = match variant_info {65VariantInfo::Struct(struct_info) => struct_info,66info => {67return Err(make_custom_error(format_args!(68"expected struct variant type but received {info:?}",69)));70}71};7273let mut state = serializer.serialize_struct_variant(74enum_name,75variant_index,76variant_name,77field_len,78)?;79for (index, field) in self.enum_value.iter_fields().enumerate() {80let field_info = struct_info.field_at(index).unwrap();81state.serialize_field(82field_info.name(),83&TypedReflectSerializer::new_internal(84field.value(),85self.registry,86self.processor,87),88)?;89}90state.end()91}92VariantType::Tuple if field_len == 1 => {93let field = self.enum_value.field_at(0).unwrap();9495if type_info.type_path_table().module_path() == Some("core::option")96&& type_info.type_path_table().ident() == Some("Option")97{98serializer.serialize_some(&TypedReflectSerializer::new_internal(99field,100self.registry,101self.processor,102))103} else {104serializer.serialize_newtype_variant(105enum_name,106variant_index,107variant_name,108&TypedReflectSerializer::new_internal(field, self.registry, self.processor),109)110}111}112VariantType::Tuple => {113let mut state = serializer.serialize_tuple_variant(114enum_name,115variant_index,116variant_name,117field_len,118)?;119for field in self.enum_value.iter_fields() {120state.serialize_field(&TypedReflectSerializer::new_internal(121field.value(),122self.registry,123self.processor,124))?;125}126state.end()127}128}129}130}131132133