[英]Why can't show FolderBrowserDialog twice in Window constructor?
出於好奇,我想知道為什么我不能在Window
的構造函數中一個接一個地顯示FolderBrowserDialog
兩個不同實例,但是可以在Window
的Loaded
事件中做到這一點。
fbd1
),沒有顯示下一個對話框。 范例1:
public partial class MainWindow : Window {
public MainWindow() {
InitializeComponent();
using (var fbd1 = new FolderBrowserDialog()) {
fbd1.ShowDialog();
}
using (var fbd2 = new FolderBrowserDialog()) {
fbd2.ShowDialog();
}
}
}
范例2:
public partial class MainWindow : Window {
public MainWindow() {
InitializeComponent();
}
private void Window_Loaded(object sender, RoutedEventArgs e) {
using (var fbd1 = new FolderBrowserDialog()) {
fbd1.ShowDialog();
}
using (var fbd2 = new FolderBrowserDialog()) {
fbd2.ShowDialog();
}
}
}
順便說一句,我也已經使用WinForms進行了測試,這幾乎是相同的。
它在Form
的構造函數和 Form
的Load
事件中無效,但在Shown
事件中有效。
您喜歡的答案實際上不是正確的答案,它確實會激活第二個對話框。 激活狀態和Z順序是不同的Windows屬性。 您只是看不到對話框,因為您丟失了前景。 只有當您擁有可以留在前景中的窗戶時,您才能保留一個。
程序啟動后,需要約6秒鍾才能用自己的窗口竊取前景。 超時很容易看到,Windows顯示Cursors.AppStarting光標(帶有沙漏的小箭頭)。 這樣可以使第一個對話框進入前台。 但是接下來發生的事情注定會出錯。 當用戶關閉對話框時,您的應用程序沒有剩余可移動到前台的窗口。 Windows現在正在尋找另一個放置在前台的窗口,這不可避免地是另一個進程擁有的。 例如,當您調試時,很有可能是VS主窗口。 而6秒已到期。 第二個對話框將出現並被激活,但是當然它被那個窗口覆蓋了。
一個冷酷的事實是,對話框必須始終具有所有者。 FolderBrowserDialog對此太寬容了,它為您提供了一個ShowDialog()重載而沒有所有者參數。 很方便,並不總是正確的。 它在后台使用GetActiveWindow()查找所有者。 如果沒有一個,則桌面窗口將成為所有者,向前麻煩,否則不會引發異常。
正如Reza Aghaei在第二點評論中所說:
當您關閉第一個對話框時,將顯示第二個對話框,但是由於您的
Form
目前不可見並且在任務欄中不可見,因此它不會激活第二個對話框 ,而在其他窗口后面會打開它。 只需按Alt + Tab查看打開的窗口,您也會看到第二個對話框。 但是,當您的窗體可見時(例如,在“顯示”中運行代碼時),您將不會遇到此問題。
這就是我的好奇心的答案。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.