2
votes

I am new to Xamarin and I am using ActivityIndicator to say users that app is downloading the data. Problem is that I am using MVVM pattern and I need to set the values IsRunning and IsVisible from ViewModel. I have simple view:

<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
         xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
         xmlns:local="clr-namespace:HmtMobile"
         x:Class="HmtMobile.MainPage"
         Title="Přihlášení"
         >
<ScrollView>
    <StackLayout Margin="10" Spacing="15" VerticalOptions="Center">
        <ActivityIndicator x:Name="ActivityIndicator" Color="Green" IsRunning="{Binding IsBusy, Mode=TwoWay}" IsVisible="{Binding IsBusy, Mode=TwoWay}"/>
        <Entry Placeholder="Uživatelské jméno" Text="{Binding UserName}"></Entry>
        <Entry Placeholder="Heslo" Text="{Binding Password}" IsPassword="True"></Entry>
        <Button Text="Přihlášení" Command="{Binding LoginCommand}" BackgroundColor="#77D065" TextColor="White"></Button>
    </StackLayout>
</ScrollView>

In the view constructor I am assigning the BindingContext

public MainPage()
    {
        InitializeComponent();
        this.BindingContext = new CredentialViewModel(this);
    }

Other properties works because when I want to login the properties returns the actual username and password but the twoway binding doesn´t. Properties are declared same so I do not understand why is this happening.

 private string password;
public string Password
    {
        get { return password; }
        set { password = value; OnPropertyChanged(); }
    }
    private bool isBusy;

    public bool IsBusy
    {
        get { return isBusy; }
        set { isBusy = value; OnPropertyChanged(); }
    }

I am using the simple Login method.

private async Task Login()
    {
        IsBusy = true;
        await Task.Delay(5000);
   }

THe ActivityIndicator is not appearing. Does anyone know why? OnPropertyCHanged is coded this way:

 public class Bindable
{
    public event PropertyChangedEventHandler PropertyChanged;

    protected void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
    }
}
1
Why does it need to be TwoWay? For what you are doing the default (OneWay) is enough. Try to remove the TwoWay declaration and see if it works.Gerald Versluis
Are you sure? I need to set the value in VM and that populate it to view when I try to change it to OneWay it doesn´t recognize the change from code.Jan Holešínský
OneWay means that when you set it from the BindingContext it should update accordingly in the UI. If it is not updated correctly there probably is something wrong with your NotifyPropertyChanged mechanism.Gerald Versluis
The OnPropertyChanged is coded the way I showed in question update.Jan Holešínský
Is INotifyProeprtyChanged defined in your ViewModel ? Dunno why it is in a class calles Bindable ... Or is your ViewModel deriving from that ? simpla do it like this: public class CredentialViewModel : INotifyPropertyChangedFelix D.

1 Answers

0
votes

I figure it out based on Felix message. The problem was that in Bindable class I forgot to add : INotifyPropertyChanged.