2017-03-17 48 views
-1

我正在使用向用戶顯示3D呈現數據的自定義控件。該控件具有一個ResetView()方法,該方法將控件的狀態返回到其默認值。我有一個視圖模型,它是窗口的數據上下文,所以當在同一視圖中單擊按鈕並維護MVVM結構時,如何調用控件的ResetView方法?如何通過WPF中的命令調用自定義控件的方法

+1

'button.Click'和'control.ResetView()'根本不涉及虛擬機。你可以在代碼後面的Click處理程序中執行'control.ResetView()',因爲它是內部視圖操作。 – ASh

+0

第二個想法,如果控制綁定到虛擬機,Vm可能應該有'Reset'方法並暴露'ResetCommand'爲button.Command綁定 – ASh

+0

是啊我知道按鈕點擊是非MVVM,點擊我的意思該命令綁定到按鈕 – user3519506

回答

0

一種可能的方法,我通常使用:

在您的視圖模型創建類型的IObservable的屬性。您可以使用 作爲實際的 實現使用來自反應性擴展(RX)的主題。

public class ViewModel 
{ 
    private Subject<Unit> _resetRequest = new Subject<Unit>(); 

    public IObservable<Unit> ResetRequest 
    { 
     get { return _resetRequest; } 
    } 
} 

爲控件創建一個行爲。行爲必須綁定到您的財產並訂閱observable。從訂閱OnNext處理程序中調用您的 控件的ResetView()方法。

public class ResetViewBehavior : Behavior<YourControl> 
{ 
    private IDisposable _subscription; 

    public static readonly DependencyProperty RequestProperty = DependencyProperty.Register("Request", typeof(IObservable<Unit>), typeof(ResetViewBehavior), new PropertyMetadata(null, OnRequestChanged)); 

    public IObservable<Unit> Request 
    { 
     get { return (IObservable<Unit>)GetValue(RequestProperty); } 
     set { SetValue(RequestProperty, value); } 
    } 

    private static void OnRequestChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) 
    { 
     ((ResetViewBehavior)d).Resubscribe(); 
    } 

    private void Resubscribe() 
    { 
     _subscription?.Dispose(); 
     _subscription = Request?.Subscribe(_ => AssociatedObject.ResetView()); 
    } 

    protected override void OnAttached() 
    { 
     Resubscribe(); 
    } 

    protected override void OnDetaching() 
    { 
     _subscription?.Dispose(); 
    } 

} 

在XAML:

<Window> 
     <YourControl> 
      <i:Interaction.Behaviors> 
       <b:ResetViewBehavior Request="{Binding ResetRequest}" /> 
      </i:Interaction.Behaviors> 
     </YourControl> 
    </Window> 

當你想重置視圖從調用視圖模型拍攝對象的OnNext方法。

public class ViewModel 
{ 
    private Subject<Unit> _resetRequest = new Subject<Unit>(); 

    public IObservable<Unit> ResetRequest 
    { 
     get { return _resetRequest; } 
    } 

    private void ResetView() 
    { 
     _resetRequest.OnNext(new Unit()); 
    } 
} 

使用這種方法,您沒有背後的代碼,我個人總是試圖在MVVM中避免這種情況。相反,你會在可重用行爲中包含你的邏輯。

如果您使用其他類而不是Unit作爲IObservable參數,還可以將一些數據傳遞給控件的方法。

+0

非常感謝,我會看看實施它。 – user3519506