Вам не нужно блокировать графический интерфейс, вам просто нужно вызвать invoke:
Элементы управления в Windows Forms связаны с
конкретная нить и не нить
безопасный. Поэтому, если вы звоните
Метод управления из другого
нить, вы должны использовать один из
методы вызова элемента управления для маршала
вызов в нужную ветку. это
свойство может быть использовано для определения
Вы должны вызвать метод вызова, который
может быть полезным, если вы не знаете, что
поток владеет контролем. исх
Вот как это выглядит в коде:
public delegate void ComponentReadyDelegate(YourComponent component);
public void LoadComponent(YourComponent component)
{
if (this.InvokeRequired)
{
ComponentReadyDelegate e = new ComponentReadyDelegate(LoadComponent);
this.BeginInvoke(e, new object[]{component});
}
else
{
// The component is used by a UI control
component.DoSomething();
component.GetSomething();
}
}
// From the other thread just initialize the component
// and call the LoadComponent method on the GUI.
component.Initialize(); // 5-15 seconds
yourForm.LoadComponent(component);
Обычно вызов LoadComponent
из другого потока вызовет исключение между потоками, но в описанной выше реализации метод будет вызываться в потоке GUI.
InvokeRequired
сообщает вам, если:
вызывающая сторона должна вызвать метод invoke
при вызове метода к
контролировать, потому что вызывающий абонент находится на
другой поток, чем тот, который
контроль был создан на.
исх
Обновление:
Поэтому, если я правильно вас понимаю, объект управления создается в потоке, отличном от потока GUI, поэтому даже если вы смогли передать его в поток GUI, вы все равно не сможете использовать его, не вызвав межпотоковое исключение , Решением было бы создать объект в потоке GUI, но инициализировать его в отдельном потоке:
public partial class MyForm : Form
{
public delegate void ComponentReadyDelegate(YourComponent component);
private YourComponent _component;
public MyForm()
{
InitializeComponent();
// The componet is created on the same thread as the GUI
_component = new YourComponent();
ThreadPool.QueueUserWorkItem(o =>
{
// The initialization takes 5-10 seconds
// so just initialize the component in separate thread
_component.Initialize();
LoadComponent(_component);
});
}
public void LoadComponent(YourComponent component)
{
if (this.InvokeRequired)
{
ComponentReadyDelegate e = new ComponentReadyDelegate(LoadComponent);
this.BeginInvoke(e, new object[]{component});
}
else
{
// The component is used by a UI control
component.DoSomething();
component.GetSomething();
}
}
}