Вопрос по multithreading, winforms, c#, delegates, invokerequired – Где UpdateFormText является делегатом

1

у приложение формы в C #, и мне нужно иметь возможность изменять содержимое Rich Text Box из любого потока, я попытался использоватьделегат а такжеInvokeRequired, но делегат, который я сделал, по-прежнему выдает ошибку межпотокового вызова, и InvokeRequired завершает работу формы без выдачи ошибки Функция, которую я должен иметь возможность выполнять из любого потока:

    public static void updateSub(int what)
    {
        subDisplay.subBox.Text = tb[what];
    }

Делегат, которого я пытался использовать:

    public delegate void UpdateDelegateVoid(int what);
    static public UpdateDelegateVoid uSub = new UpdateDelegateVoid(updateSub);
    uSub(0);

Мой InvokeRequired код:

    public static void updateSub(int what)
    {
        if (subDisplay.subBox.InvokeRequired)
        {
            subDisplay.subBox.Invoke(new MethodInvoker(finish));
        }
        else
        {
            subDisplay.subBox.Text = tb[what];
        }
    }

Я не совсем уверен, почему приведенный выше код не работает. Спасибо!

Извините но что такоеfinish? Что такоеMethodInvoker? R. Martinho Fernandes
@Martinho:MethodInvoker существует до .Net 1.1 и использовался ранееAction возникшие. Oliver
Чтобы приблизиться к точке, где происходит исключение, вы должны открыть в Visual StudioОтладка - исключения и проверьте все флажки. В этом случае компилятор сломается до того, как будет сгенерировано исключение. Oliver
Что этот бит делаетsubDisplay.subBox.Invoke(new MethodInvoker(finish)) и почему это в статическом методе, конечно, это должно быть в случаеsubDisplay, ЯвляетсяsubDisplay статическое свойство? Jodrell

Ваш Ответ

3   ответа
1

если требуется вызов.

public void UpdateSub(string message)
{
    if (!subDisplay.subBox.InvokeRequired)
    {
        subDisplay.subBox.Text = message;
    }
    else
    {
        var d = new UpdateFormText(UpdateSub);
        Invoke(d, new object[] { message });
    }
}

Где UpdateFormText является делегатом

public delegate void UpdateFormText(string message);
2

и это прекрасно работает. Для той же цели, что вы намерены.

public void UpdateSub(string message)
{
    subDisplay.subBox.Invoke((Action)delegate {
        subDisplay.subBox.Text = message;
    });
}

Надеюсь, это поможет вам или кому-то еще в этом!

Что такое "действие"? Peter Kelly
3

когда вы проверяетеInvokeRequired и найти этоtrueВы должны сделать звонокк тому же методу, Я не уверен, что это решит вашу конкретную проблему (мне нужно увидеть больше деталей об исключениях и код), но я имею в виду следующее:

public static void updateSub(int what)
{
    if (subDisplay.subBox.InvokeRequired)
    {
        subDisplay.subBox.Invoke(new Action<int>(updateSub), what);
    }
    else
    {
        subDisplay.subBox.Text = tb[what];
    }
}

Если вы получаете «странное поведение», то убедитесь, что форма действительно создана в главном потоке приложения. В WinForms это не принудительно (как в WPF), поэтому вполне возможно, что поток, в котором была создана форма, на самом деле не является корневым потоком приложения.

@Neil Умм, причина, по которой MethodInvoker 'сбивал' форму, заключается в том, что я случайно поместил MethodInvoker (финиш) вместо MethodInvoker (updateSub), я предполагаю, что это сработает, если я это изменит ... Хотя я нашел способ чтобы сделать правильный вызов между потоками: `displaySub.Invoke ((MethodInvoker) делегат {subDisplay.subBox.Text = tb [what];});` George Korac
Но это не сработает.MethodInvoker является делегатом для вызова методов без параметров и возвращаемого значения. Но updateSub имеет параметр int ... takrl
@Martinho: я получал ошибку между потоками, когда использовал делегата, хотя «сбой формы», который я получал при использовании MethodInvoke, был просто вызван моей глупостью ... :) George Korac
@ Джордж: так, на самом деле вы не получили ошибку между потоками, верно? R. Martinho Fernandes
@takrl Хороший вопрос, и именно поэтому SO должен иметь встроенный компилятор. :) Я обновился до общегоAction вместо. Neil Barnwell

Похожие вопросы