Ну, здесь есть две отдельные проблемы:
- Обновление интерфейса другого класса
- Обновление интерфейса из другого потока
Они почти полностью ортогональны. Как только вы решите каждый из них в отдельности, вы можете соединить их вместе.
Если есть понятные способы изменения пользовательского интерфейса (например, обновление текста в строке состояния или что-то в этом роде), я бы написал методы в самом классе пользовательского интерфейса, чтобы сделать это, и просто вызывал эти методы. из другого класса. Кроме того, вы можете предоставить индивидуальный контроль над пользовательским интерфейсом - предпочтительно через свойства - и затем использовать Control.Invoke
обычным способом из другого класса, например,
MethodInvoker action = () => form.StatusLabel.Text = "Finished";
form.BeginInvoke(action);
Пока вы вызываете Invoke
для элемента управления, который "живет" в том же потоке, что и все элементы управления, к которым вы прикасаетесь, не имеет значения, какой из них вы используете ... поэтому альтернатива может быть:
Label label = form.StatusLabel;
MethodInvoker action = () => label.Text = "Finished";
label.BeginInvoke(action);
Одно из отличий состоит в том, что в этом последнем коде свойство StatusLabel
оценивается в рабочем потоке - что может привести к условиям гонки, если ваш пользовательский интерфейс меняет его на ссылки на другие метки в разные времена. Я бы вообще предпочел первый подход.
(Я согласен с комментарием icktoofay о том, что BeginInvoke
предпочтительнее, если только вам действительно не нужно ждать, между прочим ... хотя тогда вам нужно быть осторожным с изменениями любых переменных, захваченных анонимными функциями.)