#c# #wpf #multithreading #mvvm #caliburn.micro
#c# #wpf #многопоточность #mvvm #caliburn.micro
Вопрос:
У меня есть приложение caliburn.micro WPF, и я запускаю его из F # с помощью вызова этой функции:
public void LaunchGUI()
{
if (_guiWindow == null)
{
var windowThread = new Thread(() =>
{
try
{
// Create our context, and install it:
SynchronizationContext.SetSynchronizationContext(new DispatcherSynchronizationContext(Dispatcher.CurrentDispatcher));
AppBootstrapper.Initialize();
var app = new App();
app.InitializeComponent();
//guiWindow = app.MainWindow;
//// When the window closes, shut down the dispatcher
//guiWindow.Closed = (s, e) =>
// Dispatcher.CurrentDispatcher.BeginInvokeShutdown(DispatcherPriority.Background);
//guiWindow.Closed = (s, e) =>
// guiWindow = null;
//guiWindow.WindowState = WindowState.Minimized;
//guiWindow.Show();
//guiWindow.WindowState = WindowState.Normal;
//guiWindow.Activate();
// Start the Dispatcher Processing
Dispatcher.Run();
}
catch (Exception e)
{
LogMessage("error in gui thread: " e);
//guiWindow.Close();
//guiWindow = null;
}
});
windowThread.SetApartmentState(ApartmentState.STA);
windowThread.IsBackground = true;
windowThread.Start();
}
else
{
_guiWindow.WindowState = WindowState.Minimized;
_guiWindow.Show();
_guiWindow.WindowState = WindowState.Normal;
_guiWindow.Activate();
}
}
}
Проблема в том, что мне нужно иметь ссылку на главное окно, чтобы я мог отслеживать, открыто ли оно все еще и т.д., Но оно всегда равно null (отсюда и прокомментированный код). Обратите внимание, что это отлично работает при запуске «обычного» приложения MVVM и инициализации его аналогичным образом:
public void ShowGui()
{
if (guiWindow == null)
{
var windowThread = new Thread(() =>
{
try
{
// Create our context, and install it:
SynchronizationContext.SetSynchronizationContext(
new DispatcherSynchronizationContext(
Dispatcher.CurrentDispatcher));
guiWindow = new MainWindow();
// When the window closes, shut down the dispatcher
guiWindow.Closed = (s, e) =>
Dispatcher.CurrentDispatcher.BeginInvokeShutdown(DispatcherPriority.Background);
guiWindow.Closed = (s, e) =>
guiWindow = null;
guiWindow.WindowState = WindowState.Minimized;
guiWindow.Show();
guiWindow.WindowState = WindowState.Normal;
guiWindow.Activate();
// Start the Dispatcher Processing
Dispatcher.Run();
}
catch (Exception)
{
try
{
guiWindow.Close();
}
catch (Exception)
{
throw;
}
guiWindow = null;
}
});
windowThread.SetApartmentState(ApartmentState.STA);
windowThread.IsBackground = true;
windowThread.Start();
}
else
{
guiWindow.WindowState = WindowState.Minimized;
guiWindow.Show();
guiWindow.WindowState = WindowState.Normal;
guiWindow.Activate();
}
}
Мой вопрос в том, как мне получить доступ к созданному главному окну?
Ответ №1:
// вы получаете основные окна приложения следующим образом:
var _guiWindow = Приложение.Текущий.MainWindow как MainWindow;
Комментарии:
1. Это всегда значение null, независимо от того, пытаюсь ли я получить к нему доступ из основного потока или из потока GUI, который я создал здесь.
2. Неважно, похоже, что это была проблема с потоками (потребовалось немного подождать, пока оно будет инициализировано). Теперь у меня возникла проблема с попыткой получить доступ к нему из другого потока, но это уже другая тема. Спасибо.