Как исправить проблемы с мерцанием вложенного элемента управления winform - PullRequest
11 голосов
/ 26 февраля 2010

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

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

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

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

Ответы [ 4 ]

14 голосов
/ 26 февраля 2010

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

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

2 голосов
/ 26 февраля 2010

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

0 голосов
/ 26 февраля 2010

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

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

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

0 голосов
/ 26 февраля 2010

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

...