Skip to content

Bevy settings support tuple structs and non-unit like enums#23812

Merged
alice-i-cecile merged 2 commits intobevyengine:mainfrom
mpowell90:feat/tuple-support-in-settings-group-derive-macro
Apr 15, 2026
Merged

Bevy settings support tuple structs and non-unit like enums#23812
alice-i-cecile merged 2 commits intobevyengine:mainfrom
mpowell90:feat/tuple-support-in-settings-group-derive-macro

Conversation

@mpowell90
Copy link
Copy Markdown
Contributor

Objective

Implements part of #23302

For background on bevy settings see the initial PR:
#23034

Solution

As we invoke the serde toml serializer:
Single field tuple structs are serialized as single values:

#[derive(Resource, SettingsGroup, Reflect, PartialEq, Debug, Default)]
#[reflect(Resource, SettingsGroup, Default)]
struct SingleFieldTupleStruct(u8);

Results in:

[single_field_tuple_struct]
single_field_tuple_struct = 0

Multi-field tuple structs are serialized as arrays of values, with nested structs serialized as inline tables:

#[derive(Reflect, PartialEq, Debug, Default)]
#[reflect(Default)]
struct NestedStruct {
    a: u8,
    b: u16,
}

#[derive(Resource, SettingsGroup, Reflect, PartialEq, Debug, Default)]
#[reflect(Resource, SettingsGroup, Default)]
struct MultiFieldTupleStruct(u8, NestedStruct);

Results in:

[multi_field_tuple_struct]
multi_field_tuple_struct = [0, { a = 0, b = 0 }]

Non-unit enums retain the "key" field with it defaulting the resources name, with it being serialized into the group table:

#[derive(Resource, SettingsGroup, Reflect, PartialEq, Debug)]
#[reflect(Resource, SettingsGroup, Default)]
enum EnumSingleTupleVariant {
    A(u8),
}

impl Default for EnumSingleTupleVariant {
    fn default() -> Self {
        EnumSingleTupleVariant::A(0)
    }
}

Results in:

[enum_single_tuple_variant.enum_single_tuple_variant]
A = 0

The same multi-field tuple serialization occurs in enums:

#[derive(Resource, SettingsGroup, Reflect, PartialEq, Debug)]
#[reflect(Resource, SettingsGroup, Default)]
enum EnumMultiNewTypeVariant {
    A(SingleFieldTupleStruct, MultiFieldTupleStruct),
}

impl Default for EnumMultiNewTypeVariant {
    fn default() -> Self {
        EnumMultiNewTypeVariant::A(
            SingleFieldTupleStruct(0),
            MultiFieldTupleStruct(0, NestedStruct { a: 0, b: 0 }),
        )
    }
}

Results in:

[enum_multi_new_type_variant.enum_multi_new_type_variant]
A = [0, [0, { a = 0, b = 0 }]]

Enums variants with fields are serialised with field entries:

#[derive(Resource, SettingsGroup, Reflect, PartialEq, Debug)]
#[reflect(Resource, SettingsGroup, Default)]
enum EnumStructVariant {
    A { x: u8, y: u16 },
}

impl Default for EnumStructVariant {
    fn default() -> Self {
        EnumStructVariant::A { x: 0, y: 0 }
    }
}

Results in:

[enum_struct_variant.enum_struct_variant.A]
x = 0
y = 0

Notes

  • I'm not 100% sold on the [group_name.key_name] for non-unit like enums, its easy enough to not include the key for these types but i'll keep in for the sake of discussion.
  • Still not supporting Unions. Settings: Serialize enums and newtype structs #23302 did not mention them but I can add support for these in this PR or we can just not support them at all. Open to discussion.

Testing

  • I've added to the above examples to the bevy settings test suite.
  • I've ran the persisting_preferences example and cross referenced the toml output in the file.

@alice-i-cecile alice-i-cecile requested a review from viridia April 15, 2026 15:37
@alice-i-cecile alice-i-cecile added this to the 0.19 milestone Apr 15, 2026
@alice-i-cecile alice-i-cecile added C-Bug An unexpected or incorrect behavior A-Editor Graphical tools to make Bevy games D-Straightforward Simple bug fixes and API improvements, docs, test and examples S-Needs-Review Needs reviewer attention (from anyone!) to move forward labels Apr 15, 2026
@viridia
Copy link
Copy Markdown
Contributor

viridia commented Apr 15, 2026

We should update the release note to include these follow-on PR numbers.

@alice-i-cecile
Copy link
Copy Markdown
Member

alice-i-cecile commented Apr 15, 2026

Still not supporting Unions. #23302 did not mention them but I can add support for these in this PR or we can just not support them at all. Open to discussion.

IMO we shouldn't bother supporting unions. I have never seen these used for normal Rust things in a way that you might use in settings.

@alice-i-cecile alice-i-cecile added this pull request to the merge queue Apr 15, 2026
@alice-i-cecile alice-i-cecile added S-Ready-For-Final-Review This PR has been approved by the community. It's ready for a maintainer to consider merging it and removed S-Needs-Review Needs reviewer attention (from anyone!) to move forward labels Apr 15, 2026
Merged via the queue into bevyengine:main with commit 695c8e0 Apr 15, 2026
48 checks passed
@mpowell90 mpowell90 deleted the feat/tuple-support-in-settings-group-derive-macro branch April 15, 2026 18:39
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

A-Editor Graphical tools to make Bevy games C-Bug An unexpected or incorrect behavior D-Straightforward Simple bug fixes and API improvements, docs, test and examples S-Ready-For-Final-Review This PR has been approved by the community. It's ready for a maintainer to consider merging it

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants