Reputation: 103
I want to use deeply nested enums to represent blocks in my game:
enum Element { Void, Materal(Material) }
enum Material { Gas(Gas), NonGas(NonGas) }
enum NonGas { Liquid(Liquid), Solid(Solid) }
enum Solid { MovableSolid(MovableSolid), ImmovableSolid(ImmovableSolid) }
enum Gas { Smoke }
enum Liquid { Water }
enum ImmovableSolid { Bedrock }
enum MovableSolid { Sand, GunPowder }
I found it very verbose to declare an Element
:
let block: Element = Element::Materal(Material::NonGas(NonGas::Solid(Solid::ImmovableSolid(ImmovableSolid::Bedrock))));
Is it possible to create a macro to add syntactic sugar for my enum declaration?
I'm hoping to create a macro that can automagically resolve the enum path, for example
let block: Element = NewElement!(ImmovableSolid::Bedrock);
Upvotes: 0
Views: 101
Reputation: 2581
Using cdhowie's From
idea, I think you'd only need trait impls from your lowest level enums. You can skip ones like impl From<Material> for Element
because you need a child to create a Material
, so it doesn't really make sense to start at that level.
impl From<Gas> for Element {
fn from(e: Gas) -> Element {
Element::Materal(Material::Gas(e))
}
}
impl From<Liquid> for Element {
fn from(e: Liquid) -> Element {
Element::Materal(Material::NonGas(NonGas::Liquid(e)))
}
}
impl From<ImmovableSolid> for Element {
fn from(e: ImmovableSolid) -> Element {
Element::Materal(Material::NonGas(NonGas::Solid(Solid::ImmovableSolid(e))))
}
}
impl From<MovableSolid> for Element {
fn from(e: MovableSolid) -> Element {
Element::Materal(Material::NonGas(NonGas::Solid(Solid::MovableSolid(e))))
}
}
fn main() {
println!("{:?}", Element::from(ImmovableSolid::Bedrock));
}
Upvotes: 2