Как исправить проблемы с мерцанием вложенного элемента управления winform

В настоящее время я работаю над программой, которая использует довольно сложную структуру вложенных элементов управления winform, которая динамически изменяется, когда пользователь делает определенные выборы. Более подробно о конкретной компоновке элементов управления было бы слишком много для этого вопроса.

Когда бы ни был сделан выбор, в основную модель, которая контролируется пользовательскими элементами управления, вносится множество обновлений. Это приводит к серии соответствующих изменений в размере / положении / видимости отображаемых элементов управления. Все эти изменения приводят к мучительно интенсивному мерцанию элементов управления на экране. Мне нужно как-то исправить это так, чтобы каждый раз, когда пользователь делает выбор, экран в основном зависал до тех пор, пока все обновления элемента управления не будут завершены.

Я попытался использовать методы Control.SuspendLayout/Control.ResumeLayout во многих различных местах и ​​способах, и я не могу устранить сумасшедшее мерцание. Я думал, что приостановка макета на корневом элементе управления во время изменений решит проблему, но кажется, что этот SuspendLayout не помогает при изменении дочерних элементов управления.

Нужно ли использовать какой-то другой подход, а не SuspendLayout? Есть ли способ отладки SuspendLayout, чтобы увидеть, почему он не выглядит каскадным для всех дочерних элементов управления?

4 ответа

Приостановить /ResumeLayout не ваша проблема здесь. Это только приостанавливает автоматическую разметку, которая вызывается свойствами Anchor и Dock. Двойная буферизация также не может решить вашу проблему, которая только подавляет мерцание в каждом отдельном элементе управления. Ваша настоящая проблема заключается в том, что вы одновременно обновляете слишком много элементов управления, каждый из которых по очереди рисует сам, и это требует времени.

То, что вам нужно, это другой вид двойной буферизации, композитинга. Проверьте, решает ли решение в этой теме вашу проблему.

В дополнение к предложению @tommieb75 для двойной буферизации, вы можете попробовать и посмотреть, есть ли у ваших элементов управления корневого уровня BeginUpdate/EndUpdate метод пар. Это должно помочь подавить перерисовки между вызовами.

Использовать SetControlStyles в пользовательском элементе управления флаг OptimizedDoubleBuffer что предотвратит мерцание.

Если вы используете WinForms 2+, вы можете просто установить "Управление. DoubleBuffer'свойство на элементе управления true (даже в дизайнере).

В фреймворке 2 установка DoubleBuffered устанавливает 3 флага: OptimizedDoubleBuffer, AllPaintingInWmPaint и еще один, который я забыл, возможно, "UserPaint".

Кроме того, посмотрите на BeginUpdate/EndUpdate, как упомянуто @yetapb.

Другие вопросы по тегам