2013-09-26 93 views
0

我有一個WPF打開從Microsoft Outlook的功能區中的按鈕,爲我正在開發的插件。重新打開微軟Outlook插件C關閉的WPF#

private void _HandlerUserSettings(Office.CommandBarButton ctrl, ref bool cancel) 
{ 
    var windowUserSettings = new WpfUserSettings(); 
    windowUserSettings.Show(); 
} 

,如果我從它的關閉按鈕關閉WPF,如果我再次點擊按鈕來處理窗口的表演,這是行不通的。 我想關閉動作不僅僅是一個簡單的隱藏,所以我的目標是重寫關閉動作。我試圖在截止方法工作*我的XAML窗口WpfUserSettings_Window_Closing *:

<Window x:Class="TrainingForgeOutlookAddin.View.WpfUserSettings" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
     xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
     mc:Ignorable="d" 
     d:DesignHeight="350" d:DesignWidth="700" Title="User Settings" 
     WindowStartupLocation="CenterScreen" Loaded="WpfUserSettings_OnLoaded" 
     Closing="WpfUserSettings_Window_Closing"> 
.... 
</Window> 

你有任何建議或HOWTO閱讀,我沒發現? 謝謝

回答

0

據我所知,關閉功能會破壞窗口,你不能叫

window.Show() 

多次。這意味着窗口中的所有數據都已丟失。這是有道理的,因爲Window就像您的普通窗口一樣承載您的應用程序的根。實現這一點的方法是在調用.Show()之前創建一個全新的窗口。但是,這會造成您的數據未保存的問題。一旦你打開你的新窗口,它會再次變成空白。雖然這不是你問題的一部分,但我認爲有些人可能會覺得這很有用。

爲此,您需要使兩個Windows對話才能保存數據。父母將堅持孩子的數據,然後將其交給新創建的窗口重新填充。

有些人更喜歡代表,我更喜歡爲此使用接口。

定義一個簡單的界面。這建立了孩子與父窗口之間的關係,並允許孩子通知其關閉並將其數據返回以保持安全。

public interface IParentWindow 
{ 
    void ChildClosed(SomeData data); 
} 

這將告知孩子已經被關閉父窗口,現在窗口,直到再次打開該窗口可以抓住的數據。

分配此父窗口:

public partial class MainWindow : Window, IParentWindow 

這將迫使你實現ChildClosed功能。在我們這樣做之前,你會注意到我定義了SomeData。只要兩個窗口都使用它來回發送數據,這可以是任何你喜歡的東西。

對於我來說,SomeData實施看起來是這樣的:

public struct SomeData 
{ 
    public string name; 
    public string email; 
} 

我們爲什麼我做了這個一個結構的爭論,但這是除了點。如果你願意,你可以把它變成一個班。

接下來,執行小孩關閉功能。對於這一點,在父類範圍創建SomeData對象:

SomeData lastWindowData; 

而這個功能是如何告訴父母抓住它的數據

public void ChildClosed(SomeData data) 
{ 
    lastWindowData.email = data.email; 
    lastWindowData.name = data.name; 
} 

好了,才移動到子窗口,我們必須實施窗口的開放。因爲,正如我發現的那樣(請告訴我有另一種解決方法?),一旦關閉窗口就不能重新打開。這意味着我們必須創造一個全新的窗口。把這個在你的事件,無論打開的窗口:

childWindow = new ChildWindow(lastWindowData, this); 
childWindow.Show(); 

,你會發現,在窗口取數據和「本」,這是我們的父窗口。它這樣做是爲了能夠在關閉之前回到父窗口並允許父窗口保存數據。

讓我們移動到子窗口。

修改子窗口的構造函數以接受SomeData和IParentWindow對象。回顧一下,IParentWindow是打開孩子的窗口。

public ChildWindow(SomeData data, IParentWindow parent) 

現在我們來保存從父項傳遞的數據!

定義你的窗口數據持有者也就是一些SomeData對象(子窗口類中)

SomeData myData; 

,並在構造函數中

myData.email = data.email; 
    myData.name = data.name; 

,所以我們可以重新填充一切。你可以自己找出重新分配的部分。這樣,窗口現在已經接收到先前關閉的子窗口的數據,我們可以像恢復之前的窗口一樣恢復它!

當您在窗口中執行某些操作(可能是任何地方的任何操作)時,您可以改變數據。說我給你一個姓名和電子郵件:

myData.email = "[email protected]"; 
    myData.name = "Gordon Freeman"; 

最後但並非最不重要的,一旦我們關閉子窗口中,我們可以告訴孩子被關閉父窗口,我們可以給它最近更新的數據保存再來一次!

protected override void OnClosed(EventArgs e) 
    { 
     parent.ChildClosed(myData); 
     base.OnClosed(e); 
    } 

沖洗並重復!

注意;對於第一次打開,在你有任何保存的數據之前,你可以傳入一個帶有空變量的對象。然後,您可以在子窗口中根據此確定是否需要更新UI。

+0

嗨@ serguei-fedorov,它不是很清楚我應該在哪裏放置'公共ChildWindow(SomeData數據,IParentWindow父母)'。您正在討論* window *構造函數,並且在我的_WPF場景_中,這是我的構造函數'public WpfUserSettings() { InitializeComponent(); }'但我不知道如何用你的建議來管理它。 – axel

+0

您必須修改子窗口構造函數才能使用這些變量。這將是公共的WpfUserSettings(有些數據,IParentWindow)記住SomeData對象應該由你定義。我想我必須問的問題是,當窗口關閉並重新打開時,是否要保存數據?如果不是,則丟棄數據對象。就我所知,您將需要進行接口,以便告訴父窗口該子項已關閉(並設置了一個布爾值,以便它不會再次打開)。這是IParentWindow,在我的例子中,它被作爲「this」傳遞給構造函數。 –

+0

如果您希望我專門針對您的情況減少答案,我可以爲您發佈第二個答案。 –