2017-10-08 13 views
0

助けてください: 私はXamarinを使って簡単なアプリケーションでMVVMデザインを実装しました。 私は1つのモデル(User)と1つのViewModel(UserViewModel)を持っています。 このアプリは私の最初のXamarin/MVVMアプリであり、これは初めてのことです。MVVM INotifyPropertyChanged not working

私が持っている問題は、ユーザーを追加または削除すると、ビューが更新されないということです。 ユーザーを追加または削除すると、データベースは更新されていますが、自分のビューは更新されていないことが確認できます。

下記のコードをご覧ください。何が欠けていますか?

ユーザーモデル:

public class User 
{ 
    public int Id { get; set; } 
    public string Username { get; set; } 
    public string FirstName { get; set; } 
    public string LastName { get; set; } 
    public bool IsActive { get; set; } 

    public List<Role> RolesList { get; set; } 
} 

UserViewModelコード:(完全を期すために追加しました)

public class UsersViewModel : INotifyPropertyChanged 
     { 
     private UserServices UserServ { get; set; } 

     public User UserSelected { get; set; } 

     private ObservableCollection<User> userList; 
     public ObservableCollection<User> UserList 
     { 
      get 
      { 
       return userList; 
      } 
      set 
      { 
       if (userList != value) 
       { 
        userList = value; 
        NotifyPropertyChanged(); 
       } 
      } 
     } 

     public event PropertyChangedEventHandler PropertyChanged; 

     private void NotifyPropertyChanged([CallerMemberName] String propertyName = "") 
     { 
      PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); 
     } 

     public UsersViewModel() 
     { 
      UserServ = new UserServices(); 
      UsersLoadAsync(); 
     } 

     public async void UsersLoadAsync() 
     { 
      UserList = await UserServ.UsersGetAsync(); 
     } 
    } 

ユーザーヘルパーサービスコード

public class UserServices 
    { 

     public async Task<ObservableCollection<User>> UsersGetAsync() 
     { 
      ObservableCollection<User> UserList = await App.UserService.GetAsync(); 

      return UserList; 
     } 

     public async Task<bool> UsersAddAsync(User user) 
     { 
      bool success = await App.UserService.PostAsync(user); 
      return success; 
     } 

     public async Task<bool> UsersRemoveAsync(User user) 
     { 
      bool success = await App.UserService.DeleteAsync(user.Id, user); 
      return success; 
     } 

    } 

ビューXAMLコード:

<?xml version="1.0" encoding="utf-8" ?> 
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms" 
      xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml" 
      xmlns:local="clr-namespace:PB_Logbook" 
      x:Class="PB_Logbook.MainPage" 
      xmlns:ViewModels="clr-namespace:PB_Logbook.ViewModels;assembly:PB_Logbook"> 

    <ContentPage.BindingContext> 
     <ViewModels:UsersViewModel/> 
    </ContentPage.BindingContext> 
    <StackLayout> 
     <ListView ItemsSource="{Binding UserList, Mode=TwoWay}" HasUnevenRows="True" ItemSelected="Item_SelectedAsync" IsPullToRefreshEnabled="True"> 
     <ListView.ItemTemplate> 
      <DataTemplate> 
       <ViewCell> 
        <StackLayout Orientation="Vertical" Padding="12,6"> 
         <Label Text="{Binding Username}" FontSize="24"/> 
         <Label Text="{Binding FirstName}" FontSize="18" Opacity="0.6"/> 
         <Label Text="{Binding LastName}" FontSize="18" Opacity="0.6"/> 
        </StackLayout> 
       </ViewCell> 
      </DataTemplate> 
     </ListView.ItemTemplate> 
    </ListView> 
    <Button Text="Add" Clicked="AddButton_ClickedAsync"></Button> 
     <Button Text="Remove" Clicked="RemoveButton_ClickedAsync"></Button> 
    </StackLayout> 


</ContentPage> 

の背後にあるビューコード:

public partial class MainPage : ContentPage 
    { 
     private UserServices UserServices { get; set; } 
     private UsersViewModel UsersVM { get; set; } 


     public MainPage() 
     { 
      InitializeComponent(); 
      UserServices = new UserServices(); 
      UsersVM = new UsersViewModel(); 
     } 

     private async void AddButton_ClickedAsync(object sender, EventArgs e) 
     { 
      await AddUserAsync(); 
     } 

     private async void RemoveButton_ClickedAsync(object sender, EventArgs e) 
     { 
      await RemoveUserAsync(); 
     } 

     private async void Item_SelectedAsync(object sender, EventArgs e) 
     { 
      UsersVM.UserSelected = ((User)((ListView)sender).SelectedItem); 

     } 

     private async void Pull_RefreshAsync(object sender, EventArgs e) 
     { 
      //UsersVM.UsersLoadAsync(); 
     } 

     private async Task AddUserAsync() 
     { 
      Random rnd = new Random(); 
      int rndNumber = rnd.Next(1, 100); 

      User user = new User() 
      { 
       Username = "User " + rndNumber, 
       FirstName = "Firstname " + rndNumber, 
       LastName = "Surname " + rndNumber, 
       IsActive = true 
      }; 

      bool success = await UserServices.UsersAddAsync(user); 

      if (success) 
      { 
       if (!UsersVM.UserList.Contains(user)) 
        UsersVM.UserList.Add(user); 
      } 
     } 

     private async Task RemoveUserAsync() 
     { 
      bool success = await UserServices.UsersRemoveAsync(UsersVM.UserSelected); 

      if (success) 
      { 
       if (UsersVM.UserList.Contains(UsersVM.UserSelected)) 
        UsersVM.UserList.Remove(UsersVM.UserSelected); 
      } 
     } 
    } 

問題は、私の見解では更新されないユーザーを追加/削除です。

ありがとうございます。私もお勧めし

+1

'一覧<>'と 'のObservableCollection <>'を使用して 'INotifyPropertyChanged'の実装を置き換え支援を期待して、簡単な天気アプリを持っています。 – jsanalytics

+0

返事ありがとう、@jstreet。 List <>をObservableCollection <>に置き換えましたが、それでも動作しません。他のアドバイスは? –

+0

私はチャンスを得るとすぐに私はもっと近くで見ていきます。 – jsanalytics

答えて

2

あなたはXamarin MVVMに新しいしている場合、このリンクはXamarinにあなたがMVVMの基本を理解するのに役立ちますが

https://deanilvincent.github.io/2017/06/03/basic-understanding-of-mvvm-and-databinding-in-xamarin-forms/

フォーム、あなたのコードの後ろに軽減し、ちょうど実装してください。あなたのViewModelのコマンドを含むすべて。

保存して更新するときにコードが機能していても、表示が正しく反映されていないと書いてありますか? saveコマンドの直後にリストを取得する方法を記述してください。あなたのViewModelであなたのXAML

<Button Text="Save" Command="{Binding SaveCommand}"/> 

でこのよう

は、あなたがMVVMに新しいしている場合は、あなたもこの linkを確認することができますXamarin

public Command SaveCommand{ 
    get{ 
     return new Command(async()=>{ 
      // your command save here 
      // then put your method for fetching the updated list: your UsersLoadAsync(); 
     }); 
    } 
} 

からコマンドを使用する必要があります。それはXamarin MVVMを使用します。完了したら、あなたは、単純なMVVM実装

私はそれはあなたが

+0

ポストをありがとう。私はあなたの助言に従って、すべての論理とコマンドをViewModelに移しました。私はまた保存後にリストを再ロードしようとしましたが、まだビューを更新しません。 –