InvokeRequired и ToolStripStatusLabel

В моем приложении у меня есть класс, который отвечает за все действия базы данных. Он вызывается из основного класса и использует делегаты для вызова методов после завершения действия. Поскольку он асинхронный, я должен использовать invoke в моем графическом интерфейсе, поэтому я создал простой метод расширений:

 public static void InvokeIfRequired<T>(this T c, Action<T> action)
            where T: Control
        {
            if (c.InvokeRequired)
            {
                c.Invoke(new Action(() => action(c)));
            }
            else
            {
                action(c);
            }
        }

Это прекрасно работает, когда я пытаюсь вызвать его на textBox:

textBox1.InvokeIfRequired(c => { c.Text = "it works!"; });

но когда я пытаюсь вызвать его на ToolStripStatusLabel или ToolStripProgressBar, я получаю сообщение об ошибке:

Тип 'System.Windows.Forms.ToolStripStatusLabel' нельзя использовать в качестве параметра типа 'T' в универсальном типе или методе 'SimpleApp.Helpers.InvokeIfRequired (T, System.Action)'. Не существует неявного преобразования ссылок из 'System.Windows.Forms.ToolStripStatusLabel' в 'System.Windows.Forms.Control'.

Я знаю, что это, вероятно, простое исправление, но я могу справиться с этим:/

2 ответа

Решение

Это потому, что ToolStripItem (основа для тех двух, которые вызывают ошибку) является компонентом, а не элементом управления. Попробуйте вызвать свой метод расширения на панели инструментов, которой они принадлежат, и настройте методы делегата.

Я хотел бы добавить к принятому решению. Вы можете получить элемент управления из компонента, используя метод GetCurrentParent из ToolStripStatusLabel.

Вместо того чтобы делать toolStripStatusLabel1.InvokeIfRequired, делать toolStripStatusLabel1.GetCurrentParent().InvokeIfRequired

Метод расширения с использованием GetCurrentParent().InvokeRequired

public static void ToolStripStatusInvokeAction<TControlType>(this TControlType control, Action<TControlType> del)
    where TControlType : ToolStripStatusLabel
    {
        if (control.GetCurrentParent().InvokeRequired)
            control.GetCurrentParent().Invoke(new Action(() => del(control)));
        else
            del(control);
    }

Вызов расширения ToolStripStatusInvokeAction:

toolStripAppStatus.ToolStripStatusInvokeAction(t =>
{ 
    t.Text= "it works!";
    t.ForeColor = Color.Red;
});
Другие вопросы по тегам