HorusSoftwareUY / Xamarin.Forms.Skeleton

The new loading approach for cool apps in Xamarin Forms
MIT License
450 stars 52 forks source link

Button's background color not updating when using Prism Commands #31

Open kxgonzalez opened 2 years ago

kxgonzalez commented 2 years ago

Description

When adding a shimmer to a button that its state is being controlled by using Delegate Commands, the background color is not updated properly after finishing the animation.

Steps to reproduce

  1. Create a prism project
  2. Add a button with a style that handles the button's visual state
  3. Set a delegate command to enable/disable the button
  4. Add a shimmer with animation
  5. Observe how the button's background color remains the same color instead of the disabled color

Expected behavior

The background is set to its disabled state color shimmer-bug-expected

Actual behavior

The background remains in the enabled state color shimmer-bug-actual

Basic information

Visual Studio Community 2022 for Mac Version 17.3.3 (build 10)

Xamarin Forms 5.0.0.2125 Xamarin Forms Skeleton 2.0.0 Prism.Forms 7.2.0.1422

View

<ContentPage
    xmlns:sk="clr-namespace:Xamarin.Forms.Skeleton;assembly=Xamarin.Forms.Skeleton">
    <ContentPage.Content>
        <StackLayout>
            <Grid
                RadioButtonGroup.GroupName="codeGroup"
                RowDefinitions="auto,auto">
                    <RadioButton />
                    <RadioButton />
            </Grid>

            <Button
                Text="{x:Static Resources:TextResources.Send}"
                Style="{StaticResource PrimaryBlueRoundedButtonStyle}"
                Command="{Binding SubmitCommand}"
                sk:Skeleton.IsBusy="{Binding IsInitializing}"
                sk:Skeleton.BackgroundColor="{StaticResource PrimaryBlue}"
                sk:Skeleton.Animation="{sk:DefaultAnimation Source=Fade, Interval=750, Parameter=0.25}" />
        </StackLayout>
    </ContentPage.Content>
</ContentPage>

ViewModel

using Prism.Commands;
using Prism.Navigation;
using Prism.Services;

namespace MyApp.ViewModels
{
    public class PageViewModel
    {
        public DelegateCommand SubmitCommand { get; private set; }

        private ConfirmationCodeOption _selectedOption;
        public ConfirmationCodeOption SelectedOption
        {
            get { return _selectedOption; }
            set { SetProperty(ref _selectedOption, value); }
        }

        private bool _isInitializing;
        public bool IsInitializing
        {
            get { return _isInitializing; }
            set { SetProperty(ref _isInitializing, value); }
        }

        public PageViewModel(...) : base(...)
        {
            IsInitializing = true;

            SubmitCommand = new DelegateCommand(async () => await Submit(), CanSubmit)
                .ObservesProperty(() => SelectedOption);
            //CanSubmit() returns false, button is disabled and gray

            InitView();
        }

        private async Task InitView()
        {
            //retrieve values for radio buttons
            await Task.Delay(3000);
            IsInitializing = false;
            SubmitCommand.RaiseCanExecuteChanged();
            //CanSubmit() returns false, button is disabled and blue
        }

        private bool CanSubmit()
        {
            return SelectedOption != ConfirmationCodeOption.None;
        }
    }
}

Styles

<Color x:Key="PrimaryBlue">#516181</Color>
<Color x:Key="InactiveGray">#B1B2B1</Color>

<Style x:Key="PrimaryBlueRoundedButton" TargetType="Button" BaseResourceKey="BareButton">
    <Setter Property="BackgroundColor" Value="{StaticResource PrimaryBlue}"/>
    <Setter Property="TextColor" Value="{StaticResource White}"/>
    <Setter Property="CornerRadius" Value="20"/>
    <Setter Property="HorizontalOptions" Value="FillAndExpand"/>
    <Setter Property="FontFamily" Value="{StaticResource SegmaBold}"/>
    <Setter Property="FontSize" Value="14"/>
</Style>

<Style x:Key="InactiveGrayRoundedButton" TargetType="Button" BaseResourceKey="BareButton">
    <Setter Property="BackgroundColor" Value="{StaticResource InactiveGray}"/>
    <Setter Property="TextColor" Value="{StaticResource White}"/>
    <Setter Property="CornerRadius" Value="20"/>
    <Setter Property="HorizontalOptions" Value="FillAndExpand"/>
    <Setter Property="FontFamily" Value="{StaticResource SegmaBold}"/>
    <Setter Property="FontSize" Value="14"/>
</Style>

<Style x:Key="PrimaryBlueRoundedButtonStyle" TargetType="Button">
    <Setter Property="VisualStateManager.VisualStateGroups">
        <VisualStateGroupList>
            <VisualStateGroup x:Name="CommonStates">
                <VisualState x:Name="Normal">
                    <VisualState.Setters>
                        <Setter Property="Style" Value="{StaticResource PrimaryBlueRoundedButton}" />
                    </VisualState.Setters>
                </VisualState>
                <VisualState x:Name="Disabled">
                    <VisualState.Setters>
                        <Setter Property="Style" Value="{StaticResource InactiveGrayRoundedButton}" />
                    </VisualState.Setters>
                </VisualState>
            </VisualStateGroup>
        </VisualStateGroupList>
    </Setter>
</Style>