使用ViewModel WPF从Codehind执行方法

时间:2014-03-06 16:07:08

标签: wpf view viewmodel code-behind

我已经在应用程序开发中途放弃了MVVM,只是为了让这个应用程序出来。

我在后面的代码中编写了一个方法来更新数据库/ datagrid等。

我的应用程序导航正在使用命令向ViewModel发出一些事件但从未触及代码隐藏,除了一次初始化类。

所以基本上我按下按钮一次,它使用默认的初始设置,但是一旦视图被初始化,我就不能再调用我的代码隐藏的Update()方法。

如何从视图模型中调用此代码隐藏方法?

谢谢!

更新代码

 //Navigation ViewModel
//PaneVm.cs

public CommandExtension NewAssignmentCommand { get; set; }
    private void CreateCommands()
    {
        NewAssignmentCommand = new CommandExtension(NewAssignment, CanNewAssignment);
}
GlobalCommands.NewAssignmentCommand = NewAssignmentCommand;

private bool CanNewGroupAssignment(object obj)
    {
        return true;
    }

    private void NewGroupAssignment(object obj)
    {
        OnPropertyChanged("NewGroupAssignmentCommand");
    }


//MainVM.cs
// [Events]
    void _PaneVm_PropertyChanged(object sender, System.ComponentModel.PropertyChangedEventArgs e)
    {
        if (e.PropertyName == "NewGroupAssignmentCommand")
            WorkspaceVm.CurrentVm = new NewAssignmentsVm();
}


//NewAssignmentVm.cs
//Constructor
    public NewAssignmentsVm()
    {
        var rc = new RepositoryContext();

        _RoResearchers = new ObservableCollection<Researcher>(rc.ResearcherData.GetAllResearchers());

        _QuarterDateTime = DateTime.Now;

        CreateCommands();
    }

//NewAssignment.cs
//Code-behind
//The method
private void UpdateGrid()
    {
        report_datagrid.ItemsSource = null;

        using (var rc = new RepositoryContext())
        {
            if (quarter_datepicker.SelectedDate != null)
            {
                if (!String.IsNullOrEmpty(reportType))
                    researchers = rc.ResearcherData.GetResearchersWeeksByQuarter(Convert.ToDateTime(quarter_datepicker.SelectedDate), reportType).ToList();

            }
        }
    }

更新2:

我根据这个答案解决了我的问题。我创建了一个全局行动

 public static class GlobalCommands 
 { 
 public static Action UpdateGrid { get; set; } 
 } 

然后在我的代码隐藏构造函数中,我将值设置为public

   MyCodeBehind() 
   { 
       GlobalCommands.UpdateGrid = new Action(() => this.UpdateGrid()); 
   } 

不需要再次绑定到上下文。其他一切都是一样的。谢谢

2 个答案:

答案 0 :(得分:4)

主要思想是:

class MyCodeBehind
{
   public MyCodeBehind()
   {
      Action action = new Action(()=> this.SomeMethodIWantToCall());
      var myVM = new MyVM(action); // This is your ViewModel
      this.DataContext = myVM;
   }

   private void SomeMethodIWantToCall(){...}
}

class MyVM
{
    private Action action;

    public MyVM(Action someAction)
    {
       this.action = someAction;
    }

    private void SomeMethodInVM()
    {
        this.action(); // Calls the method SomeMethodIWantToCall() in your code behind
    }
}

答案 1 :(得分:1)

您可以在xaml绑定中使用NotifyOnSourceUpdated,而不是让代码隐藏知道viewmodel。

这样的事情:

<TextBlock Grid.Row="1" Grid.Column="1" Name="RentText"
  Text="{Binding Path=Rent, Mode=OneWay, NotifyOnTargetUpdated=True}"
  TargetUpdated="OnTargetUpdated"/>

这里,“OnTargetUpdated”是代码中的处理程序。当ViewModel的“Rent”属性发生变化时,将调用此处理程序。

MSDN

的详细信息