.net 2010 Вызов Doevents (да, я хочу) изнутри пользовательской библиотеки управления

StackOverflow https://stackoverflow.com/questions/3760069

Вопрос

У меня есть библиотека пользовательского контроля. Теперь есть контроль, который выглядит как панель, и когда она открывается, я хочу оживить его вертикальные, как это:

For h As Single = 0 To finalHeight Step 0.5
    Me.Height = CInt(h)
    '  HERE I WANT TO CALL DoEvents'
Next
Me.Height = finalHeight 

Если я не называю Doevents в петле, тогда анимация не отображается, я получаю только окончательную высоту без визуальной обратной связи по пути.

Я могу назвать DoEvents изнутри моего главного проекта WinForm, но не могу внутри библиотеки.

Как я могу это сделать, не тонув в воду глубоких нитей?

Это было полезно?

Решение 6

Это то, что я нашел: таймер, даже с быстрыми интервалами, это действительно медленно. Я не знаю почему, но анимация очень крутится с таймером. Упрощенный код:

 rolex = New Timer()
 rolex.Interval = 150
 AddHandler rolex.Tick,
            Sub(sender As Object, e As EventArgs)

                Me.Height += 5

                If Me.Height < finalHeight Then Exit Sub

                rolex.Stop()
                rolex = Nothing

                Me.Height = finalHeight 
            End Sub
 rolex.Start()

Без таймера я использую цикл:

For i As Single = 0 To finalHeight Step 0.5
            Height = CInt(i)
            Application.DoEvents()
Next
Height = finalHeight 

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

Любые подсказки?

Другие советы

Извините, но совершенно невозможно сделать использование DoEvents Safe здесь. Ничего хорошего не произойдет, когда пользователь закрывает форму, пока ваша анимация идет. Он будет разорвать программу с помощью ObjectDisposed исключением. Создание DoEvents Safe требует установки внутреннего свойства формы для False, чтобы пользователь не мог случайно привести к тому, что Mishaps подобно. Управление не может разумно установить Форма Включено свойство на ложь, особенно не для анимации.

Обходной путь достаточно прост, просто используйте таймер с интервалом 15 мсек. Достаточно быстро, чтобы анимация выглядела гладкой. Вы найдете пример код, который делает это в моем ответе в эта нить.

Может быть, вы просто пропустите ссылку на (или импорт) System.Windows.Forms? DoEvents является статическим методом Application, Так что вы должны иметь возможность называть это из библиотеки.

Imports System.Windows.Forms

...

    Application.DoEvents()

(Вы уже знаете, что использовать DoEvents Это опасная вещь, поэтому я буду пропустить обычную лекцию здесь.)

Да, вы должны быть в состоянии позвонить

System.Windows.Forms.Application.DoEvents()

Изнутри вашей библиотеки кода. Похоже, вы понимаете, что DoEvents - плохая идея, поэтому я не уверен, почему вы его называете. Я предполагаю, что у вас есть это поместить внутри переопределения, такого как onvisibleChangeded, или OnPaint - если это так, вы, скорее всего, не получите результаты, которые вы последуете, поскольку контроль обновления будет приостановлен во время этих операций.

То, что вы, вероятно, хотите сделать, это создать таймер одним тиком, и на тике увеличить высоту контроля - отключите таймер, когда Finalheight достигнут или запланируйте еще один тик, если нет. Или создайте таймер и поместите свой приведенный цикл в нем на каждом тике. Убедитесь, что вы знаете о InvokeRequired и перекрестные вызовы в зависимости от того, какой тип таймера вы используете.

Неспособность воспроизвести.

Просто проверено с простой настройкой, USERCONTROL в сборке.

Таймер в Mainform продолжает тикать, когда UC вызывает DoEvents () в цикле.

Так что: Посмотрите еще раз для своей проблемы, это не то, где вы думаете, что это так.

В вашем оригинале для петли, поместите Me.Refresh где вы хотели назвать доверенно.

For h As Single = 0 To finalHeight Step 0.5
    Me.Height = CInt(h)
    Me.refresh
Next
Me.Height = finalHeight
Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top