I am implementing a simple tile set editor for retro games using Avalonia, CommunityToolkit MVVM and .NET 8. I am working on the “New Tileset” dialog, and I have a ComboBox for selecting the type of tile set (Fixed Size or Variable Size). The ComboBox is bound to an Enum defined as follows:
public enum TilesetDimensions
{
[EnumDescriptor(identifier: "FixedSize")]
FixedSize,
[EnumDescriptor(identifier: "VariableSize")]
VariableSize
}
The EnumDescriptor
attribute is my own class that adds several optional meta-data items to an emum. This has been working fine for a while, and the identifier is used to do a language translation lookup (displayed in the ComboBox via a Converter).
I am specifically trying to hide the Label after the ComboBox depending on which value is selected. The axaml code for the ComboBox is as follows. The TilesetTypes, SelectedTilesetType, and IsFixedSize bindings are defined in the ViewModel.
<ComboBox
Grid.Row="0"
Grid.Column="1"
Classes="OptionsEntry"
ItemsSource="{Binding TilesetTypes}"
SelectedValue="{Binding SelectedTilesetType, Mode=TwoWay}">
<ComboBox.ItemTemplate>
<DataTemplate>
<TextBlock
Text="{Binding, Converter={StaticResource EnumTranslationConverter}}" />
</DataTemplate>
</ComboBox.ItemTemplate>
</ComboBox>
<Label
Grid.Row="1"
Grid.Column="0"
IsVisible="{Binding IsFixedSize}"
Classes="OptionsLabel"
Content="{Binding Translator[TileSize]}"
/>
public ObservableCollection<TilesetDimensions> TilesetTypes { get; } =
new ObservableCollection<TilesetDimensions>(Enum.GetValues<TilesetDimensions>());
[ObservableProperty]
[NotifyPropertyChangedFor(nameof(IsFixedSize))]
private TilesetDimensions selectedTilesetType = TilesetDimensions.FixedSize;
public bool IsFixedSize => SelectedTilesetType == TilesetDimensions.FixedSize;
Everything is working fine, except the hiding of the label when “Variable Size” is selected. The ComboBox is filled with the correctly translated text values, and the visibility of the label works fine if I change the default value of SelectedTilesetType at design-time. It just refuses to change at run-time.
I have tried adding an event to catch it, and tried manually assigning the PropertyChanged event in the ViewModel. No breakpoints are hit, nothing is logged, when the selected value is changed at run-time. I’ve tried every iteration I can think of, even tried changing to ReactiveUI and couldn’t get THAT to change the visibility either.
partial void OnSelectedTilesetTypeChanging(TilesetDimensions oldValue, TilesetDimensions newValue)
{
Debug.WriteLine($"Selected tileset type changing from {oldValue} to {newValue}");
}
PropertyChanged += (sender, args) =>
{
if (args.PropertyName == nameof(SelectedTilesetType))
{
Debug.WriteLine($"Selected tileset type changed to {SelectedTilesetType}");
}
};
I’ve tried StackOverflow, Google Searches, CoPilot, etc., and I can’t figure out what I am doing wrong. I feel like it has to be something simple, but I don’t know what it is.