DataTrigger only occurs once per value

Hi, I have a keypad for entering a PIN with a prompt near the top. I want the Enter button's command and the prompt's text to change depending on where the user is in the login sequence (attempting to sign in, inputting a new pin, and confirming the new pin). Where the user is in the login sequence is represented by an integer value PinStatus. I added data triggers to each of these in the xaml file for the sign in page. The triggers work only the first time the PinStatus hits each of the available values (0, 1, and 2). To test, I just set the PIN status in a cycle (i.e. SignIn() sets PinStatus to 1, SetNewPin() to 2, ConfirmNewPin() to 0). What could I be doing wrong? Also, is this a recommended design?

<Button Text="Enter"
              Grid.Row="3" Grid.Column="2"
              BackgroundColor="{StaticResource BlueBackground}"
              TextColor="{StaticResource WhiteText}">
        <DataTrigger TargetType="Button" Binding="{Binding PinStatus}" Value="0">
            <Setter Property="Command" Value="{Binding SignInCommand}"/>
        <DataTrigger TargetType="Button"  Binding="{Binding PinStatus}" Value="1">
                <Setter Property="Command" Value="{Binding SetNewPinCommand}"/>
        <DataTrigger TargetType="Button"  Binding="{Binding PinStatus}" Value="2">
            <Setter Property="Command" Value="{Binding ConfirmNewPinCommand}"/>

<Label HorizontalTextAlignment="Center"
            TextColor="{StaticResource WhiteText}">
        <DataTrigger TargetType="Label" Binding="{Binding PinStatus}" Value="0">
                <Setter Property="Text" Value="Enter PIN"/>
            <DataTrigger TargetType="Label"  Binding="{Binding PinStatus}" Value="1">
                <Setter Property="Text" Value="Enter new PIN"/>
            <DataTrigger TargetType="Label"  Binding="{Binding PinStatus}" Value="2">
                <Setter Property="Text" Value="Reconfirm your new PIN"/>

Best Answer


  • ClintStLaurentClintStLaurent USUniversity ✭✭✭✭✭

    Well... DataTriggers trigger on a change of value. So from 2, to 2 wouldn't be a change. I'm not sure if that's happening in your case because I couldn't follow your description.

    Also, is this a recommended design?

    "recommended"... Eh... 10 developers will each give you a different but equally right way to approach something like this depending on their experiences and stylistic approach. All would probably be equally right, just different.

  • hwangcyrushwangcyrus Member ✭✭

    So at the beginning, PinStatus is set to 0. There are 3 commands in my view model with the following methods attached to them: SignIn(), SetNewPin(), and ConfirmNewPin().

            public void SignIn()
                PinStatus = 1;
            public void SetNewPin()
                PinStatus = 2;
            public void ConfirmNewPin()
                PinStatus = 0;

    This code combined with the above should produce a loop that goes on forever when you click the enter button. This is the expected behavior:

    Label Text: "Enter PIN" -> "Enter new PIN" -> "Reconfirm your new PIN" -> "Enter PIN" -> "Enter new PIN" -> "Reconfirm your new PIN" -> ...
    Button Command: SignInCommand -> SetNewPinCommand -> ConfirmNewPinCommand -> SignInCommand -> SetNewPinCommand -> ConfirmNewPinCommand -> ...

    However the observed behavior is that it only runs through the loop once, like so:

    Label Text: "Enter PIN" -> "Enter new PIN" -> "Reconfirm your new PIN" -> "Enter PIN" -> "Enter PIN" -> "Enter PIN" -> ...
    Button Command: SignInCommand -> SetNewPinCommand -> ConfirmNewPinCommand -> null -> null -> null -> ...

    I know the command is turning to null because I'm printing it with a Clicked handler in the code-behind.

    Still haven't figured this out...

  • ClintStLaurentClintStLaurent USUniversity ✭✭✭✭✭

    Hmmm... Not sure what to tell ya. While it doesn't solve your issue... And can tell ya that I have extensive use of DataTrigger using bool, enum and int data types as the binded property being observed as the trigger and they all work as expected. If they were our QA department would have bounced countless features back to me. So I can at least let you know it isn't a problem with the eco-system.

    I know the command is turning to null because

    Yikes. Don't do that. Unlike WPF, Xamarin does not bind to null very well. As soon as anything along the path evaluates to null all evaluation ends. You can't send null as a value thinking it will go to a converter etc. Not sure if that is having some affect here or not. Instead of a null, make a DummyCommand that does nothing but is still a real non-null object. That way the binding doesn't break and fail to evaluate.

  • hwangcyrushwangcyrus Member ✭✭

    I am not intentionally making the command null. It's a value I'm observing it turning to. I'd love to know why it's turning to null myself. It being null is what's causing the loop to end. The question now is why is it turning to null...

Sign In or Register to comment.