2017-02-15 8 views
2

ObservableCollectionを介して動的にタブ項目の追加と削除を処理するWorkspaceViewModelがあります。タブがPayslipModelに接続されるたびに、すべてのバインディングはうまく動作しますが、私が抱えている問題の1つはそれです。wpf - モデルの複数のインスタンスと対話する1つのViewModel

DataContextがWorkspaceViewModelに設定されているUserControlに保存ボタンがあり、選択したタブに表示されている情報を保存したいと思います。今度は、タブが追加されるたびに、PayslipModelの新しいインスタンスが作成されます。これは、すべてのタブでバインディングを共有したくないためです。しかし、PayslipModelには複数のインスタンスがあるので、表示されているものを保存できません。したがって、saveを押したときに何も返されません(情報が取得されているかどうかをテストするためにMessageBoxを一時的に使用)。

は、私はより良い自分の状況を説明するための図を作成しました: enter image description here

それはタブが選択またはサイクルのすべてのインスタンスを通って、バッチ節約ような何かをしているときに、現在のインスタンスにアクセスすることは可能ですか?

+0

TabControl.Selected .DataContext PaySlipModelとして? – 0x4f3759df

+1

ItemsControlにItemsSourceとSelectedItemがあります。 TabControl SelectedItemは、現在表示されているタブです。 PayslipModelが編集されているかどうかは分かりませんか? – Will

+0

@ウィル、私はコマンドを使用してボタンをバインドするので、ViewModelを介して保存を実装しようとしていました。この特定のケースでは、ViewModelで行うことはできませんか? – bruh1234

答えて

0

これはpossiblitiesの一つを示した実施例である:

ビュー

<TabControl DataContext="{Binding}" ItemsSource="{Binding Models}" > 
     <TabControl.ItemTemplate> 
      <DataTemplate> 
       <TextBlock Text="{Binding Name}" > 
       </TextBlock> 
      </DataTemplate> 
     </TabControl.ItemTemplate> 
     <TabControl.ContentTemplate> 
      <DataTemplate> 
       <DockPanel> 
        <Button DockPanel.Dock="Top" Content="Click Me" Command="{Binding DataContext.PCommand, 
                  RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=TabControl}}" 
          CommandParameter="{Binding Desc}"/> 
        <TextBlock Text="{Binding Desc}" > 
        </TextBlock> 
       </DockPanel> 
      </DataTemplate> 
     </TabControl.ContentTemplate> 
    </TabControl> 

モデルビュー

public class ModelView 
{ 
    public ModelView() 
    { 
     _models = new ObservableCollection<Model>(); 
     _pCommand = new Command(DoParameterisedCommand); 
    } 
    ObservableCollection<Model> _models; 
    public ObservableCollection<Model> Models { get { return _models; } } 

    private void DoParameterisedCommand(object parameter) 
    { 
     MessageBox.Show("Parameterised Command; Parameter is '" + 
        parameter.ToString() + "'."); 
    } 
    Command _pCommand; 
    public Command PCommand 
    { 
     get { return _pCommand; } 
    } 
} 

モデル

0これは
public class Model : INotifyPropertyChanged 
{ 
    string _desc; 
    public string Desc { get { return _desc; } set { _desc = value; RaisePropertyChanged("Desc"); } } 

    string _name; 
    public string Name { get { return _name; } set { _name = value; RaisePropertyChanged("Name"); } } 

    public event PropertyChangedEventHandler PropertyChanged; 
    void RaisePropertyChanged(string propname) 
    { 
     PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propname)); 
    } 
} 

コマンド

public class Command : ICommand 
{ 
    public Command(Action<object> parameterizedAction, bool canExecute = true) 
    { 
     _parameterizedAction = parameterizedAction; 
     _canExecute = canExecute; 
    } 


    Action<object> _parameterizedAction = null; 
    bool _canExecute = false; 
    public bool CanExecute 
    { 
     get { return _canExecute; } 
     set 
     { 
      if (_canExecute != value) 
      { 
       _canExecute = value; 
       CanExecuteChanged?.Invoke(this, EventArgs.Empty); 
      } 
     } 
    } 
    public event EventHandler CanExecuteChanged; 
    bool ICommand.CanExecute(object parameter) 
    { 
     return _canExecute; 
    } 

    void ICommand.Execute(object parameter) 
    { 
     this.DoExecute(parameter); 
    } 
    public virtual void DoExecute(object param) 
    { if (_parameterizedAction != null) 
      _parameterizedAction(param); 
     else 
      throw new Exception(); 
    } 


} 

使用を初期化します

public MainWindow() 
    { 
     InitializeComponent(); 
     ModelView mv = new ModelView(); 
     mv.Models.Add(new Model() { Name = "a", Desc = "aaa" }); 
     mv.Models.Add(new Model() { Name = "b" , Desc = "bbb"}); 
     mv.Models.Add(new Model() { Name = "c", Desc = "cccc" }); 
     this.DataContext = mv; 

    } 
関連する問題