2016-04-07 10 views
0

私はバックグラウンドで更新されるいくつかのプロパティ(Pingなど)を持つServerクラスを持っているとしましょう。 私は、Serverインスタンスを保持しているServerViewModelと、ObservableCollection内のServerViewModelの異なるインスタンスを保持しているViewであるServersViewModelを持っています。 MVVM RaiseProperty ViewModelまたはModelで変更しますか?

(短縮)サーバー・クラス:

public class Server: ObservableObject, IServer 
{ 

    /// <summary> 
    /// Gets the IP adress of the server 
    /// </summary> 
    [JsonIgnore] 
    public IPAddress IPAdress { get; private set; } 

    /// <summary> 
    /// Gets the name of the server 
    /// </summary> 
    public string Name 
    { 
     get 
     { 
      return name; 
     } 

     private set 
     { 
      if(name != value) 
      { 
       name = value; 
       RaisePropertyChanged("Name"); 
      } 

     } 
    } 

    /// <summary> 
    /// Gives the string of the ip 
    /// </summary> 
    public string IP 
    { 
     get 
     { 
      return ip; 
     } 

     private set 
     { 
      if(ip != value) 
      { 
       ip = value; 
       RaisePropertyChanged("IP"); 
      }     
     } 
    } 


    /// <summary> 
    /// Gets the ping of the server 
    /// </summary> 
    [JsonIgnore] 
    public int Ping 
    { 
     get 
     { 
      return ping; 
     } 

     private set 
     { 
      if(ping != value) 
      { 
       ping = value; 
       RaisePropertyChanged("Ping"); 
      } 
     } 
    } 

    private Thread queryThread; 

    private string name, ip; 

    /// <summary> 
    /// Initializes the server instance 
    /// </summary> 
    /// <param name="ip">The ip adress or dns of the server</param> 
    /// <param name="port">The common port to connect to</param> 
    [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors")] 
    public Server(string ip, int port) 
    { 
     IP = ip; 

     IPAddress tmpIP; 

     // Check if the given IP matches a DNS 
     if (!IPAddress.TryParse(ip, out tmpIP)) 
     { 
      try 
      { 
       this.IPAdress = Dns.GetHostEntry(ip).AddressList[0]; 
      } 
      catch (Exception ex) 
      { 
       System.Diagnostics.Debug.WriteLine(ex); 
       return; 
      } 
     } 
     else 
     { 
      this.IPAdress = IPAddress.Parse(ip); 
     } 

     Port = port; 

     queryThread = new Thread(QueryServer); 
     queryThread.Start(); 
    } 

    /// <summary> 
    /// Destructor for Server class. Stops the server thread running in background and cleans up. 
    /// </summary> 
    ~Server() 
    { 
     try 
     { 
      queryThread.Abort(); 
      queryThread = null; 
     } 
     catch 
     { 
      // Ignored 
     } 
    } 

    /// <summary> 
    /// Starts the loop that is querying the server 
    /// </summary> 
    private void QueryServer() 
    { 
    } 
} 

私は、私はそれが必要とされるProertiesでRaisePropertyChangedを追加し、バックグラウンドでデータを更新していたよう。

ServerViewModel:

public class ServerViewModel: ViewModelBase 
{ 
    private Server server; 

    public Server Server 
    { 
     get 
     { 
      return server; 
     } 
    } 

    public ServerViewModel(Server server) 
    { 
     this.server = server; 
    } 
} 

ServersViewModel:

public class ServersViewModel: ObservableObject 
{ 
    #region Members 

    ObservableCollection<ServerViewModel> servers = new ObservableCollection<ServerViewModel>(); 

    #endregion 

    #region Properties 
    public ObservableCollection<ServerViewModel> Servers 
    { 
     get 
     { 
      return servers; 
     } 

     set 
     { 
      servers = value; 
     } 
    } 
    #endregion 

    #region Construction 
    public ServersViewModel() 
    { 
     // Add servers to the collection 
    } 
    #endregion 
} 

私は、ビューのリストにServersViewModelを結合しています。リスト内の各アイテムのデータバインディングは、次のようになります。

<Label Name="lblServerPing" Content="{Binding Server.Ping}" /> 

私にとってはこれは間違っています。特に、ビューのServerインスタンスにアクセスしているため、ビューのプロパティにアクセスしていないためです。私はRaisePropertyChangedをどこに置くべきか、この動作を修正する方法はまだ分かりません。私はそれがこのように動作していることを認めなければなりませんが、MVVMのように見える方法ではないと思います。

ObservableObjectおよびViewModelBaseは、MVVMのライトであり、必要なインターフェイスを実装しています。

ありがとうございました!

答えて

1

通常、ViewModelでPropertyChangedイベントを発生させ、モデルはプロパティ/オブジェクトのコレクションにする必要があります。 ViewModelはそれらのプロパティを公開し、PropertyChangedイベントを通じて変更されたときにビューに通知します。

ここで検証ロジックが

public class ServerModel 
{ 
    public string Name { get; set; } 
    public string IP { get; set; } 
} 

public class ServerViewModel : ViewModelBase 
{ 
    private ServerModel model; 

    public ServerViewModel(ServerModel model) 
    { 
     this.model = model; 
    } 

    public string Name 
    { 
     get { return model.Name; } 
     private set 
     { 
       model.Name = value; 
       OnPropertyChanged("Name"); 
     } 
    } 

    public string IP 
    { 
     get { return model.IP; } 
     private set 
     { 
       model.IP= value; 
       OnPropertyChanged("IP"); 
     } 
    } 
} 

...あなたがうまくいけば、あなたは厳密にMVVMをフォローしたい場合は、つまり、どこへ行くの絵を描くべきか、何をやっているの簡易版ですあなたはsetterの中にViewModelを持っています。 ViewModel内部のロジックが複雑になる場合は、理想的にはサービスクラスにアウトソーシングする必要があります.ViewModelには複雑なロジックがたくさん含まれている必要はなく、ViewにModelデータの表示方法を伝えるだけです。

これが役に立ちます。

+0

ありがとうございました。それが私がこのコンセプトで誤解した点でした。だから、バックグラウンドワーカースレッドをビューモデルに移動して、このスレッドにサーバーをリフレッシュさせることができますか?それは私がこの場合にする方法です。 – chris579

関連する問題