2012-05-31 86 views
1

我是新來的MVVM,並在其自己的視圖模型C#-file碰到問題如何打開一個對話框,關閉後的對話框。搜索可能的解決方案,發現什麼都不合適 我的解決方案如下所示,但我不確定這是否有一些缺點。 定義的用戶控件,並打開它:WPF用戶控件MVVM如何關閉對話框

void ChangeDataPathExecute() 
{ 
    Window window = new Window 
    { 
     Content = new ChangeDataRootPathUserControl(), 
    }; 

    window.ShowDialog(); 
} 

在用戶控件文件的視圖模型實現:

void OkChangeDataRootPathExecute() 
{ 
    DetermineMyWindow(); 

    myWindow.Close(); 
} 

你怎麼想:

private void DetermineMyWindow() 
{ 
    foreach (Window window in App.Current.Windows) 
    { 
     ChangeDataRootPathUserControl uc = window.Content as ChangeDataRootPathUserControl; 
     if (uc == null) 
      continue; 

     myWindow = window; 
    } 
在關閉方法

最後對這個?黑客或好的解決方案? 感謝您的反饋 節拍

回答

1

您可以通過從UserControl內部引用this.Parent(只要它是第一個內容元素)來更容易地訪問該窗口。

你正在試圖做的是創建一個新的XAML文件的窗口,把你的用戶控件的一個實例,在XAML窗口裏面有什麼更正統的方法。

如果你希望你的用戶控件能夠關閉它的父窗口,那麼一個簡單的關閉事件添加到用戶控件。現在在您的Window XAML中,您可以將事件處理程序添加到關閉事件中,並在UserControl引發事件時讓窗口調用Close()。

// UserControl.cs 
public event EventHandler Close; 

void OkChangeDataRootPathExecute() 
{ 
    if (Close != null) 
     Close(this, EventArgs.Empty); 
} 


// Window.cs 
void UserControl_Close(object sender, EventArgs e) 
{ 
    Close(); 
} 

然後,如果你想添加任何額外的選項或樣式,你可以把它添加到您的XAML,如SizeToContent,WindowStartupLocation,邊框等,來控制你的對話框的外觀和感覺。

然後,當你想展示你的代碼中的對話框,你寫這樣的:

void ChangeDataPathExecute() 
{ 
    var window = new ChangeDataRootPathWindow(); 

    window.ShowDialog(); 
} 
2

ViewModel在MVVM情況下不應該知道的事情View。在你的例子中,它似乎必須知道很多關於視圖。

許多人使用許多不同的模式來從ViewModel打開/關閉窗口。我更喜歡事件/回調:

class ViewModel { 
    public event EventHandler ChangeDataRootPath; 
} 

class View : Window { 
    public View() { 
     InitializeComponent(); 

     var vm = new ViewModel(); 
     vm.ChangeDataRootPath += (s, e) => { 
      Window window = new Window { 
       Content = new ChangeDataRootPathUserControl { 
        DataContext = vm 
       } 
      }; 
      window.ShowDialog(); 
     }; 
     DataContext = vm; 
    } 
} 
+0

感謝這個想法。 我會說這是所謂的「後面的代碼」,我試圖避免 – Vik

0

您的視圖模型應該只是開個DialogService。看看here得到一個起點。

+0

感謝您的鏈接。 我試圖避免的是 _...在創建對話框的模塊中對對話結果..._ 執行任何操作。作爲一名初學者,我期望在對話本身的密切行動中實現這一點 – Vik

0

在我個人的實現,我不會讓我的視圖模型瞭解的窗口,用戶控件或任何其他視覺元素任何東西。但是這需要整個框架的定義。有很多,只是搜索和使用最適合你的那個。

但對於一個快速的解決方案,如果你想從任何地方關閉該窗口是當前具有焦點的一個,你可以用這個方法來訪問它:

public static Window GetCurrentFocusedWindow() 
{ 
    Window window = null; 

    Control currentControl = System.Windows.Input.Keyboard.FocusedElement as Control; 

    if (currentControl != null) 
     window = Window.GetWindow(currentControl); 

    return window; 
} 
+0

感謝您的支持。我認爲那樣更好 – Vik

-1

這件怎麼樣?

Window parentWindow = (Window)this.Parent; 
parentWindow.Close();