Часто в процессе разработки программы на C# WindowsForms требуется получить доступ к элементу управления, который находится в другом потоке, зачастую родительском, т.е. представляет собой элемент управления, созданный в конструкторе.
К сожалению, прямое обращение к элементам управления формы C# доступно, но может привести к различным "глюкам", которые могут быть не очень очевидны. Поэтому стоит всегда пользоваться безопасным методом обращения, в случае, если вы заранее знаете, что собираетесь обращаться к интерфейсу из потоков.
Решение достаточно простое - для обращения используйте специальную функцию с Invoke (проверка InvokeRequired ). В примере ниже будет из потока устанавливаться свойство ProgressBar-а - достаточно частая задача, которая стоит перед С# WindowsForms да и другими разработчиками для оповещения пользователя о том, как продвигается процесс.
public void SetProgress(int value)
{
if ( InvokeRequired )
{
this.Invoke(new Action(SetProgress), new object[] { value });
return;
}
_PB_Progress.Value = value;
}
Как видим, если требуется безопасное обращения (т.е. мы находимся не в родительском потоке), то он вызывает сам себя из этого потока.
Если у нас несколько аргументов в функции (к примеру, обновляем DataGridView из потока), то все они должны перечисляться через запятую в острых скобках и точно так же через запятую в фигурных скобках - {значение1, значение2}. Естественно, в параметре Action указываем имя нашей функции в C#, которая будет выполнять обращение к элементам управления из другого потока.
|